Salome HOME
Issue #3232: Delete automatic constraints if they cause conflicts
authorvsv <vsv@opencascade.com>
Tue, 2 Jun 2020 09:06:07 +0000 (12:06 +0300)
committervsv <vsv@opencascade.com>
Tue, 2 Jun 2020 09:06:34 +0000 (12:06 +0300)
src/PartSet/PartSet_Module.cpp
src/PartSet/PartSet_Module.h
src/PartSet/PartSet_OverconstraintListener.cpp
src/PartSet/PartSet_OverconstraintListener.h
src/PartSet/PartSet_SketcherReentrantMgr.cpp
src/PartSet/PartSet_SketcherReentrantMgr.h

index 7ac26dd9c76e9b5d6e9a808614b7482216724235..623083bae3b4e4fb5de76ecdbcac57d30d7a015d 100644 (file)
@@ -1854,3 +1854,28 @@ void PartSet_Module::disableCustomMode(ModuleBase_CustomizeFlag theMode) {
 void PartSet_Module::enableCustomModes() {
   myCustomPrs->enableCustomModes();
 }
+
+//******************************************************
+void PartSet_Module::onConflictingConstraints()
+{
+  const std::set<ObjectPtr>& aConstraints = myOverconstraintListener->conflictingObjects();
+  if (aConstraints.size() == 1) {
+    QObjectPtrList aObjectsList;
+    std::set<ObjectPtr>::const_iterator aIt;
+    for (aIt = aConstraints.cbegin(); aIt != aConstraints.cend(); aIt++) {
+      if (mySketchReentrantMgr->isLastAutoConstraint(*aIt))
+        aObjectsList.append(*aIt);
+    }
+    if (aObjectsList.size() > 0) {
+      XGUI_Workshop* aWorkshop = getWorkshop();
+      QString aDescription = aWorkshop->contextMenuMgr()->action("DELETE_CMD")->text();
+      ModuleBase_Operation* anOpAction = new ModuleBase_Operation(aDescription);
+      XGUI_OperationMgr* anOpMgr = aWorkshop->operationMgr();
+
+      anOpMgr->startOperation(anOpAction);
+      aWorkshop->deleteFeatures(aObjectsList);
+      anOpMgr->commitOperation();
+      ModuleBase_Tools::flushUpdated(sketchMgr()->activeSketch());
+    }
+  }
+}
index 7567f40a2912468cf2f5af1b023a5b2e8a539d87..e9481244e4b4a28190b17460cf3fb3e76ad9589f 100644 (file)
@@ -414,6 +414,8 @@ public slots:
   /// \param theTrsfType type of tranformation
   virtual void onViewTransformed(int theTrsfType = 2);
 
+  void onConflictingConstraints();
+
 protected slots:
   /// Called when previous operation is finished
   virtual void onSelectionChanged();
index 70c19725c8ff56b0221dc9c9e7d358bd78f668c3..a0eff2c34b011e8f26821d22bb0df2b9553379b9 100644 (file)
@@ -35,6 +35,8 @@
 #include "SketchPlugin_SketchEntity.h"
 #include "SketchPlugin_MacroArcReentrantMessage.h"
 #include "SketchPlugin_Sketch.h"
+#include "SketchPlugin_ConstraintHorizontal.h"
+#include "SketchPlugin_ConstraintVertical.h"
 
 #include "Events_Loop.h"
 
@@ -44,6 +46,7 @@
 #include <ModuleBase_Tools.h>
 
 #include <QString>
+#include <QTimer>
 
 //#define DEBUG_FEATURE_OVERCONSTRAINT_LISTENER
 
@@ -253,6 +256,21 @@ bool PartSet_OverconstraintListener::appendConflictingObjects(
   if (isUpdated)
     redisplayObjects(aModifiedObjects);
 
+  if (myConflictingObjects.size() == 1) {
+    // If the conflicting object is an automatic constraint caused the conflict
+    // then it has to be deleted
+    ObjectPtr aObj = *theConflictingObjects.cbegin();
+    FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(aObj);
+    if (aFeature) {
+      std::string aType = aFeature->getKind();
+      if ((aType == SketchPlugin_ConstraintHorizontal::ID()) ||
+        (aType == SketchPlugin_ConstraintVertical::ID())) {
+        PartSet_Module* aModule = dynamic_cast<PartSet_Module*>(myWorkshop->module());
+        QTimer::singleShot(5, aModule, SLOT(onConflictingConstraints()));
+      }
+    }
+  }
+
   return isUpdated;
 }
 
@@ -267,7 +285,6 @@ bool PartSet_OverconstraintListener::repairConflictingObjects(
     ObjectPtr anObject = *anIt;
     if (theConflictingObjects.find(anObject) != theConflictingObjects.end()) { // it is found
       myConflictingObjects.erase(anObject);
-
       aModifiedObjects.insert(anObject);
     }
   }
index a02dee98e5036150619507b34b019c66a607e661..551fb50eab5efa930b9f3f33348f41cc7ecefa25 100644 (file)
@@ -64,6 +64,11 @@ public:
     return (myConflictingObjects.find(theObject) != myConflictingObjects.end());
   }
 
+  const std::set<ObjectPtr>& conflictingObjects() const
+  {
+    return myConflictingObjects;
+  }
+
   bool isFullyConstrained() const { return myIsFullyConstrained; }
 
 protected:
index ff241a14139cf873b2e947cac1fc6cb069da1725..f61252974695fdbe44ac1f94c07064a53458791d 100644 (file)
@@ -75,7 +75,8 @@ PartSet_SketcherReentrantMgr::PartSet_SketcherReentrantMgr(ModuleBase_IWorkshop*
   myIsFlagsBlocked(false),
   myIsInternalEditOperation(false),
   myNoMoreWidgetsAttribute(""),
-  myIsAutoConstraints(true)
+  myIsAutoConstraints(true),
+  myLastAutoConstraint(0)
 {
 }
 
@@ -872,16 +873,24 @@ void PartSet_SketcherReentrantMgr::addConstraints(const FeaturePtr& theFeature)
     double aTolerance = Config_PropManager::real(SKETCH_TAB_NAME, "angular_tolerance");
     CompositeFeaturePtr aSketch = module()->sketchMgr()->activeSketch();
     FeaturePtr aFeature;
-    if (aHorAngle < aTolerance)
+    if (aHorAngle < aTolerance) {
       // Add horizontal constraint
       aFeature = aSketch->addFeature(SketchPlugin_ConstraintHorizontal::ID());
-    else if (aVertAngle < aTolerance)
+    }
+    else if (aVertAngle < aTolerance) {
       // Add vertical constraint
       aFeature = aSketch->addFeature(SketchPlugin_ConstraintVertical::ID());
-
+    }
     if (aFeature.get()) {
       aFeature->refattr(SketchPlugin_Constraint::ENTITY_A())->setObject(
           theFeature->firstResult());
+      myLastAutoConstraint = aFeature.get();
     }
   }
 }
+
+
+bool PartSet_SketcherReentrantMgr::isLastAutoConstraint(const ObjectPtr& theObj) const
+{
+  return theObj.get() == myLastAutoConstraint;
+}
index 046f45dba5911b13358c8d68a9974a3be0899e39..c11f56bcf439d45bfbf7db63e7863f01380898c9 100644 (file)
@@ -134,6 +134,8 @@ public:
   bool isAutoConstraints() const { return myIsAutoConstraints; }
 
 
+  bool isLastAutoConstraint(const ObjectPtr& theObj) const;
+
 public slots:
   /// The slot is called when user checks "Automatic constraints" button
   /// \param isOn a state of the check box
@@ -240,6 +242,7 @@ private:
   std::shared_ptr<GeomAPI_Pnt2d> myClickedSketchPoint; /// cashed clicked point
 
   bool myIsAutoConstraints;
+  void* myLastAutoConstraint; //< Stores address of last automatic constraint. Connot be used as a pointer!!!
 };
 
 #endif