diff --git a/common/tool/tool_manager.cpp b/common/tool/tool_manager.cpp index 4c6cb8bc80..9155aa9790 100644 --- a/common/tool/tool_manager.cpp +++ b/common/tool/tool_manager.cpp @@ -285,7 +285,8 @@ bool TOOL_MANAGER::InvokeTool( const std::string& aToolName ) } -bool TOOL_MANAGER::doRunAction( const std::string& aActionName, bool aNow, std::any aParam ) +bool TOOL_MANAGER::doRunAction( const std::string& aActionName, bool aNow, std::any aParam, + COMMIT* aCommit ) { TOOL_ACTION* action = m_actionMgr->FindAction( aActionName ); @@ -295,7 +296,7 @@ bool TOOL_MANAGER::doRunAction( const std::string& aActionName, bool aNow, std:: return false; } - doRunAction( *action, aNow, aParam ); + doRunAction( *action, aNow, aParam, aCommit ); return false; } @@ -319,7 +320,8 @@ VECTOR2D TOOL_MANAGER::GetCursorPosition() const } -bool TOOL_MANAGER::doRunAction( const TOOL_ACTION& aAction, bool aNow, std::any aParam ) +bool TOOL_MANAGER::doRunAction( const TOOL_ACTION& aAction, bool aNow, std::any aParam, + COMMIT* aCommit ) { if( m_shuttingDown ) return true; @@ -334,6 +336,10 @@ bool TOOL_MANAGER::doRunAction( const TOOL_ACTION& aAction, bool aNow, std::any if( aParam.has_value() ) event.SetParameter( aParam ); + // Pass the commit (if any) + if( aCommit ) + event.SetCommit( aCommit ); + if( aNow ) { TOOL_STATE* current = m_activeState; diff --git a/eeschema/tools/sch_edit_tool.cpp b/eeschema/tools/sch_edit_tool.cpp index 6494bdd40f..bb900459d5 100644 --- a/eeschema/tools/sch_edit_tool.cpp +++ b/eeschema/tools/sch_edit_tool.cpp @@ -676,7 +676,7 @@ int SCH_EDIT_TOOL::Rotate( const TOOL_EVENT& aEvent ) VECTOR2I rotPoint; bool moving = false; SCH_COMMIT localCommit( m_toolMgr ); - SCH_COMMIT* commit = aEvent.Parameter(); + SCH_COMMIT* commit = dynamic_cast( aEvent.Commit() ); if( !commit ) commit = &localCommit; @@ -944,7 +944,7 @@ int SCH_EDIT_TOOL::Mirror( const TOOL_EVENT& aEvent ) bool connections = false; bool moving = item->IsMoving(); SCH_COMMIT localCommit( m_toolMgr ); - SCH_COMMIT* commit = aEvent.Parameter(); + SCH_COMMIT* commit = dynamic_cast( aEvent.Commit() ); if( !commit ) commit = &localCommit; diff --git a/eeschema/tools/sch_move_tool.cpp b/eeschema/tools/sch_move_tool.cpp index 2bb1a51399..770068f0fb 100644 --- a/eeschema/tools/sch_move_tool.cpp +++ b/eeschema/tools/sch_move_tool.cpp @@ -361,7 +361,7 @@ int SCH_MOVE_TOOL::Main( const TOOL_EVENT& aEvent ) bool wasDragging = m_moveInProgress && m_isDrag; bool isSlice = false; SCH_COMMIT localCommit( m_toolMgr ); - SCH_COMMIT* commit = aEvent.Parameter(); + SCH_COMMIT* commit = dynamic_cast( aEvent.Commit() ); if( !commit ) commit = &localCommit; diff --git a/eeschema/tools/symbol_editor_edit_tool.cpp b/eeschema/tools/symbol_editor_edit_tool.cpp index 82284e4093..6f69c5f1bb 100644 --- a/eeschema/tools/symbol_editor_edit_tool.cpp +++ b/eeschema/tools/symbol_editor_edit_tool.cpp @@ -158,7 +158,7 @@ int SYMBOL_EDITOR_EDIT_TOOL::Rotate( const TOOL_EVENT& aEvent ) bool ccw = ( aEvent.Matches( EE_ACTIONS::rotateCCW.MakeEvent() ) ); LIB_ITEM* item = static_cast( selection.Front() ); SCH_COMMIT localCommit( m_toolMgr ); - SCH_COMMIT* commit = aEvent.Parameter(); + SCH_COMMIT* commit = dynamic_cast( aEvent.Commit() ); if( !commit ) commit = &localCommit; diff --git a/eeschema/tools/symbol_editor_move_tool.cpp b/eeschema/tools/symbol_editor_move_tool.cpp index da31f34850..c5791e0199 100644 --- a/eeschema/tools/symbol_editor_move_tool.cpp +++ b/eeschema/tools/symbol_editor_move_tool.cpp @@ -92,7 +92,7 @@ int SYMBOL_EDITOR_MOVE_TOOL::Main( const TOOL_EVENT& aEvent ) { KIGFX::VIEW_CONTROLS* controls = getViewControls(); SCH_COMMIT localCommit( m_toolMgr ); - SCH_COMMIT* commit = aEvent.Parameter(); + SCH_COMMIT* commit = dynamic_cast( aEvent.Commit() ); if( !commit ) commit = &localCommit; diff --git a/include/tool/tool_event.h b/include/tool/tool_event.h index 70d810b5f9..e5af59f318 100644 --- a/include/tool/tool_event.h +++ b/include/tool/tool_event.h @@ -38,6 +38,7 @@ #include #include +class COMMIT; class TOOL_ACTION; class TOOL_MANAGER; class TOOL_BASE; @@ -172,6 +173,7 @@ public: m_mouseButtons( 0 ), m_keyCode( 0 ), m_modifiers( 0 ), + m_commit( nullptr ), m_firstResponder( nullptr ) { init(); @@ -185,6 +187,7 @@ public: m_mouseButtons( 0 ), m_keyCode( 0 ), m_modifiers( 0 ), + m_commit( nullptr ), m_firstResponder( nullptr ) { if( aCategory == TC_MOUSE ) @@ -216,6 +219,7 @@ public: m_mouseButtons( 0 ), m_keyCode( 0 ), m_modifiers( 0 ), + m_commit( nullptr ), m_firstResponder( nullptr ) { if( aCategory == TC_COMMAND || aCategory == TC_MESSAGE ) @@ -253,6 +257,9 @@ public: bool IsReactivate() const { return m_reactivate; } void SetReactivate( bool aReactivate = true ) { m_reactivate = aReactivate; } + void SetCommit( COMMIT* aCommit ) { m_commit = aCommit; } + COMMIT* Commit() const { return m_commit; } + ///< Returns information about difference between current mouse cursor position and the place ///< where dragging has started. const VECTOR2D Delta() const @@ -435,8 +442,9 @@ public: /** * Return a parameter assigned to the event. Its meaning depends on the target tool. */ - template - T Parameter( typename std::enable_if::value>::type* = 0 ) const + template::value>* = nullptr > + T Parameter() const { T param; @@ -459,8 +467,9 @@ public: /** * Return pointer parameter assigned to the event. Its meaning depends on the target tool. */ - template - T Parameter( typename std::enable_if::value>::type* = 0 ) const + template::value>* = nullptr> + T Parameter() const { T param = nullptr; @@ -574,6 +583,9 @@ private: ///< State of key modifiers (Ctrl/Alt/etc.) int m_modifiers; + /// Commit the tool handling the event should add to + COMMIT* m_commit; + ///< Generic parameter used for passing non-standard data. std::any m_param; diff --git a/include/tool/tool_manager.h b/include/tool/tool_manager.h index e04d074fa9..54a0806f25 100644 --- a/include/tool/tool_manager.h +++ b/include/tool/tool_manager.h @@ -28,15 +28,17 @@ #ifndef __TOOL_MANAGER_H #define __TOOL_MANAGER_H -#include -#include #include +#include #include +#include +#include #include #include #include +class COMMIT; class TOOLS_HOLDER; class TOOL_ACTION; class TOOL_BASE; @@ -139,13 +141,14 @@ public: * depends on the action. * @return False if the action was not found. */ - template + template>* = nullptr> bool RunAction( const std::string& aActionName, T aParam ) { // Use a cast to ensure the proper type is stored inside the parameter std::any a( static_cast( aParam ) ); - return doRunAction( aActionName, true, a ); + return doRunAction( aActionName, true, a, nullptr ); } bool RunAction( const std::string& aActionName ) @@ -153,7 +156,7 @@ public: // Default initialize the parameter argument to an empty std::any std::any a; - return doRunAction( aActionName, true, a ); + return doRunAction( aActionName, true, a, nullptr ); } /** @@ -167,13 +170,32 @@ public: * depends on the action. * @return True if the action was handled immediately */ - template + template>* = nullptr> bool RunAction( const TOOL_ACTION& aAction, T aParam ) { // Use a cast to ensure the proper type is stored inside the parameter std::any a( static_cast( aParam ) ); - return doRunAction( aAction, true, a ); + return doRunAction( aAction, true, a, nullptr ); + } + + /** + * Run the specified action immediately, pausing the current action to run the new one. + * + * Note: The type of the optional parameter must match exactly with the type the consuming + * action is expecting, otherwise an assert will occur when reading the paramter. + * + * @param aAction is the action to be invoked. + * @param aCommit is the commit object the tool handling the action should add the new edits to + * @return True if the action was handled immediately + */ + bool RunAction( const TOOL_ACTION& aAction, COMMIT* aCommit ) + { + // Default initialize the parameter argument to an empty std::any + std::any a; + + return doRunAction( aAction, true, a, aCommit ); } bool RunAction( const TOOL_ACTION& aAction ) @@ -181,7 +203,7 @@ public: // Default initialize the parameter argument to an empty std::any std::any a; - return doRunAction( aAction, true, a ); + return doRunAction( aAction, true, a, nullptr ); } /** @@ -203,7 +225,7 @@ public: // Use a cast to ensure the proper type is stored inside the parameter std::any a( static_cast( aParam ) ); - return doRunAction( aActionName, false, a ); + return doRunAction( aActionName, false, a, nullptr ); } bool PostAction( const std::string& aActionName ) @@ -211,7 +233,7 @@ public: // Default initialize the parameter argument to an empty std::any std::any a; - return doRunAction( aActionName, false, a ); + return doRunAction( aActionName, false, a, nullptr ); } /** @@ -230,7 +252,7 @@ public: // Use a cast to ensure the proper type is stored inside the parameter std::any a( static_cast( aParam ) ); - return doRunAction( aAction, false, a ); + return doRunAction( aAction, false, a, nullptr ); } void PostAction( const TOOL_ACTION& aAction ) @@ -238,7 +260,7 @@ public: // Default initialize the parameter argument to an empty std::any std::any a; - doRunAction( aAction, false, a ); + doRunAction( aAction, false, a, nullptr ); } /** @@ -514,8 +536,8 @@ private: /** * Helper function to actually run an action. */ - bool doRunAction( const TOOL_ACTION& aAction, bool aNow, std::any aParam ); - bool doRunAction( const std::string& aActionName, bool aNow, std::any aParam ); + bool doRunAction( const TOOL_ACTION& aAction, bool aNow, std::any aParam, COMMIT* aCommit ); + bool doRunAction( const std::string& aActionName, bool aNow, std::any aParam, COMMIT* aCommit ); /** * Pass an event at first to the active tools, then to all others.