Salome HOME
9cc6a2bd1e08d10afd06f27085951bf0b256770c
[modules/shaper.git] / src / SketchAPI / SketchAPI_MacroEllipse.cpp
1 // Copyright (C) 2014-2023  CEA, EDF
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License, or (at your option) any later version.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "SketchAPI_MacroEllipse.h"
21 #include "SketchAPI_Line.h"
22 #include "SketchAPI_Point.h"
23
24 #include <GeomAPI_Pnt2d.h>
25
26 #include <ModelHighAPI_RefAttr.h>
27 #include <ModelHighAPI_Tools.h>
28
29 #include <SketchPlugin_Sketch.h>
30
31 #define POINT_ATTR(x) (std::dynamic_pointer_cast<GeomDataAPI_Point2D>(feature()->attribute((x))))
32 #define POINT_REF(x)  (feature()->refattr((x)))
33
34
35 SketchAPI_MacroEllipse::SketchAPI_MacroEllipse(const std::shared_ptr<ModelAPI_Feature>& theFeature,
36                                                bool callInitialize)
37 : SketchAPI_SketchEntity(theFeature)
38 {
39   if (callInitialize && initialize())
40     storeSketch(theFeature);
41 }
42
43 SketchAPI_MacroEllipse::SketchAPI_MacroEllipse(const std::shared_ptr<ModelAPI_Feature>& theFeature,
44                                                double theX1, double theY1,
45                                                double theX2, double theY2,
46                                                double theX3, double theY3,
47                                                bool byCenter)
48   : SketchAPI_SketchEntity(theFeature)
49 {
50   if (initialize()) {
51     static const ModelHighAPI_RefAttr DUMMY_REF;
52
53     GeomPnt2dPtr aPnt1(new GeomAPI_Pnt2d(theX1, theY1));
54     GeomPnt2dPtr aPnt2(new GeomAPI_Pnt2d(theX2, theY2));
55     GeomPnt2dPtr aPnt3(new GeomAPI_Pnt2d(theX3, theY3));
56
57     if (byCenter)
58       setByCenterAndPassedPoints(aPnt1, DUMMY_REF, aPnt2, DUMMY_REF, aPnt3, DUMMY_REF);
59     else
60       setByMajorAxisAndPassedPoint(aPnt1, DUMMY_REF, aPnt2, DUMMY_REF, aPnt3, DUMMY_REF);
61   }
62 }
63
64 SketchAPI_MacroEllipse::SketchAPI_MacroEllipse(const std::shared_ptr<ModelAPI_Feature>& theFeature,
65                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint1,
66                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint2,
67                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint3,
68                                                bool byCenter)
69   : SketchAPI_SketchEntity(theFeature)
70 {
71   if (initialize()) {
72     static const ModelHighAPI_RefAttr DUMMY_REF;
73     if (byCenter)
74       setByCenterAndPassedPoints(thePoint1, DUMMY_REF, thePoint2, DUMMY_REF, thePoint3, DUMMY_REF);
75     else {
76       setByMajorAxisAndPassedPoint(thePoint1, DUMMY_REF,
77                                    thePoint2, DUMMY_REF,
78                                    thePoint3, DUMMY_REF);
79     }
80   }
81 }
82
83 SketchAPI_MacroEllipse::SketchAPI_MacroEllipse(const std::shared_ptr<ModelAPI_Feature>& theFeature,
84                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint1,
85                                                const ModelHighAPI_RefAttr&           thePoint1Ref,
86                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint2,
87                                                const ModelHighAPI_RefAttr&           thePoint2Ref,
88                                                const std::shared_ptr<GeomAPI_Pnt2d>& thePoint3,
89                                                const ModelHighAPI_RefAttr&           thePoint3Ref,
90                                                bool byCenter)
91   : SketchAPI_SketchEntity(theFeature)
92 {
93   if (initialize()) {
94     if (byCenter) {
95       setByCenterAndPassedPoints(thePoint1, thePoint1Ref,
96                                  thePoint2, thePoint2Ref,
97                                  thePoint3, thePoint3Ref);
98     }
99     else {
100       setByMajorAxisAndPassedPoint(thePoint1, thePoint1Ref,
101                                    thePoint2, thePoint2Ref,
102                                    thePoint3, thePoint3Ref);
103     }
104   }
105 }
106
107 SketchAPI_MacroEllipse::~SketchAPI_MacroEllipse()
108 {
109 }
110
111 static void fillAttribute(const std::shared_ptr<GeomAPI_Pnt2d>& thePoint,
112                           const ModelHighAPI_RefAttr& thePointRef,
113                           std::shared_ptr<GeomDataAPI_Point2D> thePointAttr,
114                           AttributeRefAttrPtr thePointRefAttr)
115 {
116   GeomPnt2dPtr aPoint = thePoint;
117   if (!thePointRef.isEmpty()) {
118     fillAttribute(thePointRef, thePointRefAttr);
119     std::shared_ptr<GeomDataAPI_Point2D> anAttrPnt =
120         std::dynamic_pointer_cast<GeomDataAPI_Point2D>(thePointRefAttr->attr());
121     if (anAttrPnt)
122       aPoint = anAttrPnt->pnt();
123   }
124   fillAttribute(aPoint, thePointAttr);
125 }
126
127 void SketchAPI_MacroEllipse::setByCenterAndPassedPoints(
128     const std::shared_ptr<GeomAPI_Pnt2d>& theCenter,
129     const ModelHighAPI_RefAttr&           theCenterRef,
130     const std::shared_ptr<GeomAPI_Pnt2d>& theMajorAxisPoint,
131     const ModelHighAPI_RefAttr&           theMajorAxisPointRef,
132     const std::shared_ptr<GeomAPI_Pnt2d>& thePassedPoint,
133     const ModelHighAPI_RefAttr&           thePassedPointRef)
134 {
135   fillAttribute(SketchPlugin_MacroEllipse::ELLIPSE_TYPE_BY_CENTER_AXIS_POINT(), myellipseType);
136
137   AttributePoint2DPtr aCenterAttr = POINT_ATTR(SketchPlugin_MacroEllipse::CENTER_POINT_ID());
138   AttributePoint2DPtr aMajorAxisAttr = POINT_ATTR(SketchPlugin_MacroEllipse::MAJOR_AXIS_POINT_ID());
139   AttributePoint2DPtr aPassedAttr = POINT_ATTR(SketchPlugin_MacroEllipse::PASSED_POINT_ID());
140
141   AttributeRefAttrPtr aCenterRef = POINT_REF(SketchPlugin_MacroEllipse::CENTER_POINT_REF_ID());
142   AttributeRefAttrPtr aMajorAxisRef =
143       POINT_REF(SketchPlugin_MacroEllipse::MAJOR_AXIS_POINT_REF_ID());
144   AttributeRefAttrPtr aPassedRef = POINT_REF(SketchPlugin_MacroEllipse::PASSED_POINT_REF_ID());
145
146   fillAttribute(theCenter, theCenterRef, aCenterAttr, aCenterRef);
147   fillAttribute(theMajorAxisPoint, theMajorAxisPointRef, aMajorAxisAttr, aMajorAxisRef);
148   fillAttribute(thePassedPoint, thePassedPointRef, aPassedAttr, aPassedRef);
149
150   storeSketch(feature());
151   execute();
152 }
153
154 void SketchAPI_MacroEllipse::setByMajorAxisAndPassedPoint(
155     const std::shared_ptr<GeomAPI_Pnt2d>& theMajorAxisStart,
156     const ModelHighAPI_RefAttr&           theMajorAxisStartRef,
157     const std::shared_ptr<GeomAPI_Pnt2d>& theMajorAxisEnd,
158     const ModelHighAPI_RefAttr&           theMajorAxisEndRef,
159     const std::shared_ptr<GeomAPI_Pnt2d>& thePassedPoint,
160     const ModelHighAPI_RefAttr&           thePassedPointRef)
161 {
162   fillAttribute(SketchPlugin_MacroEllipse::ELLIPSE_TYPE_BY_AXIS_AND_POINT(), myellipseType);
163
164   AttributePoint2DPtr aMajorAxisStartAttr =
165       POINT_ATTR(SketchPlugin_MacroEllipse::MAJOR_AXIS_START_ID());
166   AttributePoint2DPtr aMajorAxisEndAttr =
167       POINT_ATTR(SketchPlugin_MacroEllipse::MAJOR_AXIS_END_ID());
168   AttributePoint2DPtr aPassedAttr = POINT_ATTR(SketchPlugin_MacroEllipse::PASSED_POINT_1_ID());
169
170   AttributeRefAttrPtr aMajorAxisStartRef =
171       POINT_REF(SketchPlugin_MacroEllipse::MAJOR_AXIS_START_REF_ID());
172   AttributeRefAttrPtr aMajorAxisEndRef =
173       POINT_REF(SketchPlugin_MacroEllipse::MAJOR_AXIS_END_REF_ID());
174   AttributeRefAttrPtr aPassedRef = POINT_REF(SketchPlugin_MacroEllipse::PASSED_POINT_1_REF_ID());
175
176   fillAttribute(theMajorAxisStart, theMajorAxisStartRef, aMajorAxisStartAttr, aMajorAxisStartRef);
177   fillAttribute(theMajorAxisEnd, theMajorAxisEndRef, aMajorAxisEndAttr, aMajorAxisEndRef);
178   fillAttribute(thePassedPoint, thePassedPointRef, aPassedAttr, aPassedRef);
179
180   storeSketch(feature());
181   execute();
182 }
183
184 void SketchAPI_MacroEllipse::storeSketch(const FeaturePtr& theFeature)
185 {
186   const std::set<AttributePtr>& aRefs = theFeature->data()->refsToMe();
187   for (std::set<AttributePtr>::const_iterator anIt = aRefs.begin(); anIt != aRefs.end(); ++anIt)
188     if ((*anIt)->id() == SketchPlugin_Sketch::FEATURES_ID()) {
189       mySketch = std::dynamic_pointer_cast<ModelAPI_CompositeFeature>((*anIt)->owner());
190       break;
191     }
192 }
193
194 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::center()
195 {
196   if (!myCenter)
197     collectAuxiliary();
198   return myCenter;
199 }
200
201 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::focus1()
202 {
203   if (!myFocus1)
204     collectAuxiliary();
205   return myFocus1;
206 }
207
208 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::focus2()
209 {
210   if (!myFocus2)
211     collectAuxiliary();
212   return myFocus2;
213 }
214
215 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::majorAxisStart()
216 {
217   if (!myMajorAxisStart)
218     collectAuxiliary();
219   return myMajorAxisStart;
220 }
221
222 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::majorAxisEnd()
223 {
224   if (!myMajorAxisEnd)
225     collectAuxiliary();
226   return myMajorAxisEnd;
227 }
228
229 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::minorAxisStart()
230 {
231   if (!myMinorAxisStart)
232     collectAuxiliary();
233   return myMinorAxisStart;
234 }
235
236 std::shared_ptr<SketchAPI_Point> SketchAPI_MacroEllipse::minorAxisEnd()
237 {
238   if (!myMinorAxisEnd)
239     collectAuxiliary();
240   return myMinorAxisEnd;
241 }
242
243 std::shared_ptr<SketchAPI_Line> SketchAPI_MacroEllipse::majorAxis()
244 {
245   if (!myMajorAxis)
246     collectAuxiliary();
247   return myMajorAxis;
248 }
249
250 std::shared_ptr<SketchAPI_Line> SketchAPI_MacroEllipse::minorAxis()
251 {
252   if (!myMinorAxis)
253     collectAuxiliary();
254   return myMinorAxis;
255 }
256
257 void SketchAPI_MacroEllipse::collectAuxiliary()
258 {
259   // collect auxiliary features
260   int aNbSubs = mySketch->numberOfSubs();
261   std::shared_ptr<SketchAPI_Point>* anAuxPoint[] = {
262     &myCenter, &myFocus1, &myFocus2,
263     &myMajorAxisStart, &myMajorAxisEnd,
264     &myMinorAxisStart, &myMinorAxisEnd
265   };
266   std::shared_ptr<SketchAPI_Line>* anAuxLine[] = {&myMajorAxis, &myMinorAxis};
267   for (int aPtInd = 7, aLinInd = 2; (aPtInd > 0 || aLinInd > 0) && aNbSubs >= 0; ) {
268     FeaturePtr aCurFeature = mySketch->subFeature(--aNbSubs);
269     if (aPtInd > 0 && aCurFeature->getKind() == SketchPlugin_Point::ID())
270       anAuxPoint[--aPtInd]->reset(new SketchAPI_Point(aCurFeature));
271     else if (aLinInd > 0 && aCurFeature->getKind() == SketchPlugin_Line::ID())
272       anAuxLine[--aLinInd]->reset(new SketchAPI_Line(aCurFeature));
273   }
274 }