]> SALOME platform Git repositories - modules/shaper.git/commitdiff
Salome HOME
Merge branch 'Dev_1.1.0' of newgeom:newgeom.git into Dev_1.1.0
authorsbh <sergey.belash@opencascade.com>
Thu, 9 Apr 2015 15:08:20 +0000 (18:08 +0300)
committersbh <sergey.belash@opencascade.com>
Thu, 9 Apr 2015 15:08:20 +0000 (18:08 +0300)
22 files changed:
src/ModuleBase/ModuleBase_Tools.cpp
src/ModuleBase/ModuleBase_Tools.h
src/PartSet/PartSet_SketcherMgr.cpp
src/PartSet/PartSet_SketcherMgr.h
src/PartSet/PartSet_WidgetSketchLabel.cpp
src/PartSet/PartSet_WidgetSketchLabel.h
src/SketchPlugin/SketchPlugin_Arc.cpp
src/SketchPlugin/plugin-Sketch.xml
src/SketchSolver/SketchSolver_Constraint.cpp
src/SketchSolver/SketchSolver_Constraint.h
src/SketchSolver/SketchSolver_ConstraintLength.cpp
src/SketchSolver/SketchSolver_ConstraintLength.h
src/SketchSolver/SketchSolver_ConstraintManager.cpp
src/SketchSolver/SketchSolver_ConstraintMirror.cpp
src/SketchSolver/SketchSolver_ConstraintRigid.cpp
src/SketchSolver/SketchSolver_Group.cpp
src/SketchSolver/SketchSolver_Group.h
src/SketchSolver/SketchSolver_Storage.cpp
src/SketchSolver/SketchSolver_Storage.h
src/SketcherPrs/SketcherPrs_PositionMgr.cpp
src/XGUI/XGUI_Displayer.cpp
src/XGUI/XGUI_Workshop.cpp

index 06e8fb08dc8befc26ccd7f1dda8c3304313598eb..a2c393658c6b0a5fd972593781b0df6a60dc9325 100644 (file)
@@ -5,6 +5,10 @@
 // Author:      Vitaly Smetannikov
 
 #include "ModuleBase_Tools.h"
+
+#include <ModelAPI_Result.h>
+#include <ModelAPI_Data.h>
+
 #include <QWidget>
 #include <QLayout>
 #include <QPainter>
@@ -105,6 +109,23 @@ void setSpinValue(QDoubleSpinBox* theSpin, double theValue)
   theSpin->blockSignals(isBlocked);
 }
 
+QString objectInfo(const ObjectPtr& theObj)
+{
+  ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(theObj);
+  FeaturePtr aFeature;// = std::dynamic_pointer_cast<ModelAPI_Feature>(theObj);
+  QString aFeatureStr = "feature";
+  if(aRes.get()) {
+    aFeatureStr.append("(Result)");
+    //aFeature = ModelAPI_Feature::feature(aRes);
+  }
+  if (aFeature.get()) {
+    aFeatureStr.append(QString(": %1").arg(aFeature->getKind().c_str()).toStdString().c_str());
+    if (aFeature->data().get() && aFeature->data()->isValid())
+      aFeatureStr.append(QString("(name=%1)").arg(aFeature->data()->name().c_str()).toStdString().c_str());
+  }
+  return aFeatureStr;
+}
+
 }
 
 
index 1f55bec750a28fb7a9e5b04df2273543c3ff44e6..c54c5441e3ea6e262fd9013dc48d98f576bfa028 100644 (file)
@@ -9,6 +9,8 @@
 
 #include "ModuleBase.h"
 
+#include <ModelAPI_Feature.h>
+
 #include <QPixmap>
 
 class QWidget;
@@ -57,6 +59,11 @@ MODULEBASE_EXPORT QPixmap lighter(const QString& theIcon, const int theLighterVa
 /// \param theValue a new value
 MODULEBASE_EXPORT void setSpinValue(QDoubleSpinBox* theSpin, double theValue);
 
+/// Converts the object to the feature or a result and generate information string
+/// \param theObj an object
+/// \return a string
+MODULEBASE_EXPORT QString objectInfo(const ObjectPtr& theObj);
+
 }
 
 #endif
index 40578fa8ad51a528d185926d14aefe0734784c9a..99c9b3e3813630ca33da0a9a61223e6c9ba63593 100644 (file)
 #include <SketchPlugin_ConstraintFillet.h>
 #include <SketchPlugin_ConstraintMirror.h>
 
+#include <SketcherPrs_Tools.h>
+
 #include <SelectMgr_IndexedMapOfOwner.hxx>
 #include <StdSelect_BRepOwner.hxx>
 
 //#include <AIS_DimensionSelectionMode.hxx>
-//#include <AIS_Shape.hxx>
+#include <AIS_Shape.hxx>
 
 #include <ModelAPI_Events.h>
 #include <ModelAPI_Session.h>
@@ -552,18 +554,9 @@ void PartSet_SketcherMgr::get2dPoint(ModuleBase_IViewWindow* theWnd, QMouseEvent
 
 void PartSet_SketcherMgr::launchEditing()
 {
-  // there should be activate the vertex selection mode because the edit can happens by the selected
-  // point
-  QIntList aModes;
-  aModes << TopAbs_VERTEX << TopAbs_EDGE;
-  // TODO: #391 - to be uncommented
-  /*aModes.append(AIS_DSM_Text);
-  aModes.append(AIS_DSM_Line);
-  aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_VERTEX));
-  aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_EDGE));*/
-
-  XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(myModule->workshop());
-  aConnector->activateSubShapesSelection(aModes);
+  // there should be activate the sketch selection mode because the edit can happens
+  // by any sketch entity or consttant selected
+  activateObjectsInSketchMode(true);
 
   if (!myCurrentSelection.empty()) {
     FeaturePtr aFeature = myCurrentSelection.begin().key();
@@ -700,6 +693,9 @@ void PartSet_SketcherMgr::stopSketch(ModuleBase_Operation* theOperation)
 {
   myIsMouseOverWindow = false;
   myIsConstraintsShown = true;
+  // the objects activated in the sketch should be deactivated in order to do not have the specific
+  // sketch selection mode activated on objects in neutral point of the application(no started operation)
+  activateObjectsInSketchMode(false);
 
   XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(myModule->workshop());
   XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
@@ -757,6 +753,10 @@ void PartSet_SketcherMgr::stopNestedSketch(ModuleBase_Operation* theOp)
   connectToPropertyPanel(false);
   myIsPropertyPanelValueChanged = false;
   myIsMouseOverViewProcessed = true;
+
+  // the sketch objects selection should be activated in order to select any sketch
+  // object
+  activateObjectsInSketchMode(true);
 }
 
 void PartSet_SketcherMgr::commitNestedSketch(ModuleBase_Operation* theOperation)
@@ -826,6 +826,11 @@ bool PartSet_SketcherMgr::canDisplayObject(const ObjectPtr& theObject) const
 void PartSet_SketcherMgr::onPlaneSelected(const std::shared_ptr<GeomAPI_Pln>& thePln)
 {
   myPlaneFilter->setPlane(thePln->impl<gp_Pln>());
+
+  // after the plane is selected in the sketch, the sketch selection should be activated
+  // it can not be performed in the sketch label widget because, we don't need to switch off
+  // the selection by any label deactivation, but need to switch it off by stop the sketch
+  activateObjectsInSketchMode(true);
 }
 
 void PartSet_SketcherMgr::getCurrentSelection(const FeaturePtr& theFeature,
@@ -1015,6 +1020,23 @@ void PartSet_SketcherMgr::visualizeFeature(ModuleBase_Operation* theOperation,
   aDisplayer->updateViewer();
 }
 
+void PartSet_SketcherMgr::activateObjectsInSketchMode(const bool isActive)
+{
+  ModuleBase_IWorkshop* aWorkshop = myModule->workshop();
+  XGUI_ModuleConnector* aConnector = dynamic_cast<XGUI_ModuleConnector*>(aWorkshop);
+  XGUI_Displayer* aDisplayer = aConnector->workshop()->displayer();
+
+  QIntList aModes;
+  if (isActive) {
+    aModes.append(SketcherPrs_Tools::Sel_Dimension_Text);
+    aModes.append(SketcherPrs_Tools::Sel_Dimension_Line);
+    aModes.append(SketcherPrs_Tools::Sel_Constraint);
+    aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_VERTEX));
+    aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_EDGE));
+  }
+  aDisplayer->activateObjects(aModes);
+}
+
 void PartSet_SketcherMgr::storeSelection(const bool theHighlightedOnly)
 {
   ModuleBase_IWorkshop* aWorkshop = myModule->workshop();
index 01789c136b6e4a46054a215006aadffb5aa58e14..977c666d39d9d9b911985ea84b8d0e514797c767 100644 (file)
@@ -246,6 +246,11 @@ private:
   /// \param isToDisplay a flag about the display or erase the feature
   void visualizeFeature(ModuleBase_Operation* theOperation, const bool isToDisplay);
 
+  /// Activates all visualized objects in the following selection modes: Dimension_Text/Line/Constraint,
+  /// Shape Edge and Vertex. If the active flag is empty, it deactivates all modes
+  /// \param isActive the flag whether the modes should be activated or deactivated
+  void activateObjectsInSketchMode(const bool isActive);
+
 private:
   PartSet_Module* myModule;
 
index af8e9d56af5061f563fe2ca5a854b61e09b39307..5570182990f55b7a8ff0fab76f7f4f73bf630ebb 100644 (file)
@@ -40,7 +40,7 @@
 #include <Config_PropManager.h>
 
 #include <QLabel>
-#include <QTimer>
+//#include <QTimer>
 #include <QApplication>
 #include <QVBoxLayout>
 #include <QCheckBox>
@@ -61,9 +61,9 @@ PartSet_WidgetSketchLabel::PartSet_WidgetSketchLabel(QWidget* theParent,
   myLabel->setToolTip("");
   myLabel->setIndent(5);
 
-  mySelectionTimer = new QTimer(this);
-  connect(mySelectionTimer, SIGNAL(timeout()), SLOT(setSketchingMode()));
-  mySelectionTimer->setSingleShot(true);
+  //mySelectionTimer = new QTimer(this);
+  //connect(mySelectionTimer, SIGNAL(timeout()), SLOT(setSketchingMode()));
+  //mySelectionTimer->setSingleShot(true);
 
   QVBoxLayout* aLayout = new QVBoxLayout(this);
   ModuleBase_Tools::zeroMargins(aLayout);
@@ -130,7 +130,7 @@ void PartSet_WidgetSketchLabel::onPlaneSelected()
         //XGUI_Displayer* aDisp = myWorkshop->displayer();
         //aDisp->closeLocalContexts();
         emit planeSelected(plane());
-        setSketchingMode();
+        //setSketchingMode();
 
         // Update sketcher actions
         XGUI_ActionsMgr* anActMgr = myWorkshop->actionsMgr();
@@ -216,7 +216,7 @@ void PartSet_WidgetSketchLabel::activateCustom()
     // In order to avoid Opening/Closing of context too often
     // it can be useful for a delay on the property panel filling
     // it is possible that it is not necessary anymore, but it requires a check
-    mySelectionTimer->start(20);
+    //mySelectionTimer->start(20);
   } else {
     // We have to select a plane before any operation
     showPreviewPlanes();
@@ -241,7 +241,7 @@ void PartSet_WidgetSketchLabel::activateCustom()
 void PartSet_WidgetSketchLabel::deactivate()
 {
   // Do not set selection mode if the widget was activated for a small moment 
-  mySelectionTimer->stop();
+  //mySelectionTimer->stop();
   //XGUI_Displayer* aDisp = myWorkshop->displayer();
   //aDisp->closeLocalContexts();
   erasePreviewPlanes();
@@ -353,7 +353,7 @@ std::shared_ptr<GeomAPI_Dir> PartSet_WidgetSketchLabel::setSketchPlane(const Top
 }
 
 
-void PartSet_WidgetSketchLabel::setSketchingMode()
+/*void PartSet_WidgetSketchLabel::setSketchingMode()
 {
   XGUI_Displayer* aDisp = myWorkshop->displayer();
   // Clear standard selection modes if they are defined
@@ -361,6 +361,7 @@ void PartSet_WidgetSketchLabel::setSketchingMode()
   //aDisp->openLocalContext();
 
   // Get default selection modes
+  
   QIntList aModes;
   aModes.append(SketcherPrs_Tools::Sel_Dimension_Text);
   aModes.append(SketcherPrs_Tools::Sel_Dimension_Line);
@@ -369,7 +370,7 @@ void PartSet_WidgetSketchLabel::setSketchingMode()
   aModes.append(AIS_Shape::SelectionMode((TopAbs_ShapeEnum) TopAbs_EDGE));
 
   aDisp->activateObjects(aModes);
-}
+}*/
 
 void PartSet_WidgetSketchLabel::showConstraints(bool theOn)
 {
index 0b26103a47bed65f9be334dd6d73b852dfe33b71..0207199bbdfa78399e60c0d038d1a779cb329793 100644 (file)
@@ -19,7 +19,7 @@
 #include <TopoDS_Shape.hxx>
 
 class QLabel;
-class QTimer;
+//class QTimer;
 class XGUI_OperationMgr;
 class XGUI_Workshop;
 class QCheckBox;
@@ -114,7 +114,7 @@ protected:
   void onPlaneSelected();
 
   /// Set sketch specific mode of selection
-  void setSketchingMode();
+  //void setSketchingMode();
 
  private:
    /// Create preview of planes for sketch plane selection
@@ -147,7 +147,7 @@ protected:
   AISObjectPtr myXYPlane;
   bool myPreviewDisplayed;
 
-  QTimer* mySelectionTimer;
+  //QTimer* mySelectionTimer;
 
   QCheckBox* myShowConstraints;
 };
index 026266a30d164a160208039d0a0c8c3f809d50fe..5599f3b0b138ce470394780fe97d80fe7faa40de 100644 (file)
@@ -13,6 +13,7 @@
 #include <ModelAPI_Session.h>
 
 #include <GeomAPI_Circ2d.h>
+#include <GeomAPI_Circ.h>
 #include <GeomAPI_Pnt2d.h>
 #include <GeomDataAPI_Point2D.h>
 #include <GeomDataAPI_Dir.h>
@@ -209,14 +210,28 @@ void SketchPlugin_Arc::attributeChanged(const std::string& theID)
 {
   std::shared_ptr<GeomDataAPI_Point2D> aCenterAttr = std::dynamic_pointer_cast<
       GeomDataAPI_Point2D>(data()->attribute(CENTER_ID()));
-  if (!aCenterAttr->isInitialized())
-    return;
   std::shared_ptr<GeomDataAPI_Point2D> aStartAttr = std::dynamic_pointer_cast<
       GeomDataAPI_Point2D>(data()->attribute(START_ID()));
-  if (!aStartAttr->isInitialized())
-    return;
   std::shared_ptr<GeomDataAPI_Point2D> anEndAttr = std::dynamic_pointer_cast<
       GeomDataAPI_Point2D>(data()->attribute(END_ID()));
+  if (theID == EXTERNAL_ID()) {
+    std::shared_ptr<GeomAPI_Shape> aSelection = data()->selection(EXTERNAL_ID())->value();
+    // update arguments due to the selection value
+    if (aSelection && !aSelection->isNull() && aSelection->isEdge()) {
+      std::shared_ptr<GeomAPI_Edge> anEdge( new GeomAPI_Edge(aSelection));
+      std::shared_ptr<GeomAPI_Circ> aCirc = anEdge->circle();
+      if (aCirc.get()) {
+        aStartAttr->setValue(sketch()->to2D(anEdge->firstPoint()));
+        anEndAttr->setValue(sketch()->to2D(anEdge->lastPoint()));
+        aCenterAttr->setValue(sketch()->to2D(aCirc->center()));
+      }
+    }
+    return;
+  }
+  if (!aCenterAttr->isInitialized())
+    return;
+  if (!aStartAttr->isInitialized())
+    return;
   if (!anEndAttr->isInitialized())
     return;
 
index 6657008fd201a8a6294a6af54fc5fed5660803e6..382bd3d612f7e8d9610be38cd0a515e4f26e2aaa 100644 (file)
@@ -57,7 +57,7 @@
         </sketch_shape_selector>/>
         <sketch_shape_selector 
           id="ConstraintEntityB" 
-          label="Last object" 
+          label="Second object" 
           tooltip="Select point, line end point, line, center of circle or arc." 
           shape_types="edge vertex">
           <validator id="PartSet_DifferentObjects"/>
             <validator id="SketchPlugin_ExternalValidator" parameters="ConstraintEntityB"/>
         </sketch_constraint_shape_selector>
         
-        <sketch_constraint_shape_selector id="ConstraintEntityB" label="Last line" tooltip="Select a line" 
+        <sketch_constraint_shape_selector id="ConstraintEntityB" label="Second line" tooltip="Select a line" 
             shape_types="edge">
             <validator id="GeomValidators_Edge" parameters="line"/>
             <validator id="PartSet_DifferentObjects"/>
         </sketch_constraint_shape_selector>
         
         <sketch_constraint_shape_selector id="ConstraintEntityB" 
-            label="Last line" tooltip="Select an line" 
+            label="Second line" tooltip="Select an line" 
             shape_types="edge">
             <validator id="PartSet_DifferentObjects"/>
           <validator id="SketchPlugin_ExternalValidator" parameters="ConstraintEntityA"/>
         </sketch_constraint_shape_selector>
         
         <sketch_constraint_shape_selector id="ConstraintEntityB"
-            label="Last object" tooltip="Select line, circle or arc" shape_types="edge">
+            label="Second object" tooltip="Select line, circle or arc" shape_types="edge">
           <validator id="SketchPlugin_EqualAttr" parameters="ConstraintEntityA"/>
           <validator id="PartSet_DifferentObjects"/>
         </sketch_constraint_shape_selector>
         </sketch_constraint_shape_selector>
         
         <sketch_constraint_shape_selector id="ConstraintEntityB"
-            label="Last object" tooltip="Select line or arc" shape_types="edge">
+            label="Second object" tooltip="Select line or arc" shape_types="edge">
         <validator id="SketchPlugin_TangentAttr" parameters="ConstraintEntityA"/>
         <validator id="PartSet_DifferentObjects"/>
         </sketch_constraint_shape_selector>
         </sketch_constraint_shape_selector>
 
         <sketch_constraint_shape_selector id="ConstraintEntityB"
-            label="Last object" tooltip="Select line or arc" shape_types="edge">
+            label="Second object" tooltip="Select line or arc" shape_types="edge">
         </sketch_constraint_shape_selector>
 
         <doublevalue_editor label="Value" tooltip="Fillet radius" id="ConstraintValue" min="0">
index b86ce1a28073d4caa0cecf85827bc7e4b4b517b8..36bde98f820d2a17ad264f40cf414f4b4a3a3cda 100644 (file)
@@ -618,18 +618,24 @@ void SketchSolver_Constraint::calculateMiddlePoint(
 
     double xStart = anArcPoint[1][0] / aRad, xEnd = anArcPoint[2][0] / aRad;
     double yStart = anArcPoint[1][1] / aRad, yEnd = anArcPoint[2][1] / aRad;
+    double aTanStart = abs(xStart) < tolerance ? yStart : yStart / xStart;
+    double aTanEnd   = abs(xEnd) < tolerance   ? yEnd   : yEnd / xEnd;
+    double aCotStart = abs(yStart) < tolerance ? xStart : xStart / yStart;
+    double aCotEnd   = abs(yEnd) < tolerance   ? xEnd   : xEnd / yEnd;
     if (anArcPoint[1][0] * anArcPoint[2][0] < 0.0) {
       if (anArcPoint[1][0] > 0.0)
         yEnd = 2.0 - yEnd;
       else
         yStart = -2.0 - yStart;
     } else {
-      if (yStart > yEnd) {
-        yStart = 2.0 - yStart;
-        yEnd = -2.0 - yEnd;
-      } else {
-        yStart = -2.0 - yStart;
-        yEnd = 2.0 - yEnd;
+      if (aTanStart > aTanEnd) {
+        if (yStart > yEnd) {
+          yStart = 2.0 - yStart;
+          yEnd = -2.0 - yEnd;
+        } else {
+          yStart = -2.0 - yStart;
+          yEnd = 2.0 - yEnd;
+        }
       }
     }
     if (anArcPoint[1][1] * anArcPoint[2][1] < 0.0) {
@@ -638,12 +644,14 @@ void SketchSolver_Constraint::calculateMiddlePoint(
       else
         xStart = -2.0 - xStart;
     } else {
-      if (xStart > xEnd) {
-        xStart = 2.0 - xStart;
-        xEnd = -2.0 - xEnd;
-      } else {
-        xStart = -2.0 - xStart;
-        xEnd = 2.0 - xEnd;
+      if (aCotStart < aCotEnd) {
+        if (xStart > xEnd) {
+          xStart = 2.0 - xStart;
+          xEnd = -2.0 - xEnd;
+        } else {
+          xStart = -2.0 - xStart;
+          xEnd = 2.0 - xEnd;
+        }
       }
     }
     x = (1.0 - theCoeff) * xStart + theCoeff * xEnd;
@@ -666,3 +674,10 @@ void SketchSolver_Constraint::calculateMiddlePoint(
   }
 }
 
+void SketchSolver_Constraint::makeTemporary() const
+{
+  std::vector<Slvs_hConstraint>::const_iterator anIt = mySlvsConstraints.begin();
+  for (; anIt != mySlvsConstraints.end(); anIt++)
+    myStorage->addTemporaryConstraint(*anIt);
+}
+
index 6cfe355f8aa159338b4e2d1b8a3c68a6beeafe92..134263412da5574997e456bb728db825191de3ef 100644 (file)
@@ -51,6 +51,9 @@ public:
   /// \brief Returns the type of constraint
   virtual int getType() const = 0;
 
+  /// \brief The constraint is made temoparary
+  void makeTemporary() const;
+
   /// \brief Checks the constraint is used by current object
   virtual bool hasConstraint(ConstraintPtr theConstraint) const
   { return theConstraint == myBaseConstraint; }
index 3d1d1bf22e6426e664c8a6d1b9256c0ebccbefeb..bf519342b2a2de8f74f28683e25e6265a73ecf89 100644 (file)
@@ -34,3 +34,9 @@ void SketchSolver_ConstraintLength::process()
   adjustConstraint();
 }
 
+void SketchSolver_ConstraintLength::adjustConstraint()
+{
+  // No need to store the line, which length is constrained
+  myFeatureMap.clear();
+}
+
index 5d0583752c2dd4634de75fd37299732a3e992e66..7f91d7e3a33c74ccd37939b715a4dc8877788311 100644 (file)
@@ -27,6 +27,10 @@ public:
 protected:
   /// \brief Converts SketchPlugin constraint to a list of SolveSpace constraints
   virtual void process();
+
+  /// \brief This method is used in derived objects to check consistence of constraint.
+  ///        E.g. the distance between line and point may be signed.
+  virtual void adjustConstraint();
 };
 
 #endif
index d6094199f576d0f12f44be87a050c514606b2051..79616858f5a292c628dc9dbe717d8fad6785bc96 100644 (file)
@@ -114,9 +114,7 @@ void SketchSolver_ConstraintManager::processEvent(
           std::dynamic_pointer_cast<SketchPlugin_Feature>(*aFeatIter);
         if (!aFeature)
           continue;
-        if (aFeature->getKind() == SketchPlugin_ConstraintFillet::ID() ||
-            aFeature->getKind() == SketchPlugin_ConstraintMirror::ID() ||
-            aFeature->getKind() == SketchPlugin_ConstraintTangent::ID()) {
+        if (SketchSolver_Group::isComplexConstraint(aFeature)) {
           aComplexConstraints.insert(aFeature);
           continue;
         }
index f3ded1d30f1046113d0ef92ac879f94f63c959df..fde4b811ecd73e1b72683d306a5c836f8f2222bf 100644 (file)
@@ -159,6 +159,20 @@ void SketchSolver_ConstraintMirror::process()
             0.0, aBothMiddlePoints[i], SLVS_E_UNKNOWN, aBothArcs[i].h, SLVS_E_UNKNOWN);
         aPonCircConstr.h = myStorage->addConstraint(aPonCircConstr);
         mySlvsConstraints.push_back(aPonCircConstr.h);
+        if (i == 0) {
+          // additional constraint for the point to be in the middle of a base arc
+          Slvs_Entity aLine1 = Slvs_MakeLineSegment(SLVS_E_UNKNOWN, myGroup->getId(),
+              myGroup->getWorkplaneId(), aBothArcs[i].point[1], aBothMiddlePoints[i]);
+          aLine1.h = myStorage->addEntity(aLine1);
+          Slvs_Entity aLine2 = Slvs_MakeLineSegment(SLVS_E_UNKNOWN, myGroup->getId(),
+              myGroup->getWorkplaneId(), aBothArcs[i].point[2], aBothMiddlePoints[i]);
+          aLine2.h = myStorage->addEntity(aLine2);
+          Slvs_Constraint aMiddleConstr = Slvs_MakeConstraint(SLVS_E_UNKNOWN, myGroup->getId(),
+              SLVS_C_EQUAL_LENGTH_LINES, myGroup->getWorkplaneId(),
+              0.0, SLVS_E_UNKNOWN, SLVS_E_UNKNOWN, aLine1.h, aLine2.h);
+          aMiddleConstr.h = myStorage->addConstraint(aMiddleConstr);
+          mySlvsConstraints.push_back(aMiddleConstr.h);
+        }
       }
 
       aBaseArcPoints[2] = aBothMiddlePoints[0];
@@ -319,6 +333,7 @@ void SketchSolver_ConstraintMirror::adjustConstraint()
     if (aPonCircA.h == SLVS_E_UNKNOWN || aPonCircB.h == SLVS_E_UNKNOWN)
       continue;
 
+    bool aNeedToResolve = myStorage->isNeedToResolve();
     // Calculate middle point for base arc and mirrored point on mirror arc
     Slvs_Entity aBaseArc = myStorage->getEntity(aPonCircA.entityA);
     Slvs_Entity aBasePoint = myStorage->getEntity(aPonCircA.ptA);
@@ -327,7 +342,14 @@ void SketchSolver_ConstraintMirror::adjustConstraint()
     calculateMiddlePoint(aBaseArc, 0.5, aParamX.val, aParamY.val);
     myStorage->updateParameter(aParamX);
     myStorage->updateParameter(aParamY);
+    Slvs_Entity aMirrorArc = myStorage->getEntity(aPonCircB.entityA);
     Slvs_Entity aMirrorPoint = myStorage->getEntity(aPonCircB.ptA);
-    makeMirrorEntity(aBasePoint, aMirrorPoint, aStartEnd);
+    aParamX = myStorage->getParameter(aMirrorPoint.param[0]);
+    aParamY = myStorage->getParameter(aMirrorPoint.param[1]);
+    calculateMiddlePoint(aMirrorArc, 0.5, aParamX.val, aParamY.val);
+    myStorage->updateParameter(aParamX);
+    myStorage->updateParameter(aParamY);
+    // To avoid looped recalculations of sketch
+    myStorage->setNeedToResolve(aNeedToResolve);
   }
 }
index 6c1875ccb062394d2df1312fad8271c1aeb43626..956f4b727549d5a33923878541ecd3d42997d04b 100644 (file)
@@ -52,7 +52,8 @@ void SketchSolver_ConstraintRigid::process()
     if (*anEntIter == SLVS_E_UNKNOWN)
       continue;
     Slvs_hConstraint aConstrID = myStorage->isPointFixed(*anEntIter);
-    bool isForceUpdate = (aConstrID != SLVS_E_UNKNOWN && !myBaseConstraint);
+    bool isForceUpdate = (aConstrID != SLVS_E_UNKNOWN && !myBaseConstraint &&
+                          myStorage->isTemporary(aConstrID));
     if (isEmpty && !isForceUpdate) { // create new constraint
       if (aConstrID != SLVS_E_UNKNOWN)
         continue; // the coincident point is already fixed
@@ -61,7 +62,7 @@ void SketchSolver_ConstraintRigid::process()
       aConstraint.h = myStorage->addConstraint(aConstraint);
       mySlvsConstraints.push_back(aConstraint.h);
       if (!myBaseConstraint)
-        myStorage->addTemporaryConstraint(aConstraint.h);
+        myStorage->addConstraintWhereDragged(aConstraint.h);
     } else { // update already existent constraint
       if (aConstrID == SLVS_E_UNKNOWN || myBaseConstraint)
         aConstrID = *aConstrIter;
@@ -69,7 +70,7 @@ void SketchSolver_ConstraintRigid::process()
       aConstraint.ptA = *anEntIter;
       myStorage->addConstraint(aConstraint);
       if (!myBaseConstraint)
-        myStorage->addTemporaryConstraint(aConstraint.h);
+        myStorage->addConstraintWhereDragged(aConstraint.h);
       if (!isEmpty) {
         aConstrIter++;
         isEmpty = aConstrIter == mySlvsConstraints.end();
@@ -86,7 +87,7 @@ void SketchSolver_ConstraintRigid::process()
     aConstraint.h = myStorage->addConstraint(aConstraint);
     mySlvsConstraints.push_back(aConstraint.h);
     if (!myBaseConstraint)
-      myStorage->addTemporaryConstraint(aConstraint.h);
+      myStorage->addConstraintWhereDragged(aConstraint.h);
   }
 }
 
@@ -226,14 +227,14 @@ void SketchSolver_ConstraintRigid::fixArc(const Slvs_Entity& theArc)
     aConstraint.h = myStorage->addConstraint(aConstraint);
     mySlvsConstraints.push_back(aConstraint.h);
     if (!myBaseConstraint)
-      myStorage->addTemporaryConstraint(aConstraint.h);
+      myStorage->addConstraintWhereDragged(aConstraint.h);
   }
 
   // Fix radius of the arc
   bool isExists = false;
   std::list<Slvs_Constraint> aDiamConstraints = myStorage->getConstraintsByType(SLVS_C_DIAMETER);
   std::list<Slvs_Constraint>::iterator anIt = aDiamConstraints.begin();
-  for (; anIt != aDiamConstraints.end() && !isExists; anIt)
+  for (; anIt != aDiamConstraints.end() && !isExists; anIt++)
     if (anIt->entityA == myFeatureMap.begin()->second)
       isExists = true;
   if (!isExists) {
@@ -242,7 +243,7 @@ void SketchSolver_ConstraintRigid::fixArc(const Slvs_Entity& theArc)
     aConstraint.h = myStorage->addConstraint(aConstraint);
     mySlvsConstraints.push_back(aConstraint.h);
     if (!myBaseConstraint)
-      myStorage->addTemporaryConstraint(aConstraint.h);
+      myStorage->addConstraintWhereDragged(aConstraint.h);
   }
 }
 
index b51828ba9d0eb78e560f1d934f11f9801a4642a3..7fdc32a4c5e74b5c2c1ee514339fd2d28f60e298 100644 (file)
@@ -30,6 +30,7 @@
 #include <SketchPlugin_ConstraintCoincidence.h>
 #include <SketchPlugin_ConstraintMirror.h>
 #include <SketchPlugin_ConstraintRigid.h>
+#include <SketchPlugin_ConstraintTangent.h>
 #include <SketchPlugin_Feature.h>
 
 #include <SketchPlugin_Arc.h>
@@ -230,7 +231,7 @@ bool SketchSolver_Group::changeConstraint(
         continue;
       aConstraint->setGroup(this);
       aConstraint->setStorage(myStorage);
-      myTempConstraints.insert(aConstraint);
+      setTemporary(aConstraint);
     }
   }
   // Fix base features for mirror
@@ -272,7 +273,7 @@ void SketchSolver_Group::moveFeature(std::shared_ptr<SketchPlugin_Feature> theFe
     return;
   aConstraint->setGroup(this);
   aConstraint->setStorage(myStorage);
-  myTempConstraints.insert(aConstraint);
+  setTemporary(aConstraint);
 }
 
 // ============================================================================
@@ -294,7 +295,7 @@ void SketchSolver_Group::fixFeaturesList(AttributeRefListPtr theList)
       continue;
     aConstraint->setGroup(this);
     aConstraint->setStorage(myStorage);
-    myTempConstraints.insert(aConstraint);
+    setTemporary(aConstraint);
   }
 }
 
@@ -413,9 +414,18 @@ void SketchSolver_Group::mergeGroups(const SketchSolver_Group& theGroup)
   if (!myFeatureStorage)
     myFeatureStorage = FeatureStoragePtr(new SketchSolver_FeatureStorage);
 
+  std::vector<ConstraintPtr> aComplexConstraints;
   ConstraintConstraintMap::const_iterator aConstrIter = theGroup.myConstraints.begin();
+  // append simple constraints
   for (; aConstrIter != theGroup.myConstraints.end(); aConstrIter++)
-    changeConstraint(aConstrIter->first);
+    if (isComplexConstraint(aConstrIter->first))
+      aComplexConstraints.push_back(aConstrIter->first);
+    else
+      changeConstraint(aConstrIter->first);
+  // append complex constraints
+  std::vector<ConstraintPtr>::iterator aComplexIter = aComplexConstraints.begin();
+  for (; aComplexIter != aComplexConstraints.end(); aComplexIter++)
+      changeConstraint(*aComplexIter);
 }
 
 // ============================================================================
@@ -513,6 +523,7 @@ bool SketchSolver_Group::isConsistent()
 void SketchSolver_Group::removeTemporaryConstraints()
 {
   myTempConstraints.clear();
+  myStorage->removeTemporaryConstraints();
   // Clean lists of removed entities in the storage
   std::set<Slvs_hParam> aRemPar;
   std::set<Slvs_hEntity> aRemEnt;
@@ -539,3 +550,27 @@ void SketchSolver_Group::removeConstraint(ConstraintPtr theConstraint)
   if (aCIter != myConstraints.end())
     myConstraints.erase(aCIter);
 }
+
+// ============================================================================
+//  Function: isComplexConstraint
+//  Class:    SketchSolver_Group
+//  Purpose:  verifies the constraint is complex, i.e. it needs another constraints to be created before
+// ============================================================================
+bool SketchSolver_Group::isComplexConstraint(FeaturePtr theConstraint)
+{
+  return theConstraint->getKind() == SketchPlugin_ConstraintFillet::ID() ||
+         theConstraint->getKind() == SketchPlugin_ConstraintMirror::ID() ||
+         theConstraint->getKind() == SketchPlugin_ConstraintTangent::ID();
+}
+
+// ============================================================================
+//  Function: setTemporary
+//  Class:    SketchSolver_Group
+//  Purpose:  append given constraint to th group of temporary constraints
+// ============================================================================
+void SketchSolver_Group::setTemporary(SolverConstraintPtr theConstraint)
+{
+  theConstraint->makeTemporary();
+  myTempConstraints.insert(theConstraint);
+}
+
index 30d675c636c949733e4c03f39736eef051b32631..79f5f9fe04350c2ec7f5f4c7d0bbe9f3ee4342aa 100644 (file)
@@ -70,6 +70,9 @@ class SketchSolver_Group
     return mySketch->data() && mySketch->data()->isValid();
   }
 
+  /// \brief Verifies the constraint is complex, i.e. it needs another constraints to be created before
+  static bool isComplexConstraint(FeaturePtr theConstraint);
+
   /** \brief Adds or updates a constraint in the group
    *  \param[in] theConstraint constraint to be changed
    *  \return \c true if the constraint added or updated successfully
@@ -151,6 +154,9 @@ private:
   /// \brief Apply temporary rigid constraints for the list of features
   void fixFeaturesList(AttributeRefListPtr theList);
 
+  /// \brief Append given constraint to th group of temporary constraints
+  void setTemporary(SolverConstraintPtr theConstraint);
+
 private:
   Slvs_hGroup myID; ///< Index of the group
   Slvs_hEntity myWorkplaneID; ///< Index of workplane, the group is based on
index 1690d7d561d37b5a4040b46b3ba2583fe7522168..40d1d281f55e1c7afd4f5c8808720c2143833162 100644 (file)
@@ -151,19 +151,13 @@ bool SketchSolver_Storage::removeEntity(const Slvs_hEntity& theEntityID)
       if (anEntIter->distance == theEntityID)
         return false;
     }
-    std::set<Slvs_hEntity> anEntAndSubs;
-    anEntAndSubs.insert(theEntityID);
-    for (int i = 0; i < 4; i++)
-      if (myEntities[aPos].point[i] != SLVS_E_UNKNOWN)
-        anEntAndSubs.insert(myEntities[aPos].point[i]);
-
     std::vector<Slvs_Constraint>::const_iterator aConstrIter = myConstraints.begin();
     for (; aConstrIter != myConstraints.end(); aConstrIter++) {
       Slvs_hEntity anEntIDs[6] = {aConstrIter->ptA, aConstrIter->ptB,
           aConstrIter->entityA, aConstrIter->entityB,
           aConstrIter->entityC, aConstrIter->entityD};
       for (int i = 0; i < 6; i++)
-        if (anEntAndSubs.find(anEntIDs[i]) != anEntAndSubs.end())
+        if (anEntIDs[i] == theEntityID)
           return false;
     }
     // The entity is not used, remove it and its parameters
@@ -324,7 +318,7 @@ std::list<Slvs_Constraint> SketchSolver_Storage::getConstraintsByType(int theCon
 }
 
 
-void SketchSolver_Storage::addTemporaryConstraint(const Slvs_hConstraint& theConstraintID)
+void SketchSolver_Storage::addConstraintWhereDragged(const Slvs_hConstraint& theConstraintID)
 {
   if (myFixed != SLVS_E_UNKNOWN)
     return; // the point is already fixed
@@ -333,6 +327,22 @@ void SketchSolver_Storage::addTemporaryConstraint(const Slvs_hConstraint& theCon
     myFixed = theConstraintID;
 }
 
+void SketchSolver_Storage::addTemporaryConstraint(const Slvs_hConstraint& theConstraintID)
+{
+  myTemporaryConstraints.insert(theConstraintID);
+}
+
+void SketchSolver_Storage::removeTemporaryConstraints()
+{
+  myTemporaryConstraints.clear();
+}
+
+bool SketchSolver_Storage::isTemporary(const Slvs_hConstraint& theConstraintID) const
+{
+  return myTemporaryConstraints.find(theConstraintID) != myTemporaryConstraints.end();
+}
+
+
 void SketchSolver_Storage::getRemoved(
     std::set<Slvs_hParam>& theParameters,
     std::set<Slvs_hEntity>& theEntities,
index cf04f47ab4c89112e1f9117b2a9b3d23ed73b5e7..a95d83c72c032a9b7bda639641a02fadf27e8c27 100644 (file)
@@ -87,8 +87,15 @@ public:
   /// \brief Returns list of constraints of specified type
   std::list<Slvs_Constraint> getConstraintsByType(int theConstraintType) const;
 
-  /// \brief Attach temporary constraint to this storage. It need to make precise calculations
+  /// \brief Attach constraint SLVS_C_WHERE_DRAGGED to this storage. It need to make precise calculations
+  void addConstraintWhereDragged(const Slvs_hConstraint& theConstraintID);
+
+  /// \brief Add transient constraint
   void addTemporaryConstraint(const Slvs_hConstraint& theConstraintID);
+  /// \brief Remove all transient constraints
+  void removeTemporaryConstraints();
+  /// \brief Checks the constraint is temporary
+  bool isTemporary(const Slvs_hConstraint& theConstraintID) const;
 
   /// \brief Shows the sketch should be resolved
   bool isNeedToResolve() const
@@ -129,6 +136,7 @@ private:
 
   bool myNeedToResolve; ///< parameters are changed and group needs to be resolved
 
+  std::set<Slvs_hConstraint> myTemporaryConstraints; ///< list of transient constraints
   std::set<Slvs_hParam> myRemovedParameters; ///< list of just removed parameters (cleared when returning to applicant)
   std::set<Slvs_hEntity> myRemovedEntities; ///< list of just removed entities (cleared when returning to applicant)
   std::set<Slvs_hConstraint> myRemovedConstraints; ///< list of just removed constraints (cleared when returning to applicant)
index 1e8a9ee7d6a14629b86a7a1839c0f45745570a18..ec7938b89abfd58c7fdf66432b34ca550ae76a9d 100644 (file)
@@ -107,7 +107,7 @@ gp_Pnt SketcherPrs_PositionMgr::getPosition(ObjectPtr theShape,
     // Odd position
     aP.Translate(-aShift);
     if (aPos > 1) {
-      if (aPos % 4 == 0) 
+      if ((aPos - 1) % 4 == 0) 
         aM = (aPos - 1) / 4;
       else
         aM = -(aPos + 1) / 4;
index 57cb4980184dcd53395de57db0d13164a03e1cc5..368dbb57469080e6f02d66e23a37690cb3388df4 100644 (file)
@@ -753,8 +753,30 @@ void XGUI_Displayer::activate(const Handle(AIS_InteractiveObject)& theIO,
   if (aContext.IsNull() || theIO.IsNull())
     return;
 
-  aContext->Load(theIO, -1, true);
-  aContext->Deactivate(theIO);
+  // deactivate object in all modes, which are not in the list of activation
+  TColStd_ListOfInteger aTColModes;
+  aContext->ActivatedModes(theIO, aTColModes);
+  TColStd_ListIteratorOfListOfInteger itr( aTColModes );
+  QIntList aModesActivatedForIO;
+  for (; itr.More(); itr.Next() ) {
+    Standard_Integer aMode = itr.Value();
+    if (!theModes.contains(aMode)) {
+#ifdef DEBUG_ACTIVATE
+      qDebug(QString("deactivate: %1").arg(aMode).toStdString().c_str());
+#endif
+      aContext->Deactivate(theIO, aMode);
+    }
+    else {
+      aModesActivatedForIO.append(aMode);
+#ifdef DEBUG_ACTIVATE
+      qDebug(QString("  active: %1").arg(aMode).toStdString().c_str());
+#endif
+    }
+  }
+  // loading the interactive object allowing the decomposition
+  if (aTColModes.IsEmpty())
+    aContext->Load(theIO, -1, true);
+
   Handle(AIS_Trihedron) aTrihedron = Handle(AIS_Trihedron)::DownCast(theIO);
   //Deactivate trihedron which can be activated in local selector
   if (aTrihedron.IsNull()) {
@@ -763,10 +785,18 @@ void XGUI_Displayer::activate(const Handle(AIS_InteractiveObject)& theIO,
     if (theModes.size() == 0) {
       //aContext->Load(anAISIO, 0, true);
       aContext->Activate(theIO);
+#ifdef DEBUG_ACTIVATE
+      qDebug("activate in all modes");
+#endif
     } else {
       foreach(int aMode, theModes) {
         //aContext->Load(anAISIO, aMode, true);
-        aContext->Activate(theIO, aMode);
+        if (!aModesActivatedForIO.contains(aMode)) {
+          aContext->Activate(theIO, aMode);
+#ifdef DEBUG_ACTIVATE
+          qDebug(QString("activate: %1").arg(aMode).toStdString().c_str());
+#endif
+        }
       }
     }
   }
index 027248cba7cc970790c1227faadc9975ff867ed2..41c911529b558fc01f1ebe6032f7a178c3fe7b33 100644 (file)
@@ -54,8 +54,9 @@
 #include <ModuleBase_WidgetFactory.h>
 #include <ModuleBase_Tools.h>
 #include <ModuleBase_IViewer.h>
-#include<ModuleBase_FilterFactory.h>
+#include <ModuleBase_FilterFactory.h>
 #include <ModuleBase_PageBase.h>
+#include <ModuleBase_Tools.h>
 
 #include <Config_Common.h>
 #include <Config_FeatureMessage.h>
 //#define DEBUG_FEATURE_CREATED
 //#define DEBUG_FEATURE_REDISPLAY
 
-QString objectInfo(ObjectPtr theObj)
-{
-  ResultPtr aRes = std::dynamic_pointer_cast<ModelAPI_Result>(theObj);
-  FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(theObj);
-  QString aFeatureStr = "feature";
-  if(aRes.get()) {
-    aFeatureStr.append("(Result)");
-    aFeature = ModelAPI_Feature::feature(aRes);
-  }
-  if (aFeature.get()) {
-    aFeatureStr.append(QString(": %1").arg(aFeature->getKind().c_str()).toStdString().c_str());
-    if (aFeature->data().get() && aFeature->data()->isValid())
-      aFeatureStr.append(QString("(name=%1)").arg(aFeature->data()->name().c_str()).toStdString().c_str());
-  }
-  return aFeatureStr;
-}
-
-
 QMap<QString, QString> XGUI_Workshop::myIcons;
 
 
@@ -541,7 +524,7 @@ void XGUI_Workshop::onFeatureRedisplayMsg(const std::shared_ptr<ModelAPI_ObjectU
 #ifdef DEBUG_FEATURE_REDISPLAY
   QStringList anInfo;
   for (aIt = aObjects.begin(); aIt != aObjects.end(); ++aIt) {
-    anInfo.append(objectInfo((*aIt)));
+    anInfo.append(ModuleBase_Tools::objectInfo((*aIt)));
   }
   QString anInfoStr = anInfo.join(", ");
   qDebug(QString("onFeatureRedisplayMsg: %1, %2").arg(aObjects.size()).arg(anInfoStr).toStdString().c_str());
@@ -562,7 +545,7 @@ void XGUI_Workshop::onFeatureRedisplayMsg(const std::shared_ptr<ModelAPI_ObjectU
       // Redisplay the visible object or the object of the current operation
       bool isVisibleObject = myDisplayer->isVisible(aObj);
       #ifdef DEBUG_FEATURE_REDISPLAY
-      //QString anObjInfo = objectInfo((aObj));
+      //QString anObjInfo = ModuleBase_Tools::objectInfo((aObj));
       //qDebug(QString("visible=%1 : display= %2").arg(isVisibleObject).arg(anObjInfo).toStdString().c_str());
       #endif
 
@@ -598,7 +581,7 @@ void XGUI_Workshop::onFeatureCreatedMsg(const std::shared_ptr<ModelAPI_ObjectUpd
 #ifdef DEBUG_FEATURE_CREATED
   QStringList anInfo;
   for (aIt = aObjects.begin(); aIt != aObjects.end(); ++aIt) {
-    anInfo.append(objectInfo((*aIt)));
+    anInfo.append(ModuleBase_Tools::objectInfo((*aIt)));
   }
   QString anInfoStr = anInfo.join(", ");
   qDebug(QString("onFeatureCreatedMsg: %1, %2").arg(aObjects.size()).arg(anInfoStr).toStdString().c_str());
@@ -679,8 +662,10 @@ void XGUI_Workshop::onOperationStopped(ModuleBase_Operation* theOperation)
 
   // Activate objects created by current operation 
   // in order to clean selection modes
-  QIntList aModes;
-  myDisplayer->activateObjects(aModes);
+  // the deactivation should be pefromed in the same place, where the mode is activated,
+  // e.g. activation in the current widget activation, deactivation - in the widget's deactivation
+  //QIntList aModes;
+  //myDisplayer->activateObjects(aModes);
   myModule->operationStopped(theOperation);
 }