diff --git a/src/Gui/Navigation/GestureNavigationStyle.h b/src/Gui/Navigation/GestureNavigationStyle.h index 92e5c6874e..dc86f50a64 100644 --- a/src/Gui/Navigation/GestureNavigationStyle.h +++ b/src/Gui/Navigation/GestureNavigationStyle.h @@ -42,6 +42,7 @@ public: GestureNavigationStyle(); ~GestureNavigationStyle() override; const char* mouseButtons(ViewerMode) override; + ClarifySelectionMode clarifySelectionMode() const override { return ClarifySelectionMode::Ctrl; } protected: SbBool processSoEvent(const SoEvent* const ev) override; diff --git a/src/Gui/Navigation/NavigationStyle.h b/src/Gui/Navigation/NavigationStyle.h index 270a1706b8..246471ce08 100644 --- a/src/Gui/Navigation/NavigationStyle.h +++ b/src/Gui/Navigation/NavigationStyle.h @@ -105,6 +105,11 @@ public: Clip = 4, /**< Clip objects using a lasso. */ }; + enum class ClarifySelectionMode { + Default, /**< Long press with LMB to trigger clarify selection */ + Ctrl /**< Long press with Ctrl+LMB to trigger clarify selection */ + }; + enum OrbitStyle { Turntable, Trackball, @@ -192,6 +197,8 @@ public: bool isDraggerUnderCursor(const SbVec2s pos) const; + virtual ClarifySelectionMode clarifySelectionMode() const { return ClarifySelectionMode::Default; } + void setOrbitStyle(OrbitStyle style); OrbitStyle getOrbitStyle() const; @@ -353,6 +360,7 @@ public: ~InventorNavigationStyle() override; const char* mouseButtons(ViewerMode) override; std::string userFriendlyName() const override; + ClarifySelectionMode clarifySelectionMode() const override { return ClarifySelectionMode::Ctrl; } protected: SbBool processSoEvent(const SoEvent * const ev) override; @@ -492,6 +500,7 @@ public: OpenSCADNavigationStyle(); ~OpenSCADNavigationStyle() override; const char* mouseButtons(ViewerMode) override; + ClarifySelectionMode clarifySelectionMode() const override { return ClarifySelectionMode::Ctrl; } protected: SbBool processSoEvent(const SoEvent * const ev) override; diff --git a/src/Gui/PreferencePages/DlgSettingsNavigation.cpp b/src/Gui/PreferencePages/DlgSettingsNavigation.cpp index 97dd29302d..93cad16387 100644 --- a/src/Gui/PreferencePages/DlgSettingsNavigation.cpp +++ b/src/Gui/PreferencePages/DlgSettingsNavigation.cpp @@ -94,6 +94,8 @@ void DlgSettingsNavigation::saveSettings() ui->spinBoxZoomStep->onSave(); ui->spinBoxAnimationDuration->onSave(); ui->checkBoxSpinningAnimations->onSave(); + ui->checkBoxEnableLongPressClarifySelection->onSave(); + ui->spinBoxLongPressTimeout->onSave(); ui->qspinNewDocScale->onSave(); ui->prefStepByTurn->onSave(); ui->naviCubeCorner->onSave(); @@ -144,6 +146,8 @@ void DlgSettingsNavigation::loadSettings() ui->spinBoxZoomStep->onRestore(); ui->spinBoxAnimationDuration->onRestore(); ui->checkBoxSpinningAnimations->onRestore(); + ui->checkBoxEnableLongPressClarifySelection->onRestore(); + ui->spinBoxLongPressTimeout->onRestore(); ui->qspinNewDocScale->onRestore(); ui->prefStepByTurn->onRestore(); ui->naviCubeCorner->onRestore(); diff --git a/src/Gui/PreferencePages/DlgSettingsNavigation.ui b/src/Gui/PreferencePages/DlgSettingsNavigation.ui index 1a62a40116..d2ba5d1510 100644 --- a/src/Gui/PreferencePages/DlgSettingsNavigation.ui +++ b/src/Gui/PreferencePages/DlgSettingsNavigation.ui @@ -850,6 +850,99 @@ Mouse tilting is not disabled by this setting. + + + + Clarify Selection + + + + + + Enable Clarify Selection on long press of left mouse button. +When enabled, holding left mouse button shows a menu to select overlapping objects. +Some navigation styles (OpenInventor, Gesture, OpenSCAD) require Ctrl+LMB instead of just LMB. + + + Enable long press clarify selection + + + true + + + EnableLongPressClarifySelection + + + View + + + + + + + Time in seconds to hold left mouse button before showing clarify selection menu + + + Long press timeout + + + Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter + + + + + + + + 80 + 16777215 + + + + Duration in seconds to hold left mouse button before clarify selection is triggered + + + s + + + 1 + + + 0.300000000000000 + + + 3.000000000000000 + + + 0.100000000000000 + + + 1.000000000000000 + + + LongPressTimeout + + + View + + + + + + + Qt::Horizontal + + + + 40 + 20 + + + + + + + @@ -908,5 +1001,38 @@ Mouse tilting is not disabled by this setting. - + + + checkBoxEnableLongPressClarifySelection + toggled(bool) + spinBoxLongPressTimeout + setEnabled(bool) + + + 274 + 867 + + + 274 + 897 + + + + + checkBoxEnableLongPressClarifySelection + toggled(bool) + labelLongPressTimeout + setEnabled(bool) + + + 274 + 867 + + + 100 + 897 + + + + diff --git a/src/Gui/View3DInventorViewer.cpp b/src/Gui/View3DInventorViewer.cpp index 56568ef78e..1043414914 100644 --- a/src/Gui/View3DInventorViewer.cpp +++ b/src/Gui/View3DInventorViewer.cpp @@ -115,6 +115,8 @@ #include "Multisample.h" #include "NaviCube.h" #include "Navigation/NavigationStyle.h" +#include "Navigation/GestureNavigationStyle.h" +#include "Navigation/SiemensNXNavigationStyle.h" #include "Selection.h" #include "SoDevicePixelRatioElement.h" #include "SoFCDB.h" @@ -171,6 +173,30 @@ private: Gui::Command::runCommand(Gui::Command::Gui, "Gui.runCommand('Std_ClarifySelection')"); } + bool shouldEnableLongPress(View3DInventorViewer* viewer, const QPoint& pos, bool ctrlPressed) const { + bool enabled = App::GetApplication() + .GetParameterGroupByPath("User parameter:BaseApp/Preferences/View") + ->GetBool("EnableLongPressClarifySelection", true); + if (!enabled) { + return false; + } + + // check edit mode and view provider editing (for example transform manipulator) + if (viewer->isEditing() || viewer->isEditingViewProvider()) { + return false; + } + + if (auto* navStyle = viewer->navigationStyle()) { + // reject if navigation style requires ctrl and it's not pressed or we're under a dragger + if ((navStyle->clarifySelectionMode() == NavigationStyle::ClarifySelectionMode::Ctrl && !ctrlPressed) || + navStyle->isDraggerUnderCursor(SbVec2s(pos.x(), pos.y()))) { + return false; + } + } + + return true; + } + QTimer* longPressTimer; QPoint pressPosition; View3DInventorViewer* currentViewer = nullptr; @@ -223,12 +249,15 @@ public: if (mouseEvent->button() == Qt::LeftButton) { currentViewer = static_cast(obj); pressPosition = mouseEvent->pos(); + bool ctrlPressed = (mouseEvent->modifiers() & Qt::ControlModifier) != 0; - int longPressTimeout = App::GetApplication() - .GetParameterGroupByPath("User parameter:BaseApp/Preferences/View") - ->GetInt("LongPressTimeout", 1000); - longPressTimer->setInterval(longPressTimeout); - longPressTimer->start(); + if (shouldEnableLongPress(currentViewer, pressPosition, ctrlPressed)) { + double longPressTimeout = App::GetApplication() + .GetParameterGroupByPath("User parameter:BaseApp/Preferences/View") + ->GetFloat("LongPressTimeout", 1.0); + longPressTimer->setInterval(static_cast(longPressTimeout * 1000)); + longPressTimer->start(); + } } } else if (event->type() == QEvent::MouseButtonRelease) {