From 71a9eca750e3ccb7be122c4a8748c66da7fb07da Mon Sep 17 00:00:00 2001 From: Abdullah Tahiri Date: Sun, 15 Oct 2023 06:43:34 +0200 Subject: [PATCH] Sketcher: ToolSettings Widget - Tool Management =============================================== Sets the full interface between the DrawSketchHandler and a tool widget available somewhere in the UI. Signalling is as follows: 1. On activation of the tool, DrawSketchHandler notifies the tool widget. 2. The tool widget retrieves tool information necessary for representation (type of widget, visibility, ...) 3. When the tool widget has created an appropriate widget, it notifies back a widget change. 4. The tool receives the widget handler and can now configure and interact with the widget. --- src/Mod/Sketcher/Gui/DrawSketchHandler.cpp | 41 ++++++++++++++++++ src/Mod/Sketcher/Gui/DrawSketchHandler.h | 35 +++++++++++++++ src/Mod/Sketcher/Gui/TaskDlgEditSketch.cpp | 7 ++- src/Mod/Sketcher/Gui/TaskDlgEditSketch.h | 1 + src/Mod/Sketcher/Gui/TaskSketcherTool.cpp | 24 +++-------- src/Mod/Sketcher/Gui/ViewProviderSketch.cpp | 48 +++++++++++++++++++++ src/Mod/Sketcher/Gui/ViewProviderSketch.h | 27 ++++++++++++ 7 files changed, 163 insertions(+), 20 deletions(-) diff --git a/src/Mod/Sketcher/Gui/DrawSketchHandler.cpp b/src/Mod/Sketcher/Gui/DrawSketchHandler.cpp index b1b4ccf3ef..c7e3fcdc75 100644 --- a/src/Mod/Sketcher/Gui/DrawSketchHandler.cpp +++ b/src/Mod/Sketcher/Gui/DrawSketchHandler.cpp @@ -286,6 +286,27 @@ QString DrawSketchHandler::getCrosshairCursorSVGName() const return QString::fromLatin1("None"); } +std::unique_ptr DrawSketchHandler::createWidget() const +{ + return nullptr; +} + +bool DrawSketchHandler::isWidgetVisible() const +{ + return false; +}; + +QPixmap DrawSketchHandler::getToolIcon() const +{ + return QPixmap(); +} + +QString DrawSketchHandler::getToolWidgetText() const +{ + return QString(); +} + + void DrawSketchHandler::activate(ViewProviderSketch* vp) { sketchgui = vp; @@ -1105,6 +1126,26 @@ void DrawSketchHandler::drawDirectionAtCursor(const Base::Vector2d& position, } } +std::unique_ptr DrawSketchHandler::createToolWidget() const +{ + return createWidget(); // NVI +} + +bool DrawSketchHandler::isToolWidgetVisible() const +{ + return isWidgetVisible(); // NVI +} + +QPixmap DrawSketchHandler::getToolWidgetHeaderIcon() const +{ + return getToolIcon(); +} + +QString DrawSketchHandler::getToolWidgetHeaderText() const +{ + return getToolWidgetText(); +} + void DrawSketchHandler::drawEditMarkers(const std::vector& EditMarkers, unsigned int augmentationlevel) { diff --git a/src/Mod/Sketcher/Gui/DrawSketchHandler.h b/src/Mod/Sketcher/Gui/DrawSketchHandler.h index f2c6f45a30..5971842e23 100644 --- a/src/Mod/Sketcher/Gui/DrawSketchHandler.h +++ b/src/Mod/Sketcher/Gui/DrawSketchHandler.h @@ -178,8 +178,38 @@ public: void resetPositionText(); void renderSuggestConstraintsCursor(std::vector& suggestedConstraints); + /** @name Interfacing with tool dialogs */ + //@{ + + /** @brief Slot to receive signaling that a widget intended for the tool has changed and is + * available ant the provided pointer. + */ void toolWidgetChanged(QWidget* newwidget); + /** @brief Factory function returning a tool widget of the type necessary for the specific tool. + * This is a NVI interface and specific handlers must overload the corresponding virtual + * function. + */ + std::unique_ptr createToolWidget() const; + + /** @brief Returns whether this tool expects/supports a visible tool widget. Emphasis is in + * visibility, so to allow to adapt the interface accordingly. + * This is an NVI interface and specific handlers must overload the corresponding virtual + * function. + */ + bool isToolWidgetVisible() const; + /** @brief Returns a pixmap icon intended for a visible tool widget. + * This is an NVI interface and specific handlers must overload the corresponding virtual + * function. + */ + QPixmap getToolWidgetHeaderIcon() const; + /** @brief Returns a header text intended for a visible tool widget. + * This is an NVI interface and specific handlers must overload the corresponding virtual + * function. + */ + QString getToolWidgetHeaderText() const; + //@} + private: // NVI virtual void preActivated(); virtual void activated() @@ -195,6 +225,11 @@ protected: // NVI requiring base implementation virtual std::string getToolName() const; virtual QString getCrosshairCursorSVGName() const; + virtual std::unique_ptr createWidget() const; + virtual bool isWidgetVisible() const; + virtual QPixmap getToolIcon() const; + virtual QString getToolWidgetText() const; + protected: // helpers /** diff --git a/src/Mod/Sketcher/Gui/TaskDlgEditSketch.cpp b/src/Mod/Sketcher/Gui/TaskDlgEditSketch.cpp index 6ec7ec27b4..fb84095d67 100644 --- a/src/Mod/Sketcher/Gui/TaskDlgEditSketch.cpp +++ b/src/Mod/Sketcher/Gui/TaskDlgEditSketch.cpp @@ -95,12 +95,15 @@ TaskDlgEditSketch::~TaskDlgEditSketch() void TaskDlgEditSketch::slotToolChanged(const std::string& toolname) { - bool hidden = toolname == "DSH_None" || toolname == "DSH_Point"; - ToolSettings->setHidden(hidden); + bool widgetvisible = false; if (toolname != "DSH_None") { + widgetvisible = sketchView->toolManager.isWidgetVisible(); + ToolSettings->toolChanged(toolname); } + + ToolSettings->setHidden(!widgetvisible); } //==== calls from the TaskView =============================================================== diff --git a/src/Mod/Sketcher/Gui/TaskDlgEditSketch.h b/src/Mod/Sketcher/Gui/TaskDlgEditSketch.h index 80e505f9f7..51b4c6701a 100644 --- a/src/Mod/Sketcher/Gui/TaskDlgEditSketch.h +++ b/src/Mod/Sketcher/Gui/TaskDlgEditSketch.h @@ -74,6 +74,7 @@ public: return QDialogButtonBox::Close; } + /** @brief Function used to register a slot to be triggered when the tool widget is changed. */ template boost::signals2::connection registerToolWidgetChanged(F&& f) { diff --git a/src/Mod/Sketcher/Gui/TaskSketcherTool.cpp b/src/Mod/Sketcher/Gui/TaskSketcherTool.cpp index c0ab89492e..7990b44631 100644 --- a/src/Mod/Sketcher/Gui/TaskSketcherTool.cpp +++ b/src/Mod/Sketcher/Gui/TaskSketcherTool.cpp @@ -47,34 +47,22 @@ using namespace Gui::TaskView; TaskSketcherTool::TaskSketcherTool(ViewProviderSketch* sketchView) : TaskBox(Gui::BitmapFactory().pixmap("document-new"), tr("Tool parameters"), true, nullptr) , sketchView(sketchView) -{ - widget = std::make_unique(this, sketchView); - - this->groupLayout()->addWidget(widget.get()); -} +{} TaskSketcherTool::~TaskSketcherTool() {} void TaskSketcherTool::toolChanged(const std::string& toolname) { - // TODO: Implement a factory here to get an appropriate widget from the toolname + Q_UNUSED(toolname) - // At this stage, we add a Default tool widget for all tools with a defined name, but this needs - // to change - if (toolname != "DSH_None") { - widget = std::make_unique(this, sketchView); + widget = sketchView->toolManager.createToolWidget(); + if (widget) { this->groupLayout()->addWidget(widget.get()); - if (toolname == "DSH_Line") { - setHeaderText(tr("Line parameters")); - setHeaderIcon(Gui::BitmapFactory().pixmap("Sketcher_CreateLine")); - } - else if (toolname == "DSH_Circle") { - setHeaderText(tr("Circle parameters")); - setHeaderIcon(Gui::BitmapFactory().pixmap("Sketcher_CreateCircle")); - } + setHeaderText(sketchView->toolManager.getToolWidgetText()); + setHeaderIcon(sketchView->toolManager.getToolIcon()); signalToolWidgetChanged(this->widget.get()); } diff --git a/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp b/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp index dec39feb52..8712ff1489 100644 --- a/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp +++ b/src/Mod/Sketcher/Gui/ViewProviderSketch.cpp @@ -377,6 +377,53 @@ void ViewProviderSketch::ParameterObserver::OnChange(Base::Subject& } } + +/************** ViewProviderSketch::ToolManager *********************/ +ViewProviderSketch::ToolManager::ToolManager(ViewProviderSketch * vp): vp(vp) +{} + +std::unique_ptr ViewProviderSketch::ToolManager::createToolWidget() const +{ + if(vp && vp->sketchHandler) { + return vp->sketchHandler->createToolWidget(); + } + else { + return nullptr; + } +} + +bool ViewProviderSketch::ToolManager::isWidgetVisible() const +{ + if(vp && vp->sketchHandler) { + return vp->sketchHandler->isWidgetVisible(); + } + else { + return false; + } +} + +QPixmap ViewProviderSketch::ToolManager::getToolIcon() const +{ + if(vp && vp->sketchHandler) { + return vp->sketchHandler->getToolIcon(); + } + else { + return QPixmap(); + } +} + +QString ViewProviderSketch::ToolManager::getToolWidgetText() const +{ + if(vp && vp->sketchHandler) { + return vp->sketchHandler->getToolWidgetText(); + } + else { + return QString(); + } +} + + + /*************************** ViewProviderSketch **************************/ // Struct for holding previous click information @@ -395,6 +442,7 @@ PROPERTY_SOURCE_WITH_EXTENSIONS(SketcherGui::ViewProviderSketch, PartGui::ViewPr ViewProviderSketch::ViewProviderSketch() : SelectionObserver(false) + , toolManager(this) , Mode(STATUS_NONE) , listener(nullptr) , editCoinManager(nullptr) diff --git a/src/Mod/Sketcher/Gui/ViewProviderSketch.h b/src/Mod/Sketcher/Gui/ViewProviderSketch.h index 047f664781..1e20e2d46f 100644 --- a/src/Mod/Sketcher/Gui/ViewProviderSketch.h +++ b/src/Mod/Sketcher/Gui/ViewProviderSketch.h @@ -472,6 +472,31 @@ private: SoRenderManager* renderMgr; }; +public: + /* API to retrieve information about the active DrawSketchHandler. In particular related to how + * tool widgets should be handled. + */ + class ToolManager + { + public: + ToolManager(ViewProviderSketch* vp); + + /** @brief Factory function returning a tool widget of the type appropriate for the current + * active tool. If no tool is active, expect a nullptr. + */ + std::unique_ptr createToolWidget() const; + /** @brief Returns whether the current tool's widget is intended to be visible for the user + */ + bool isWidgetVisible() const; + /** @brief Returns the intended icon for a visible tool widget (e.g. for header/title).*/ + QPixmap getToolIcon() const; + /** @brief Returns the intended text for a visible tool widget (e.g. for header/title).*/ + QString getToolWidgetText() const; + + private: + ViewProviderSketch* vp; + }; + public: /// constructor ViewProviderSketch(); @@ -493,6 +518,8 @@ public: SketcherGui::PropertyVisualLayerList VisualLayerList; //@} + const ToolManager toolManager; + // TODO: It is difficult to imagine that these functions are necessary in the public interface. // This requires review at a second stage and possibly refactor it. /** @name handler control */