Salome HOME
Issue #604 Creation of an unexpected line in the Sketcher
[modules/shaper.git] / src / SketchSolver / SketchSolver_ConstraintMovement.cpp
1 #include <SketchSolver_ConstraintMovement.h>
2 #include <SketchSolver_Error.h>
3 #include <SketchSolver_Group.h>
4
5 #include <GeomDataAPI_Point2D.h>
6
7 SketchSolver_ConstraintMovement::SketchSolver_ConstraintMovement(FeaturePtr theFeature)
8   : SketchSolver_ConstraintRigid(theFeature)
9 {
10   process();
11 }
12
13 void SketchSolver_ConstraintMovement::process()
14 {
15   cleanErrorMsg();
16   if (!myBaseFeature || !myStorage || myGroup == 0) {
17     /// TODO: Put error message here
18     return;
19   }
20   if (!mySlvsConstraints.empty()) // some data is changed, update constraint
21     update(myBaseConstraint);
22
23   double aValue;
24   std::vector<Slvs_hEntity> anEntities;
25   bool isFullyMoved;
26   getAttributes(aValue, anEntities, isFullyMoved);
27   if (!myErrorMsg.empty() || (myFeatureMap.empty() && myAttributeMap.empty()))
28     return;
29
30   if (isFullyMoved)
31     fixFeature();
32   else {
33     std::vector<Slvs_hEntity>::iterator anEntIt = anEntities.begin();
34     for (; anEntIt != anEntities.end(); ++anEntIt)
35       fixPoint(*anEntIt);
36   }
37 }
38
39
40 void SketchSolver_ConstraintMovement::getAttributes(
41     double& theValue,
42     std::vector<Slvs_hEntity>& theAttributes,
43     bool& theIsFullyMoved)
44 {
45   theValue = 0.0;
46   theIsFullyMoved = true;
47   int aType = SLVS_E_UNKNOWN; // type of created entity
48   Slvs_hEntity anEntityID = SLVS_E_UNKNOWN;
49   anEntityID = myGroup->getFeatureId(myBaseFeature);
50   if (anEntityID == SLVS_E_UNKNOWN) {
51     anEntityID = changeEntity(myBaseFeature, aType);
52     if (anEntityID == SLVS_E_UNKNOWN) {
53       myErrorMsg = SketchSolver_Error::NOT_INITIALIZED();
54       return;
55     }
56
57     // Check the entity is complex
58     Slvs_Entity anEntity = myStorage->getEntity(anEntityID);
59     if (anEntity.point[0] != SLVS_E_UNKNOWN) {
60       for (int i = 0; i < 4 && anEntity.point[i]; i++)
61         theAttributes.push_back(anEntity.point[i]);
62     } else // simple entity
63       theAttributes.push_back(anEntityID);
64   }
65   else {
66      myFeatureMap[myBaseFeature] = anEntityID;
67
68      std::list<AttributePtr> aPoints =
69         myBaseFeature->data()->attributes(GeomDataAPI_Point2D::typeId());
70      std::list<AttributePtr>::iterator anIt = aPoints.begin();
71      for (; anIt != aPoints.end(); ++anIt) {
72        Slvs_hEntity anAttr = myGroup->getAttributeId(*anIt);
73
74        // Check the attribute changes coordinates
75        Slvs_Entity anAttrEnt = myStorage->getEntity(anAttr);
76        double aDeltaX = myStorage->getParameter(anAttrEnt.param[0]).val;
77        double aDeltaY = myStorage->getParameter(anAttrEnt.param[1]).val;
78        std::shared_ptr<GeomDataAPI_Point2D> aPt =
79           std::dynamic_pointer_cast<GeomDataAPI_Point2D>(*anIt);
80        aDeltaX -= aPt->x();
81        aDeltaY -= aPt->y();
82        if (aDeltaX * aDeltaX + aDeltaY * aDeltaY >= tolerance * tolerance)
83          theAttributes.push_back(anAttr);
84        else
85          theIsFullyMoved = false;
86      }
87   }
88 }
89