b311480e |
1 | // Created on: 1996-12-05 |
2 | // Created by: Arnaud BOUZY/Odile Olivier |
3 | // Copyright (c) 1996-1999 Matra Datavision |
a6eb515f |
4 | // Copyright (c) 1999-2013 OPEN CASCADE SAS |
b311480e |
5 | // |
973c2be1 |
6 | // This file is part of Open CASCADE Technology software library. |
b311480e |
7 | // |
d5f74e42 |
8 | // This library is free software; you can redistribute it and/or modify it under |
9 | // the terms of the GNU Lesser General Public License version 2.1 as published |
973c2be1 |
10 | // by the Free Software Foundation, with special exception defined in the file |
11 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
12 | // distribution for complete text of the license and disclaimer of any warranty. |
b311480e |
13 | // |
973c2be1 |
14 | // Alternatively, this file may be used under the terms of Open CASCADE |
15 | // commercial license or contractual agreement. |
b311480e |
16 | |
a6eb515f |
17 | #include <AIS_LengthDimension.hxx> |
7fd59977 |
18 | |
19 | #include <AIS.hxx> |
a6eb515f |
20 | #include <BRep_Tool.hxx> |
7fd59977 |
21 | #include <BRepAdaptor_Curve.hxx> |
1c078d3b |
22 | #include <BRepExtrema_DistShapeShape.hxx> |
a6eb515f |
23 | #include <BRepLib_MakeVertex.hxx> |
24 | #include <BRepTopAdaptor_FClass2d.hxx> |
60bf98ae |
25 | #include <BRepTools.hxx> |
7fd59977 |
26 | #include <ElCLib.hxx> |
27 | #include <ElSLib.hxx> |
a6eb515f |
28 | #include <gce_MakeDir.hxx> |
60bf98ae |
29 | #include <gce_MakePln.hxx> |
1c078d3b |
30 | #include <Geom_TrimmedCurve.hxx> |
60bf98ae |
31 | #include <GeomAPI_ExtremaCurveCurve.hxx> |
60bf98ae |
32 | #include <GeomAPI_ExtremaSurfaceSurface.hxx> |
33 | #include <Geom_Curve.hxx> |
34 | #include <Geom_Line.hxx> |
7fd59977 |
35 | #include <TopExp.hxx> |
36 | #include <TopExp_Explorer.hxx> |
7fd59977 |
37 | |
7fd59977 |
38 | |
92efcf78 |
39 | IMPLEMENT_STANDARD_RTTIEXT(AIS_LengthDimension,AIS_Dimension) |
40 | |
7fd59977 |
41 | //======================================================================= |
42 | //function : Constructor |
60bf98ae |
43 | //purpose : Dimension between two faces |
44 | //======================================================================= |
45 | AIS_LengthDimension::AIS_LengthDimension (const TopoDS_Face& theFirstFace, |
46 | const TopoDS_Face& theSecondFace) |
47 | : AIS_Dimension (AIS_KOD_LENGTH) |
48 | { |
49 | SetMeasuredGeometry (theFirstFace, theSecondFace); |
50 | SetFlyout (15.0); |
51 | } |
52 | |
53 | //======================================================================= |
54 | //function : Constructor |
55 | //purpose : Dimension between two shape |
7fd59977 |
56 | //======================================================================= |
60bf98ae |
57 | AIS_LengthDimension::AIS_LengthDimension (const TopoDS_Face& theFace, |
58 | const TopoDS_Edge& theEdge) |
59 | : AIS_Dimension (AIS_KOD_LENGTH) |
60 | { |
61 | SetMeasuredGeometry (theFace, theEdge); |
62 | SetFlyout (15.0); |
63 | } |
7fd59977 |
64 | |
60bf98ae |
65 | //======================================================================= |
66 | //function : Constructor |
67 | //purpose : Dimension between two points |
68 | //======================================================================= |
a6eb515f |
69 | AIS_LengthDimension::AIS_LengthDimension (const gp_Pnt& theFirstPoint, |
70 | const gp_Pnt& theSecondPoint, |
60bf98ae |
71 | const gp_Pln& thePlane) |
72 | : AIS_Dimension (AIS_KOD_LENGTH) |
7fd59977 |
73 | { |
60bf98ae |
74 | SetMeasuredGeometry (theFirstPoint, theSecondPoint, thePlane); |
d7bffd44 |
75 | SetFlyout (15.0); |
7fd59977 |
76 | } |
77 | |
7fd59977 |
78 | //======================================================================= |
79 | //function : Constructor |
a6eb515f |
80 | //purpose : Dimension between two shape |
7fd59977 |
81 | //======================================================================= |
a6eb515f |
82 | AIS_LengthDimension::AIS_LengthDimension (const TopoDS_Shape& theFirstShape, |
83 | const TopoDS_Shape& theSecondShape, |
60bf98ae |
84 | const gp_Pln& thePlane) |
85 | : AIS_Dimension (AIS_KOD_LENGTH) |
7fd59977 |
86 | { |
60bf98ae |
87 | SetCustomPlane (thePlane); |
88 | SetMeasuredShapes (theFirstShape, theSecondShape); |
d7bffd44 |
89 | SetFlyout (15.0); |
7fd59977 |
90 | } |
91 | |
92 | //======================================================================= |
93 | //function : Constructor |
a6eb515f |
94 | //purpose : Dimension of one edge |
7fd59977 |
95 | //======================================================================= |
a6eb515f |
96 | AIS_LengthDimension::AIS_LengthDimension (const TopoDS_Edge& theEdge, |
60bf98ae |
97 | const gp_Pln& thePlane) |
98 | : AIS_Dimension (AIS_KOD_LENGTH) |
7fd59977 |
99 | { |
60bf98ae |
100 | SetMeasuredGeometry (theEdge, thePlane); |
d7bffd44 |
101 | SetFlyout (15.0); |
7fd59977 |
102 | } |
103 | |
7fd59977 |
104 | //======================================================================= |
60bf98ae |
105 | //function : SetMeasuredGeometry |
106 | //purpose : |
7fd59977 |
107 | //======================================================================= |
60bf98ae |
108 | void AIS_LengthDimension::SetMeasuredGeometry (const gp_Pnt& theFirstPoint, |
109 | const gp_Pnt& theSecondPoint, |
110 | const gp_Pln& thePlane) |
111 | { |
91b16a64 |
112 | myFirstPoint = theFirstPoint; |
113 | mySecondPoint = theSecondPoint; |
114 | myFirstShape = BRepLib_MakeVertex (myFirstPoint); |
115 | mySecondShape = BRepLib_MakeVertex (mySecondPoint); |
116 | myGeometryType = GeometryType_Points; |
60bf98ae |
117 | SetCustomPlane (thePlane); |
91b16a64 |
118 | myIsGeometryValid = IsValidPoints (theFirstPoint, theSecondPoint); |
60bf98ae |
119 | |
120 | SetToUpdate(); |
121 | } |
7fd59977 |
122 | |
60bf98ae |
123 | //======================================================================= |
124 | //function : SetMeasuredGeometry |
125 | //purpose : |
126 | //======================================================================= |
127 | void AIS_LengthDimension::SetMeasuredGeometry (const TopoDS_Edge& theEdge, |
128 | const gp_Pln& thePlane) |
7fd59977 |
129 | { |
91b16a64 |
130 | myFirstShape = theEdge; |
131 | mySecondShape = TopoDS_Shape(); |
132 | myGeometryType = GeometryType_Edge; |
60bf98ae |
133 | SetCustomPlane (thePlane); |
91b16a64 |
134 | myIsGeometryValid = InitOneShapePoints (myFirstShape); |
60bf98ae |
135 | |
136 | SetToUpdate(); |
7fd59977 |
137 | } |
138 | |
139 | //======================================================================= |
60bf98ae |
140 | //function : SetMeasuredGeometry |
141 | //purpose : |
7fd59977 |
142 | //======================================================================= |
60bf98ae |
143 | void AIS_LengthDimension::SetMeasuredGeometry (const TopoDS_Face& theFirstFace, |
144 | const TopoDS_Face& theSecondFace) |
145 | { |
146 | SetMeasuredShapes (theFirstFace, theSecondFace); |
147 | } |
7fd59977 |
148 | |
60bf98ae |
149 | //======================================================================= |
150 | //function : SetMeasuredGeometry |
151 | //purpose : |
152 | //======================================================================= |
153 | void AIS_LengthDimension::SetMeasuredGeometry (const TopoDS_Face& theFace, |
154 | const TopoDS_Edge& theEdge) |
7fd59977 |
155 | { |
60bf98ae |
156 | SetMeasuredShapes (theFace, theEdge); |
157 | } |
158 | |
159 | //======================================================================= |
160 | //function : SetMeasuredShapes |
161 | //purpose : |
162 | //======================================================================= |
163 | void AIS_LengthDimension::SetMeasuredShapes (const TopoDS_Shape& theFirstShape, |
164 | const TopoDS_Shape& theSecondShape) |
165 | { |
166 | gp_Pln aComputedPlane; |
167 | Standard_Boolean isPlaneReturned = Standard_False; |
60bf98ae |
168 | |
91b16a64 |
169 | myFirstShape = theFirstShape; |
170 | mySecondShape = theSecondShape; |
171 | myIsGeometryValid = InitTwoShapesPoints (myFirstShape, mySecondShape, aComputedPlane, isPlaneReturned); |
172 | |
173 | if (myIsGeometryValid && !myIsPlaneCustom) |
60bf98ae |
174 | { |
175 | if (isPlaneReturned) |
176 | { |
177 | myPlane = aComputedPlane; |
178 | } |
179 | else |
180 | { |
91b16a64 |
181 | myIsGeometryValid = Standard_False; |
60bf98ae |
182 | } |
183 | } |
184 | |
60bf98ae |
185 | SetToUpdate(); |
186 | } |
187 | |
188 | //======================================================================= |
189 | //function : CheckPlane |
190 | //purpose : |
191 | //======================================================================= |
192 | Standard_Boolean AIS_LengthDimension::CheckPlane (const gp_Pln& thePlane) const |
193 | { |
b0804487 |
194 | Standard_Boolean anIsFaultyNormal = |
195 | thePlane.Axis().Direction().IsParallel(gce_MakeDir (myFirstPoint, mySecondPoint), Precision::Angular()); |
196 | |
197 | if ((!thePlane.Contains (myFirstPoint, Precision::Confusion()) && !thePlane.Contains (mySecondPoint, Precision::Confusion())) |
198 | || anIsFaultyNormal) |
60bf98ae |
199 | { |
200 | return Standard_False; |
201 | } |
202 | |
203 | return Standard_True; |
204 | } |
205 | |
206 | //======================================================================= |
207 | //function : ComputePlane |
208 | //purpose : |
209 | //======================================================================= |
210 | gp_Pln AIS_LengthDimension::ComputePlane (const gp_Dir& theAttachDir) const |
211 | { |
212 | if (!IsValidPoints (myFirstPoint, mySecondPoint)) |
213 | { |
214 | return gp_Pln(); |
215 | } |
216 | |
217 | gp_Pnt aThirdPoint (myFirstPoint.Translated (gp_Vec(theAttachDir))); |
218 | gce_MakePln aPlaneConstrustor (myFirstPoint, mySecondPoint, aThirdPoint); |
219 | return aPlaneConstrustor.Value(); |
220 | } |
221 | |
222 | //======================================================================= |
223 | //function : GetModelUnits |
224 | //purpose : |
225 | //======================================================================= |
226 | const TCollection_AsciiString& AIS_LengthDimension::GetModelUnits() const |
227 | { |
228 | return myDrawer->DimLengthModelUnits(); |
7fd59977 |
229 | } |
230 | |
231 | //======================================================================= |
60bf98ae |
232 | //function : GetDisplayUnits |
233 | //purpose : |
7fd59977 |
234 | //======================================================================= |
60bf98ae |
235 | const TCollection_AsciiString& AIS_LengthDimension::GetDisplayUnits() const |
236 | { |
237 | return myDrawer->DimLengthDisplayUnits(); |
238 | } |
239 | |
240 | //======================================================================= |
241 | //function : SetModelUnits |
242 | //purpose : |
243 | //======================================================================= |
244 | void AIS_LengthDimension::SetModelUnits (const TCollection_AsciiString& theUnits) |
245 | { |
246 | myDrawer->SetDimLengthModelUnits (theUnits); |
247 | } |
248 | |
249 | //======================================================================= |
250 | //function : SetDisplayUnits |
251 | //purpose : |
252 | //======================================================================= |
253 | void AIS_LengthDimension::SetDisplayUnits (const TCollection_AsciiString& theUnits) |
254 | { |
255 | myDrawer->SetDimLengthDisplayUnits (theUnits); |
256 | } |
7fd59977 |
257 | |
60bf98ae |
258 | //======================================================================= |
259 | //function : ComputeValue |
260 | //purpose : |
261 | //======================================================================= |
262 | Standard_Real AIS_LengthDimension::ComputeValue() const |
263 | { |
264 | return IsValid() ? myFirstPoint.Distance (mySecondPoint) : 0.0; |
265 | } |
266 | |
267 | //======================================================================= |
268 | //function : Compute |
269 | //purpose : |
270 | //======================================================================= |
271 | void AIS_LengthDimension::Compute (const Handle(PrsMgr_PresentationManager3d)& /*thePM*/, |
272 | const Handle(Prs3d_Presentation)& thePresentation, |
273 | const Standard_Integer theMode) |
274 | { |
60bf98ae |
275 | mySelectionGeom.Clear (theMode); |
276 | |
277 | if (!IsValid()) |
278 | { |
279 | return; |
280 | } |
281 | |
282 | DrawLinearDimension (thePresentation, theMode, myFirstPoint, mySecondPoint); |
283 | } |
284 | |
285 | //======================================================================= |
286 | //function : ComputeFlyoutSelection |
287 | //purpose : |
288 | //======================================================================= |
289 | void AIS_LengthDimension::ComputeFlyoutSelection (const Handle(SelectMgr_Selection)& theSelection, |
290 | const Handle(SelectMgr_EntityOwner)& theEntityOwner) |
291 | { |
292 | if (!IsValid()) |
293 | { |
294 | return; |
295 | } |
296 | |
297 | ComputeLinearFlyouts (theSelection, theEntityOwner, myFirstPoint, mySecondPoint); |
298 | } |
299 | |
300 | //======================================================================= |
301 | //function : IsValidPoints |
302 | //purpose : |
303 | //======================================================================= |
304 | Standard_Boolean AIS_LengthDimension::IsValidPoints (const gp_Pnt& theFirstPoint, |
305 | const gp_Pnt& theSecondPoint) const |
306 | { |
307 | return theFirstPoint.Distance (theSecondPoint) > Precision::Confusion(); |
308 | } |
309 | |
310 | //======================================================================= |
311 | //function : InitTwoEdgesLength |
312 | //purpose : Initialization of dimension between two linear edges |
313 | //======================================================================= |
314 | Standard_Boolean AIS_LengthDimension::InitTwoEdgesLength (const TopoDS_Edge& theFirstEdge, |
d7bffd44 |
315 | const TopoDS_Edge& theSecondEdge, |
316 | gp_Dir& theDirAttach) |
7fd59977 |
317 | { |
a6eb515f |
318 | BRepAdaptor_Curve aFirstCurveAdapt (theFirstEdge); |
319 | if (aFirstCurveAdapt.GetType() != GeomAbs_Line) |
60bf98ae |
320 | { |
a6eb515f |
321 | return Standard_False; |
60bf98ae |
322 | } |
323 | |
a6eb515f |
324 | BRepAdaptor_Curve aSecondCurveAdapt (theSecondEdge); |
325 | if (aSecondCurveAdapt.GetType() != GeomAbs_Line) |
60bf98ae |
326 | { |
a6eb515f |
327 | return Standard_False; |
60bf98ae |
328 | } |
a6eb515f |
329 | |
60bf98ae |
330 | Handle(Geom_Curve) aFirstCurve; |
331 | Handle(Geom_Curve) aSecondCurve; |
332 | |
333 | gp_Pnt aPoint11 (gp::Origin()); |
334 | gp_Pnt aPoint12 (gp::Origin()); |
335 | gp_Pnt aPoint21 (gp::Origin()); |
336 | gp_Pnt aPoint22 (gp::Origin()); |
337 | Standard_Boolean isFirstInfinite = Standard_False; |
338 | Standard_Boolean isSecondInfinite = Standard_False; |
339 | |
340 | if (!AIS::ComputeGeometry (theFirstEdge, theSecondEdge, |
341 | aFirstCurve, aSecondCurve, |
342 | aPoint11, aPoint12, |
343 | aPoint21, aPoint22, |
344 | isFirstInfinite, |
345 | isSecondInfinite)) |
a6eb515f |
346 | { |
60bf98ae |
347 | return Standard_False; |
a6eb515f |
348 | } |
60bf98ae |
349 | |
350 | const Handle(Geom_Line) aFirstLine = Handle(Geom_Line)::DownCast (aFirstCurve); |
351 | const Handle(Geom_Line) aSecondLine = Handle(Geom_Line)::DownCast (aSecondCurve); |
352 | |
353 | if (!aFirstLine->Lin().Direction().IsParallel (aSecondLine->Lin().Direction(),Precision::Angular())) |
a6eb515f |
354 | { |
60bf98ae |
355 | return Standard_False; |
7fd59977 |
356 | } |
60bf98ae |
357 | |
358 | theDirAttach = aFirstLine->Lin().Direction(); |
359 | |
360 | gp_Pnt aPoint; |
361 | |
a6eb515f |
362 | if (!isFirstInfinite) |
363 | { |
60bf98ae |
364 | if (AIS::Nearest (aSecondCurve, aPoint11, aPoint21, aPoint22, aPoint)) |
365 | { |
a6eb515f |
366 | myFirstPoint = aPoint11; |
60bf98ae |
367 | mySecondPoint = aPoint; |
368 | return IsValidPoints (myFirstPoint, mySecondPoint); |
369 | } |
370 | else if (AIS::Nearest (aSecondCurve, aPoint12, aPoint21, aPoint22, aPoint)) |
371 | { |
372 | myFirstPoint = aPoint12; |
373 | mySecondPoint = aPoint; |
374 | return IsValidPoints (myFirstPoint, mySecondPoint); |
375 | } |
7fd59977 |
376 | } |
377 | |
a6eb515f |
378 | if (!isSecondInfinite) |
379 | { |
60bf98ae |
380 | if (AIS::Nearest (aFirstCurve, aPoint21, aPoint11, aPoint12, aPoint)) |
381 | { |
382 | myFirstPoint = aPoint; |
a6eb515f |
383 | mySecondPoint = aPoint21; |
60bf98ae |
384 | return IsValidPoints (myFirstPoint, mySecondPoint); |
385 | } |
386 | if (AIS::Nearest (aFirstCurve, aPoint22, aPoint11, aPoint12, aPoint)) |
387 | { |
388 | myFirstPoint = aPoint; |
389 | mySecondPoint = aPoint22; |
390 | return IsValidPoints (myFirstPoint, mySecondPoint); |
391 | } |
a6eb515f |
392 | } |
7fd59977 |
393 | |
60bf98ae |
394 | GeomAPI_ExtremaCurveCurve anExtrema (aFirstCurve, aSecondCurve); |
395 | anExtrema.NearestPoints (myFirstPoint, mySecondPoint); |
396 | return IsValidPoints (myFirstPoint, mySecondPoint); |
7fd59977 |
397 | } |
398 | |
7fd59977 |
399 | //======================================================================= |
60bf98ae |
400 | //function : InitEdgeVertexLength |
a6eb515f |
401 | //purpose : for first edge and second vertex shapes |
7fd59977 |
402 | //======================================================================= |
60bf98ae |
403 | Standard_Boolean AIS_LengthDimension::InitEdgeVertexLength (const TopoDS_Edge& theEdge, |
404 | const TopoDS_Vertex& theVertex, |
405 | gp_Dir& theEdgeDir, |
d7bffd44 |
406 | Standard_Boolean isInfinite) |
7fd59977 |
407 | { |
60bf98ae |
408 | gp_Pnt anEdgePoint1 (gp::Origin()); |
409 | gp_Pnt anEdgePoint2 (gp::Origin()); |
a6eb515f |
410 | Handle(Geom_Curve) aCurve; |
60bf98ae |
411 | |
412 | if (!AIS::ComputeGeometry (theEdge, aCurve, anEdgePoint1, anEdgePoint2, isInfinite)) |
413 | { |
a6eb515f |
414 | return Standard_False; |
60bf98ae |
415 | } |
416 | |
417 | myFirstPoint = BRep_Tool::Pnt (theVertex); |
a6eb515f |
418 | |
c5f3a425 |
419 | Handle(Geom_Line) aGeomLine (Handle(Geom_Line)::DownCast (aCurve)); |
a6eb515f |
420 | const gp_Lin& aLin = aGeomLine->Lin(); |
421 | |
60bf98ae |
422 | // Get direction of edge to build plane automatically. |
423 | theEdgeDir = aLin.Direction(); |
a6eb515f |
424 | |
60bf98ae |
425 | mySecondPoint = AIS::Nearest (aLin, myFirstPoint); |
a6eb515f |
426 | |
60bf98ae |
427 | return IsValidPoints (myFirstPoint, mySecondPoint); |
7fd59977 |
428 | } |
429 | |
7fd59977 |
430 | //======================================================================= |
60bf98ae |
431 | //function : InitEdgeFaceLength |
7fd59977 |
432 | //purpose : |
433 | //======================================================================= |
60bf98ae |
434 | Standard_Boolean AIS_LengthDimension::InitEdgeFaceLength (const TopoDS_Edge& theEdge, |
a6eb515f |
435 | const TopoDS_Face& theFace, |
60bf98ae |
436 | gp_Dir& theEdgeDir) |
7fd59977 |
437 | { |
3c162495 |
438 | theEdgeDir = gp::DX(); |
439 | |
440 | // Find attachment points (closest distance between the edge and the face) |
441 | BRepExtrema_DistShapeShape aDistAdaptor (theEdge, theFace, Extrema_ExtFlag_MIN); |
442 | if (!aDistAdaptor.IsDone() || aDistAdaptor.NbSolution() <1) |
a6eb515f |
443 | { |
60bf98ae |
444 | return Standard_False; |
7fd59977 |
445 | } |
3c162495 |
446 | myFirstPoint = aDistAdaptor.PointOnShape1 (1); |
447 | mySecondPoint = aDistAdaptor.PointOnShape2 (1); |
448 | |
449 | // Take direction for dimension line (will be orthogonalized later) parallel to edge |
450 | BRepAdaptor_Curve aCurveAdaptor (theEdge); |
451 | Standard_Real aParam; |
452 | if (aDistAdaptor.SupportOnShape1 (1).ShapeType() == TopAbs_EDGE) |
a6eb515f |
453 | { |
3c162495 |
454 | aDistAdaptor.ParOnEdgeS1 (1, aParam); |
455 | } |
456 | else |
457 | { |
458 | Standard_Real aD1 = aCurveAdaptor.Value(aCurveAdaptor.FirstParameter()).SquareDistance (myFirstPoint); |
459 | Standard_Real aD2 = aCurveAdaptor.Value(aCurveAdaptor.LastParameter()).SquareDistance (myFirstPoint); |
460 | aParam = (aD1 < aD2 ? aCurveAdaptor.FirstParameter() : aCurveAdaptor.LastParameter()); |
461 | } |
462 | gp_Pnt aP; |
463 | gp_Vec aV; |
464 | aCurveAdaptor.D1 (aParam, aP, aV); |
465 | if (aV.SquareMagnitude() > gp::Resolution()) |
466 | { |
467 | theEdgeDir = aV; |
7fd59977 |
468 | } |
7fd59977 |
469 | |
3c162495 |
470 | // reverse direction if parameter is close to the end of the curve, |
471 | // to reduce chances to have overlapping between dimension line and edge |
472 | if (Abs (aParam - aCurveAdaptor.FirstParameter()) < Abs (aParam - aCurveAdaptor.LastParameter())) |
1c078d3b |
473 | { |
3c162495 |
474 | theEdgeDir.Reverse(); |
1c078d3b |
475 | } |
60bf98ae |
476 | |
477 | return IsValidPoints (myFirstPoint, mySecondPoint); |
7fd59977 |
478 | } |
479 | |
480 | //======================================================================= |
60bf98ae |
481 | //function : InitTwoShapesPoints |
a6eb515f |
482 | //purpose : Initialization of two points where dimension layouts |
483 | // will be attached |
7fd59977 |
484 | //======================================================================= |
60bf98ae |
485 | Standard_Boolean AIS_LengthDimension::InitTwoShapesPoints (const TopoDS_Shape& theFirstShape, |
486 | const TopoDS_Shape& theSecondShape, |
487 | gp_Pln& theComputedPlane, |
488 | Standard_Boolean& theIsPlaneComputed) |
7fd59977 |
489 | { |
60bf98ae |
490 | theIsPlaneComputed = Standard_False; |
a6eb515f |
491 | gp_Dir aDirAttach; |
492 | Standard_Boolean isInfinite = Standard_False; |
60bf98ae |
493 | Standard_Boolean isSuccess = Standard_False; |
a6eb515f |
494 | switch (theFirstShape.ShapeType()) |
495 | { |
60bf98ae |
496 | case TopAbs_FACE: |
7fd59977 |
497 | { |
a6eb515f |
498 | // Initialization for face |
499 | gp_Pln aFirstPlane; |
500 | Handle(Geom_Surface) aFirstSurface; |
501 | AIS_KindOfSurface aFirstSurfKind; |
502 | Standard_Real aFirstOffset; |
60bf98ae |
503 | |
a6eb515f |
504 | TopoDS_Face aFirstFace = TopoDS::Face (theFirstShape); |
a6eb515f |
505 | |
60bf98ae |
506 | AIS::InitFaceLength (TopoDS::Face (theFirstShape), |
507 | aFirstPlane, |
508 | aFirstSurface, |
509 | aFirstSurfKind, |
510 | aFirstOffset); |
511 | |
512 | if (theSecondShape.ShapeType() == TopAbs_FACE) |
a6eb515f |
513 | { |
514 | // Initialization for face |
60bf98ae |
515 | myGeometryType = GeometryType_Faces; |
a6eb515f |
516 | gp_Pln aSecondPlane; |
517 | Handle(Geom_Surface) aSecondSurface; |
518 | AIS_KindOfSurface aSecondSurfKind; |
519 | Standard_Real aSecondOffset; |
60bf98ae |
520 | |
a6eb515f |
521 | TopoDS_Face aSecondFace = TopoDS::Face (theSecondShape); |
60bf98ae |
522 | |
523 | AIS::InitFaceLength (aSecondFace, |
524 | aSecondPlane, |
525 | aSecondSurface, |
526 | aSecondSurfKind, |
527 | aSecondOffset); |
528 | |
a6eb515f |
529 | if (aFirstSurfKind == AIS_KOS_Plane) |
7fd59977 |
530 | { |
60bf98ae |
531 | if (!aFirstPlane.Axis().Direction().IsParallel (aSecondPlane.Axis().Direction(), Precision::Angular())) |
532 | { |
533 | return Standard_False; |
534 | } |
535 | |
a6eb515f |
536 | TopExp_Explorer anExplorer (theFirstShape, TopAbs_VERTEX); |
60bf98ae |
537 | |
a6eb515f |
538 | // In case of infinite planes |
539 | if (!anExplorer.More()) |
60bf98ae |
540 | { |
a6eb515f |
541 | myFirstPoint = aFirstPlane.Location(); |
60bf98ae |
542 | } |
543 | else |
544 | { |
545 | myFirstPoint = BRep_Tool::Pnt (TopoDS::Vertex (anExplorer.Current())); |
546 | } |
547 | |
a6eb515f |
548 | mySecondPoint = AIS::ProjectPointOnPlane (myFirstPoint, aSecondPlane); |
549 | |
a6eb515f |
550 | Quantity_Parameter anU, aV; |
551 | ElSLib::Parameters (aSecondPlane, mySecondPoint, anU, aV); |
60bf98ae |
552 | |
a6eb515f |
553 | BRepTopAdaptor_FClass2d aClassifier (aSecondFace, Precision::Confusion()); |
554 | TopAbs_State aState = aClassifier.Perform (gp_Pnt2d (anU, aV), Standard_False); |
60bf98ae |
555 | |
a6eb515f |
556 | if (aState == TopAbs_OUT || aState == TopAbs_UNKNOWN) |
557 | { |
60bf98ae |
558 | mySecondPoint = AIS::Nearest (aSecondFace, myFirstPoint); |
559 | } |
560 | |
561 | isSuccess = IsValidPoints (myFirstPoint, mySecondPoint); |
562 | if (isSuccess) |
563 | { |
564 | theComputedPlane = ComputePlane (aFirstPlane.Position().XDirection()); |
565 | theIsPlaneComputed = Standard_True; |
a6eb515f |
566 | } |
7fd59977 |
567 | } |
a6eb515f |
568 | else // curvilinear faces |
7fd59977 |
569 | { |
60bf98ae |
570 | Standard_Real aU1Min, aV1Min, aU1Max, aV1Max; |
571 | Standard_Real aU2Min, aV2Min, aU2Max, aV2Max; |
572 | BRepTools::UVBounds (aFirstFace, aU1Min, aU1Max, aV1Min, aV1Max); |
573 | BRepTools::UVBounds (aSecondFace, aU2Min, aU2Max, aV2Min, aV2Max); |
574 | |
575 | GeomAPI_ExtremaSurfaceSurface anExtrema (aFirstSurface, aSecondSurface, |
576 | aU1Min, aU1Max, aV1Min, aV1Max, |
577 | aU2Min, aU2Max, aV2Min, aV2Max); |
578 | |
579 | Standard_Real aU1, aV1, aU2, aV2; |
580 | anExtrema.LowerDistanceParameters (aU1, aV1, aU2, aV2); |
581 | myFirstPoint = BRep_Tool::Surface (aFirstFace)->Value (aU1, aV1); |
582 | mySecondPoint = BRep_Tool::Surface (aSecondFace)->Value (aU2, aV2); |
583 | |
584 | // Adjust automatic plane |
585 | gp_Ax2 aLocalAxes (myFirstPoint, gce_MakeDir (myFirstPoint, mySecondPoint)); |
586 | aDirAttach = gce_MakeDir (aLocalAxes.XDirection ()); |
587 | |
588 | // Check points |
589 | isSuccess = IsValidPoints (myFirstPoint, mySecondPoint); |
590 | if (isSuccess) |
591 | { |
592 | theComputedPlane = ComputePlane (aDirAttach); |
593 | theIsPlaneComputed = Standard_True; |
594 | } |
7fd59977 |
595 | } |
60bf98ae |
596 | |
597 | return isSuccess && IsValidPoints (myFirstPoint, mySecondPoint); |
a6eb515f |
598 | } |
1c078d3b |
599 | else if (theSecondShape.ShapeType() == TopAbs_EDGE) |
a6eb515f |
600 | { |
60bf98ae |
601 | myGeometryType = GeometryType_EdgeFace; |
1c078d3b |
602 | isSuccess = InitEdgeFaceLength (TopoDS::Edge (theSecondShape), |
603 | TopoDS::Face (theFirstShape), |
a6eb515f |
604 | aDirAttach); |
60bf98ae |
605 | |
606 | if (isSuccess) |
607 | { |
608 | theComputedPlane = ComputePlane (aDirAttach); |
609 | theIsPlaneComputed = Standard_True; |
610 | } |
611 | |
612 | return isSuccess; |
a6eb515f |
613 | } |
7fd59977 |
614 | } |
a6eb515f |
615 | break; |
60bf98ae |
616 | |
617 | case TopAbs_EDGE: |
7fd59977 |
618 | { |
a6eb515f |
619 | if (theSecondShape.ShapeType() == TopAbs_VERTEX) |
620 | { |
60bf98ae |
621 | myGeometryType = GeometryType_EdgeVertex; |
622 | isSuccess = InitEdgeVertexLength (TopoDS::Edge (theFirstShape), |
623 | TopoDS::Vertex (theSecondShape), |
624 | aDirAttach, |
625 | isInfinite); |
626 | |
627 | if (isSuccess) |
628 | { |
629 | theComputedPlane = ComputePlane (aDirAttach); |
630 | theIsPlaneComputed = Standard_True; |
631 | } |
632 | |
633 | return isSuccess; |
a6eb515f |
634 | } |
635 | else if (theSecondShape.ShapeType() == TopAbs_EDGE) |
636 | { |
60bf98ae |
637 | myGeometryType = GeometryType_Edges; |
638 | isSuccess = InitTwoEdgesLength (TopoDS::Edge (theFirstShape), |
639 | TopoDS::Edge (theSecondShape), |
640 | aDirAttach); |
641 | |
642 | if (isSuccess) |
643 | { |
644 | theComputedPlane = ComputePlane (aDirAttach); |
645 | theIsPlaneComputed = Standard_True; |
646 | } |
647 | |
1c078d3b |
648 | return isSuccess; |
649 | } |
650 | else if (theSecondShape.ShapeType() == TopAbs_FACE) |
651 | { |
652 | myGeometryType = GeometryType_EdgeFace; |
653 | isSuccess = InitEdgeFaceLength (TopoDS::Edge (theFirstShape), |
654 | TopoDS::Face (theSecondShape), |
655 | aDirAttach); |
656 | |
657 | if (isSuccess) |
658 | { |
659 | theComputedPlane = ComputePlane (aDirAttach); |
660 | theIsPlaneComputed = Standard_True; |
661 | } |
662 | |
60bf98ae |
663 | return isSuccess; |
a6eb515f |
664 | } |
7fd59977 |
665 | } |
a6eb515f |
666 | break; |
60bf98ae |
667 | |
668 | case TopAbs_VERTEX: |
7fd59977 |
669 | { |
a6eb515f |
670 | if (theSecondShape.ShapeType() == TopAbs_VERTEX) |
671 | { |
60bf98ae |
672 | myGeometryType = GeometryType_Points; |
673 | myFirstPoint = BRep_Tool::Pnt (TopoDS::Vertex (theFirstShape)); |
a6eb515f |
674 | mySecondPoint = BRep_Tool::Pnt (TopoDS::Vertex (theSecondShape)); |
60bf98ae |
675 | |
676 | return IsValidPoints (myFirstPoint, mySecondPoint); |
a6eb515f |
677 | } |
678 | else if (theSecondShape.ShapeType() == TopAbs_EDGE) |
679 | { |
60bf98ae |
680 | myGeometryType = GeometryType_EdgeVertex; |
51740958 |
681 | isSuccess = InitEdgeVertexLength (TopoDS::Edge(theSecondShape), |
682 | TopoDS::Vertex(theFirstShape), |
683 | aDirAttach, |
684 | isInfinite); |
60bf98ae |
685 | if (isSuccess) |
686 | { |
687 | theComputedPlane = ComputePlane (aDirAttach); |
688 | theIsPlaneComputed = Standard_True; |
689 | } |
690 | |
691 | return isSuccess; |
a6eb515f |
692 | } |
7fd59977 |
693 | } |
a6eb515f |
694 | break; |
60bf98ae |
695 | |
696 | case TopAbs_COMPOUND: |
697 | case TopAbs_COMPSOLID: |
698 | case TopAbs_SOLID: |
699 | case TopAbs_SHELL: |
700 | case TopAbs_WIRE: |
701 | case TopAbs_SHAPE: |
702 | break; |
a6eb515f |
703 | } |
60bf98ae |
704 | |
705 | return Standard_False; |
7fd59977 |
706 | } |
707 | |
708 | //======================================================================= |
60bf98ae |
709 | //function : InitOneShapePoints |
a6eb515f |
710 | //purpose : Initialization of two points where dimension layouts |
711 | // will be attached |
712 | // Attention: 1) <theShape> can be only the edge in currect implementation |
713 | // 2) No length for infinite edge |
7fd59977 |
714 | //======================================================================= |
60bf98ae |
715 | Standard_Boolean AIS_LengthDimension::InitOneShapePoints (const TopoDS_Shape& theShape) |
7fd59977 |
716 | { |
60bf98ae |
717 | if (theShape.ShapeType() != TopAbs_EDGE) |
a6eb515f |
718 | { |
a6eb515f |
719 | return Standard_False; |
60bf98ae |
720 | } |
7fd59977 |
721 | |
60bf98ae |
722 | TopoDS_Edge anEdge = TopoDS::Edge (theShape); |
7fd59977 |
723 | |
60bf98ae |
724 | BRepAdaptor_Curve aBrepCurve(anEdge); |
725 | Standard_Real aFirst = aBrepCurve.FirstParameter(); |
726 | Standard_Real aLast = aBrepCurve.LastParameter(); |
fe83e1ea |
727 | |
60bf98ae |
728 | if (aBrepCurve.GetType() != GeomAbs_Line) |
a6eb515f |
729 | { |
60bf98ae |
730 | return Standard_False; |
7fd59977 |
731 | } |
d7bffd44 |
732 | |
60bf98ae |
733 | Standard_Boolean isInfinite = (Precision::IsInfinite (aFirst) || Precision::IsInfinite (aLast)); |
734 | if (isInfinite) |
d7bffd44 |
735 | { |
60bf98ae |
736 | return Standard_False; |
d7bffd44 |
737 | } |
7fd59977 |
738 | |
60bf98ae |
739 | myFirstPoint = aBrepCurve.Value (aBrepCurve.FirstParameter()); |
740 | mySecondPoint = aBrepCurve.Value (aBrepCurve.LastParameter()); |
7fd59977 |
741 | |
60bf98ae |
742 | return IsValidPoints (myFirstPoint, mySecondPoint); |
7fd59977 |
743 | } |
af203d54 |
744 | |
745 | //======================================================================= |
746 | //function : GetTextPosition |
747 | //purpose : |
748 | //======================================================================= |
749 | const gp_Pnt AIS_LengthDimension::GetTextPosition() const |
750 | { |
751 | if (IsTextPositionCustom()) |
752 | { |
753 | return myFixedTextPosition; |
754 | } |
755 | |
756 | // Counts text position according to the dimension parameters |
757 | return GetTextPositionForLinear (myFirstPoint, mySecondPoint); |
758 | } |
759 | |
760 | //======================================================================= |
761 | //function : SetTextPosition |
762 | //purpose : |
763 | //======================================================================= |
764 | void AIS_LengthDimension::SetTextPosition (const gp_Pnt& theTextPos) |
765 | { |
91b16a64 |
766 | if (!IsValid()) |
af203d54 |
767 | { |
768 | return; |
769 | } |
770 | |
771 | myIsTextPositionFixed = Standard_True; |
772 | myFixedTextPosition = theTextPos; |
773 | |
774 | SetToUpdate(); |
775 | } |