1 // Created on: 1996-12-11
2 // Created by: Robert COUBLANC
3 // Copyright (c) 1996-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
6 // This file is part of Open CASCADE Technology software library.
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
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.
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
18 #include <Adaptor3d_HCurve.hxx>
19 #include <Adaptor3d_HSurface.hxx>
21 #include <Bnd_Box.hxx>
22 #include <BRep_Tool.hxx>
23 #include <BRepAdaptor_Curve.hxx>
24 #include <BRepAdaptor_HSurface.hxx>
25 #include <BRepAdaptor_Surface.hxx>
26 #include <BRepBuilderAPI_MakeEdge.hxx>
27 #include <BRepBuilderAPI_MakeVertex.hxx>
28 #include <BRepTools.hxx>
29 #include <BRepTopAdaptor_FClass2d.hxx>
32 #include <GccEnt_QualifiedLin.hxx>
33 #include <gce_MakeDir.hxx>
34 #include <gce_MakeLin.hxx>
35 #include <Geom2d_Circle.hxx>
36 #include <Geom_CartesianPoint.hxx>
37 #include <Geom_Circle.hxx>
38 #include <Geom_ConicalSurface.hxx>
39 #include <Geom_Curve.hxx>
40 #include <Geom_CylindricalSurface.hxx>
41 #include <Geom_Ellipse.hxx>
42 #include <Geom_Line.hxx>
43 #include <Geom_OffsetSurface.hxx>
44 #include <Geom_Plane.hxx>
45 #include <Geom_SphericalSurface.hxx>
46 #include <Geom_Surface.hxx>
47 #include <Geom_SurfaceOfLinearExtrusion.hxx>
48 #include <Geom_SurfaceOfRevolution.hxx>
49 #include <Geom_ToroidalSurface.hxx>
50 #include <Geom_TrimmedCurve.hxx>
51 #include <GeomAPI_ExtremaCurveCurve.hxx>
52 #include <GeomAPI_IntSS.hxx>
53 #include <GeomAPI_ProjectPointOnCurve.hxx>
54 #include <GeomAPI_ProjectPointOnSurf.hxx>
55 #include <GeomLib.hxx>
56 #include <GeomProjLib.hxx>
60 #include <gp_Elips.hxx>
66 #include <Precision.hxx>
67 #include <Prs3d_LineAspect.hxx>
68 #include <Prs3d_PointAspect.hxx>
69 #include <Prs3d_Presentation.hxx>
70 #include <StdPrs_Point.hxx>
71 #include <StdPrs_WFShape.hxx>
72 #include <TColStd_Array1OfReal.hxx>
73 #include <TColStd_Array2OfReal.hxx>
75 #include <TopExp_Explorer.hxx>
77 #include <TopoDS_Edge.hxx>
78 #include <TopoDS_Face.hxx>
79 #include <TopoDS_Shape.hxx>
80 #include <TopoDS_Vertex.hxx>
81 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
83 const Standard_Real SquareTolerance = Precision::SquareConfusion();
85 //=======================================================================
88 //=======================================================================
89 gp_Pnt AIS::Nearest(const TopoDS_Shape& ashape, const gp_Pnt& apoint)
91 Standard_Real dist2 = RealLast();
92 Standard_Real curdist2;
93 gp_Pnt result(0.0,0.0,0.0);
94 gp_Pnt curpnt(0.0,0.0,0.0);
95 TopExp_Explorer explo(ashape,TopAbs_VERTEX);
98 curpnt = BRep_Tool::Pnt(TopoDS::Vertex(explo.Current()));
99 curdist2 = apoint.SquareDistance(curpnt);
100 if (curdist2 < dist2)
110 //=======================================================================
112 //purpose : For <thePoint> finds the nearest point on <theLine>.
113 //=======================================================================
114 gp_Pnt AIS::Nearest (const gp_Lin& theLine, const gp_Pnt& thePoint)
116 Handle(Geom_Line) aLine = new Geom_Line (theLine);
118 GeomAPI_ProjectPointOnCurve aPointProj (thePoint, aLine);
119 return aPointProj.Point (1);
122 //=======================================================================
124 //purpose : For the given point finds nearest point on the curve,
125 // return TRUE if found point is belongs to curve
126 // and FALSE otherwise.
127 //=======================================================================
128 Standard_Boolean AIS::Nearest (const Handle(Geom_Curve)& theCurve,
129 const gp_Pnt& thePoint,
130 const gp_Pnt& theFirstPoint,
131 const gp_Pnt& theLastPoint,
132 gp_Pnt& theNearestPoint)
134 GeomAPI_ProjectPointOnCurve aPointProj (thePoint, theCurve);
135 theNearestPoint = theCurve->Value (aPointProj.LowerDistanceParameter());
137 Standard_Real aLength = theFirstPoint.Distance (theLastPoint);
139 if (theNearestPoint.Distance (theFirstPoint) > aLength
140 || theNearestPoint.Distance (theLastPoint) >aLength)
142 return Standard_False;
145 return Standard_True;
148 //=======================================================================
151 //=======================================================================
152 gp_Pnt AIS::Farest( const TopoDS_Shape& aShape, const gp_Pnt& aPoint )
154 Standard_Real MaxDist2 = 0.0e0, curdist2;
155 gp_Pnt Result(0.0,0.0,0.0);
156 gp_Pnt curpnt(0.0,0.0,0.0);
157 TopExp_Explorer Explo( aShape, TopAbs_VERTEX );
158 for (; Explo.More(); Explo.Next())
160 curpnt = BRep_Tool::Pnt( TopoDS::Vertex( Explo.Current() ) );
161 curdist2 = aPoint.SquareDistance( curpnt );
162 if (curdist2 > MaxDist2)
172 //=======================================================================
173 //function : ComputeGeometry
174 //purpose : for line, circle, ellipse.
175 //=======================================================================
176 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theEdge,
177 Handle(Geom_Curve)& theCurve,
181 TopLoc_Location anEdgeLoc;
182 Standard_Real aFirst, aLast;
183 theCurve = BRep_Tool::Curve (theEdge, anEdgeLoc, aFirst, aLast);
184 if (theCurve.IsNull())
186 return Standard_False;
189 if (!anEdgeLoc.IsIdentity())
191 Handle(Geom_Geometry) aGeometry = theCurve->Transformed (anEdgeLoc.Transformation());
192 theCurve = Handle(Geom_Curve)::DownCast (aGeometry);
195 if (theCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
197 theCurve = Handle(Geom_TrimmedCurve)::DownCast (theCurve)->BasisCurve();
200 if (theCurve->IsInstance (STANDARD_TYPE (Geom_Line)))
202 Handle(Geom_Line) aLine = Handle(Geom_Line)::DownCast (theCurve);
203 theFirstPnt = ElCLib::Value (aFirst, aLine->Lin());
204 theLastPnt = ElCLib::Value (aLast, aLine->Lin());
206 else if (theCurve->IsInstance (STANDARD_TYPE (Geom_Circle)))
208 Handle(Geom_Circle) aCirc = Handle(Geom_Circle)::DownCast (theCurve);
210 theFirstPnt = ElCLib::Value (aFirst, aCirc->Circ());
211 theLastPnt = ElCLib::Value (aLast, aCirc->Circ());
213 else if (theCurve->IsInstance (STANDARD_TYPE (Geom_Ellipse)))
215 Handle(Geom_Ellipse) anEllipse = Handle(Geom_Ellipse)::DownCast (theCurve);
216 theFirstPnt = ElCLib::Value (aFirst, anEllipse->Elips());
217 theLastPnt = ElCLib::Value (aLast, anEllipse->Elips());
221 return Standard_False;
224 return Standard_True;
227 //=======================================================================
228 //function : ComputeGeometry
229 //purpose : for line, circle, ellipse.
230 //=======================================================================
231 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theEdge,
232 Handle(Geom_Curve)& theCurve,
235 Standard_Boolean& theIsInfinite)
237 Standard_Real aFirst, aLast;
239 BRepAdaptor_Curve anAdaptor (theEdge);
241 theCurve = Handle(Geom_Curve)::DownCast
242 (anAdaptor.Curve().Curve()->Transformed (anAdaptor.Trsf()));
244 if (theCurve.IsNull())
246 return Standard_False;
249 aFirst = anAdaptor.FirstParameter();
250 aLast = anAdaptor.LastParameter();
252 theIsInfinite = (Precision::IsInfinite (aFirst) || Precision::IsInfinite (aLast));
254 if (theCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
256 theCurve = Handle(Geom_TrimmedCurve)::DownCast (theCurve)->BasisCurve();
261 theFirstPnt = theCurve->Value (aFirst);
262 theLastPnt = theCurve->Value (aLast);
266 theFirstPnt = gp::Origin();
267 theLastPnt = gp::Origin();
270 return Standard_True;
273 //=======================================================================
274 //function : ComputeGeometry
276 //=======================================================================
278 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theEdge,
279 Handle(Geom_Curve)& theCurve,
282 Handle(Geom_Curve)& theExtCurve,
283 Standard_Boolean& theIsInfinite,
284 Standard_Boolean& theIsOnPlane,
285 const Handle(Geom_Plane)& thePlane)
287 if (thePlane.IsNull())
289 return Standard_False;
292 Standard_Real aFirst, aLast;
293 BRepAdaptor_Curve aCurveAdaptor (theEdge);
294 theCurve = Handle(Geom_Curve)::DownCast (aCurveAdaptor.Curve().Curve()->Transformed (aCurveAdaptor.Trsf()));
295 aFirst = aCurveAdaptor.FirstParameter();
296 aLast = aCurveAdaptor.LastParameter();
298 if (theCurve.IsNull())
300 return Standard_False;
303 theExtCurve = theCurve;
304 theIsInfinite = (Precision::IsInfinite (aFirst) || Precision::IsInfinite (aLast));
306 // Checks that the projected curve is not in the plane.
307 theIsOnPlane = Standard_True;
308 if (theExtCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
310 theExtCurve = Handle(Geom_TrimmedCurve)::DownCast (theExtCurve)->BasisCurve();
313 if (theExtCurve->IsInstance (STANDARD_TYPE (Geom_Line)))
315 Handle(Geom_Line) aLine = Handle(Geom_Line)::DownCast (theExtCurve);
316 theIsOnPlane = thePlane->Pln().Contains (aLine->Lin(),
317 Precision::Confusion(),
318 Precision::Angular());
320 else if (theExtCurve->IsInstance (STANDARD_TYPE (Geom_Circle)))
322 Handle(Geom_Circle) aCircle = Handle(Geom_Circle)::DownCast (theExtCurve);
324 gp_Ax3 aCircPos (aCircle->Position());
325 theIsOnPlane = aCircPos.IsCoplanar (thePlane->Pln().Position(),
326 Precision::Confusion(),
327 Precision::Angular());
332 theExtCurve.Nullify();
335 theCurve = GeomProjLib::ProjectOnPlane (theCurve, thePlane,
336 thePlane->Pln().Axis().Direction(),
339 if (theCurve->IsInstance (STANDARD_TYPE (Geom_Line)))
341 Handle(Geom_Line) aLine = Handle(Geom_Line)::DownCast (theCurve);
344 theFirstPnt = ElCLib::Value (aFirst, aLine->Lin());
345 theLastPnt = ElCLib::Value (aLast, aLine->Lin());
348 else if (theCurve->IsInstance (STANDARD_TYPE (Geom_Circle)))
350 Handle(Geom_Circle) aCirc = Handle(Geom_Circle)::DownCast (theCurve);
352 theFirstPnt = ElCLib::Value (aFirst, aCirc->Circ());
353 theLastPnt = ElCLib::Value (aLast, aCirc->Circ());
355 else if (theCurve->IsInstance (STANDARD_TYPE (Geom_Ellipse)))
357 Handle(Geom_Ellipse) anEllipse = Handle(Geom_Ellipse)::DownCast (theCurve);
359 theFirstPnt = ElCLib::Value (aFirst, anEllipse->Elips());
360 theLastPnt = ElCLib::Value (aLast, anEllipse->Elips());
364 return Standard_False;
367 return Standard_True;
370 //=======================================================================
371 //function : ComputeGeometry
373 //=======================================================================
374 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theFirstEdge,
375 const TopoDS_Edge& theSecondEdge,
376 Handle(Geom_Curve)& theFirstCurve,
377 Handle(Geom_Curve)& theSecondCurve,
378 gp_Pnt& theFirstPnt1,
380 gp_Pnt& theFirstPnt2,
382 const Handle(Geom_Plane)& thePlane)
384 if (thePlane.IsNull())
386 return Standard_False;
389 TopLoc_Location aFirstEdgeLoc, aSecondEdgeLoc;
390 Standard_Real aFirst1, aLast1, aFirst2, aLast2;
392 theFirstCurve = BRep_Tool::Curve (theFirstEdge, aFirstEdgeLoc, aFirst1, aLast1);
393 theSecondCurve = BRep_Tool::Curve (theSecondEdge, aSecondEdgeLoc, aFirst2, aLast2);
395 if (theFirstCurve.IsNull())
397 return Standard_False;
400 if (theSecondCurve.IsNull())
402 return Standard_False;
405 if (!aFirstEdgeLoc.IsIdentity())
407 Handle(Geom_Geometry) aGeomGeometry = theFirstCurve->Transformed (aFirstEdgeLoc.Transformation());
408 theFirstCurve = Handle(Geom_Curve)::DownCast (aGeomGeometry);
411 if (!aSecondEdgeLoc.IsIdentity())
413 Handle(Geom_Geometry) aGeomGeometry = theSecondCurve->Transformed (aSecondEdgeLoc.Transformation());
414 theSecondCurve = Handle(Geom_Curve)::DownCast (aGeomGeometry);
417 theFirstCurve = GeomProjLib::ProjectOnPlane (theFirstCurve, thePlane,
418 thePlane->Pln().Axis().Direction(),
422 theSecondCurve = GeomProjLib::ProjectOnPlane (theSecondCurve, thePlane,
423 thePlane->Pln().Axis().Direction(),
427 if (theFirstCurve->IsInstance (STANDARD_TYPE(Geom_TrimmedCurve)))
429 theFirstCurve = Handle(Geom_TrimmedCurve)::DownCast (theFirstCurve)->BasisCurve();
432 if (theSecondCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
434 theSecondCurve = Handle(Geom_TrimmedCurve)::DownCast (theSecondCurve)->BasisCurve();
437 if (theFirstCurve->IsInstance(STANDARD_TYPE(Geom_Line)))
439 Handle(Geom_Line) aLine = Handle(Geom_Line)::DownCast (theFirstCurve);
441 theFirstPnt1 = ElCLib::Value (aFirst1, aLine->Lin());
442 theLastPnt1 = ElCLib::Value (aLast1, aLine->Lin());
444 else if (theFirstCurve->IsInstance(STANDARD_TYPE(Geom_Circle)))
446 Handle(Geom_Circle) aCirc = Handle(Geom_Circle)::DownCast (theFirstCurve);
448 theFirstPnt1 = ElCLib::Value (aFirst1, aCirc->Circ());
449 theLastPnt1 = ElCLib::Value (aLast1, aCirc->Circ());
453 return Standard_False;
456 if (theSecondCurve->IsInstance (STANDARD_TYPE (Geom_Line)))
458 Handle(Geom_Line) aLine = Handle(Geom_Line)::DownCast (theSecondCurve);
460 theFirstPnt2 = ElCLib::Value (aFirst2, aLine->Lin());
461 theLastPnt2 = ElCLib::Value (aLast2, aLine->Lin());
463 else if (theSecondCurve->IsInstance (STANDARD_TYPE (Geom_Circle)))
465 Handle(Geom_Circle) aCirc = Handle(Geom_Circle)::DownCast (theSecondCurve);
467 theFirstPnt2 = ElCLib::Value (aFirst2, aCirc->Circ());
468 theLastPnt2 = ElCLib::Value (aLast2, aCirc->Circ());
472 return Standard_False;
475 return Standard_True;
478 //=======================================================================
479 //function : ComputeGeometry
480 //purpose : Computes the geometry of the 2 edges.
481 //=======================================================================
482 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theFirstEdge,
483 const TopoDS_Edge& theSecondEdge,
484 Handle(Geom_Curve)& theFirstCurve,
485 Handle(Geom_Curve)& theSecondCurve,
486 gp_Pnt& theFirstPnt1,
488 gp_Pnt& theFirstPnt2,
490 Standard_Boolean& theIsInfinite1,
491 Standard_Boolean& theIsInfinite2)
493 theIsInfinite1 = theIsInfinite2 = Standard_False;
495 if (!AIS::ComputeGeometry (theFirstEdge, theFirstCurve,theFirstPnt1, theLastPnt1, theIsInfinite1))
497 return Standard_False;
500 if (!AIS::ComputeGeometry (theSecondEdge, theSecondCurve,theFirstPnt2, theLastPnt2, theIsInfinite2))
502 return Standard_False;
505 if (theIsInfinite1 || theIsInfinite2)
507 if (theFirstCurve->DynamicType() == theSecondCurve->DynamicType())
509 gp_Lin aLin1 = Handle(Geom_Line)::DownCast (theFirstCurve)->Lin();
510 gp_Lin aLin2 = Handle(Geom_Line)::DownCast (theSecondCurve)->Lin();
514 theFirstPnt1 = ElCLib::Value (ElCLib::Parameter (aLin2, theFirstPnt2), aLin1);
515 theLastPnt1 = ElCLib::Value (ElCLib::Parameter (aLin2, theLastPnt2), aLin1);
517 else if (theIsInfinite2)
519 theFirstPnt2 = ElCLib::Value (ElCLib::Parameter (aLin1, theFirstPnt1), aLin2);
520 theLastPnt2 = ElCLib::Value (ElCLib::Parameter (aLin1, theLastPnt1), aLin2);
525 if (theIsInfinite1 && !theIsInfinite2)
527 GeomAPI_ProjectPointOnCurve aProjector (theFirstPnt2, theFirstCurve);
528 theFirstPnt1 = theFirstCurve->Value (aProjector.LowerDistanceParameter ());
530 aProjector.Init (theLastPnt2, theFirstCurve);
531 theLastPnt1 = theFirstCurve->Value (aProjector.LowerDistanceParameter ());
533 else if (!theIsInfinite1 && theIsInfinite2)
535 GeomAPI_ProjectPointOnCurve aProjector (theFirstPnt1, theSecondCurve);
536 theFirstPnt2 = theSecondCurve->Value (aProjector.LowerDistanceParameter ());
538 aProjector.Init (theLastPnt1, theSecondCurve);
539 theLastPnt2 = theSecondCurve->Value (aProjector.LowerDistanceParameter ());
543 return Standard_False;
548 return Standard_True;
551 //=======================================================================
552 //function : ComputeGeometry
553 //purpose : Computes the geometry of the 2 edges in the current wp
554 // and the 'right' geometry of the edges if one doesn't
555 // belong to the current working plane.
556 // There may be only one curve that can't belong to the
557 // current working plane ( attachement constraint)
558 // if the 2 edges belong to the current WP, <WhatProj> = 0
560 // indexExt = 0 2 edges are in the current wp
561 // indexExt = 1 first edge is not in the current wp
562 // indexExt = 2 second edge is not in the current wp
563 // if none of the two edges is in the current wp ,
564 // it returns Standard_False
565 //=======================================================================
566 Standard_Boolean AIS::ComputeGeometry (const TopoDS_Edge& theFirstEdge,
567 const TopoDS_Edge& theSecondEdge,
568 Standard_Integer& theExtIndex,
569 Handle(Geom_Curve)& theFirstCurve,
570 Handle(Geom_Curve)& theSecondCurve,
571 gp_Pnt& theFirstPnt1,
573 gp_Pnt& theFirstPnt2,
575 Handle(Geom_Curve)& theExtCurve,
576 Standard_Boolean& theIsInfinite1,
577 Standard_Boolean& theIsInfinite2,
578 const Handle(Geom_Plane)& thePlane)
580 if (thePlane.IsNull())
582 return Standard_False;
585 theExtCurve.Nullify();
588 Standard_Real aFirst1, aLast1, aFirst2, aLast2;
589 theIsInfinite1 = theIsInfinite2 = Standard_False;
591 BRepAdaptor_Curve aFirstAdaptor (theFirstEdge);
592 BRepAdaptor_Curve aSecondAdaptor (theSecondEdge);
594 theFirstCurve = Handle(Geom_Curve)::DownCast
595 (aFirstAdaptor.Curve().Curve()->Transformed (aFirstAdaptor.Trsf()));
596 theSecondCurve = Handle(Geom_Curve)::DownCast
597 (aSecondAdaptor.Curve().Curve()->Transformed (aSecondAdaptor.Trsf()));
599 if (theFirstCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
601 theFirstCurve = Handle(Geom_TrimmedCurve)::DownCast (theFirstCurve)->BasisCurve();
603 if (theSecondCurve->IsInstance (STANDARD_TYPE (Geom_TrimmedCurve)))
605 theSecondCurve = Handle(Geom_TrimmedCurve)::DownCast (theSecondCurve)->BasisCurve();
608 aFirst1 = aFirstAdaptor.FirstParameter();
609 aLast1 = aFirstAdaptor.LastParameter();
611 aFirst2 = aSecondAdaptor.FirstParameter();
612 aLast2 = aSecondAdaptor.LastParameter();
614 if (theFirstCurve.IsNull() || theSecondCurve.IsNull())
616 return Standard_False;
619 Handle(Geom_Curve) aFirstSaved = theFirstCurve;
620 Handle(Geom_Curve) aSecondSaved = theSecondCurve;
622 // Checks that the projected curve is not in the plane
623 Standard_Boolean isFirstOnPlane,isSecondOnPlane;
625 if ((!ComputeGeomCurve (theFirstCurve, aFirst1, aLast1, theFirstPnt1, theLastPnt1, thePlane, isFirstOnPlane))
626 || (!ComputeGeomCurve( theSecondCurve, aFirst2, aLast2, theFirstPnt2, theLastPnt2, thePlane,isSecondOnPlane)))
628 return Standard_False;
631 if (Precision::IsInfinite (aFirst1) || Precision::IsInfinite (aLast1))
633 theIsInfinite1 = Standard_True;
636 if (Precision::IsInfinite (aFirst2) || Precision::IsInfinite (aLast2))
638 theIsInfinite2 = Standard_True;
641 if (theIsInfinite1 && theIsInfinite2)
646 if (theIsInfinite1 || theIsInfinite2)
648 if (theFirstCurve->DynamicType() == theSecondCurve->DynamicType())
650 gp_Lin aLin1 = Handle(Geom_Line)::DownCast (theFirstCurve)->Lin();
651 gp_Lin aLin2 = Handle(Geom_Line)::DownCast (theSecondCurve)->Lin();
653 if (theExtIndex == 1)
655 theFirstPnt1 = ElCLib::Value (ElCLib::Parameter (aLin2, theFirstPnt2), aLin1);
656 theLastPnt1 = ElCLib::Value (ElCLib::Parameter (aLin2, theLastPnt2), aLin1);
658 else if (theExtIndex == 2)
660 theFirstPnt2 = ElCLib::Value (ElCLib::Parameter (aLin1, theFirstPnt1), aLin2);
661 theLastPnt2 = ElCLib::Value (ElCLib::Parameter (aLin1, theLastPnt1), aLin2);
666 if (isFirstOnPlane && isSecondOnPlane)
668 return Standard_True;
671 if (!isFirstOnPlane && isSecondOnPlane)
672 {// curve 2 only in the plane
674 theExtCurve = aFirstSaved;
676 else if (isFirstOnPlane && !isSecondOnPlane)
677 {// curve 1 only in the plane
679 theExtCurve = aSecondSaved;
683 return Standard_False;
686 return Standard_True;
689 //=======================================================================
690 //function : ComputeGeomCurve
691 //purpose : Checks if aCurve belongs to aPlane; if not, projects aCurve in aPlane
692 // and returns aCurveproj;
694 //=======================================================================
695 Standard_Boolean AIS::ComputeGeomCurve (Handle(Geom_Curve)& aCurve,
696 const Standard_Real first1,
697 const Standard_Real last1,
700 const Handle(Geom_Plane)& aPlane,
701 Standard_Boolean& isOnPlane)
703 isOnPlane = Standard_True;
704 const Standard_Integer NodeNumber = 20;
705 Standard_Real Delta = (last1 - first1) / (NodeNumber - 1);
706 if (Delta <= Precision::PConfusion())
708 Delta = last1 - first1;
711 gp_Pnt CurPnt(0.0, 0.0, 0.0);
712 Standard_Real CurPar = first1;
713 for (Standard_Integer i = 1; i <= NodeNumber; i++)
715 CurPnt = aCurve->Value( CurPar );
716 if (aPlane->Pln().SquareDistance( CurPnt ) > SquareTolerance)
718 isOnPlane = Standard_False;
724 if (!Precision::IsInfinite(first1) && !Precision::IsInfinite(last1))
726 FirstPnt1 = aCurve->Value (first1);
727 LastPnt1 = aCurve->Value (last1);
732 Handle(Geom_Curve) aGeomCurve = GeomProjLib::ProjectOnPlane (aCurve,
734 aPlane->Pln().Axis().Direction(),
737 if (aCurve->IsInstance(STANDARD_TYPE(Geom_TrimmedCurve)))
739 aCurve = Handle(Geom_TrimmedCurve)::DownCast (aCurve)->BasisCurve();
741 if (! Precision::IsInfinite(first1) && ! Precision::IsInfinite(last1))
743 FirstPnt1 = AIS::ProjectPointOnPlane( FirstPnt1, aPlane->Pln() );
744 LastPnt1 = AIS::ProjectPointOnPlane( LastPnt1, aPlane->Pln() );
747 return Standard_True;
750 //=======================================================================
751 //function : ComputeGeometry
752 //purpose : computes the point corresponding to the vertex <aVertex>
753 // in the plane <aPlane>. If the vertex is already in the plane
754 // <isOnPlane>, <isOnPlane> = true.
755 // <point> is the projected vertex in the plane.
756 //=======================================================================
757 Standard_Boolean AIS::ComputeGeometry(const TopoDS_Vertex& aVertex,
759 const Handle(Geom_Plane)& aPlane,
760 Standard_Boolean& isOnPlane)
762 point = BRep_Tool::Pnt(aVertex);
763 isOnPlane = aPlane->Pln().Contains(point, Precision::Confusion());
765 point = AIS::ProjectPointOnPlane( point, aPlane->Pln() );
767 return Standard_True;
770 //=======================================================================
771 //function : GetPlaneFromFace
773 // Returns type of surface which can be Plane or OtherSurface
774 //=======================================================================
775 Standard_Boolean AIS::GetPlaneFromFace(const TopoDS_Face& aFace,
777 Handle( Geom_Surface )& aSurf,
778 AIS_KindOfSurface & aSurfType,
779 Standard_Real & Offset)
782 Standard_Boolean Result = Standard_False;
783 BRepAdaptor_Surface surf1( aFace );
784 Handle( Adaptor3d_HSurface ) surf2;
785 Standard_Boolean isOffset = Standard_False;
787 if (surf1.GetType() == GeomAbs_OffsetSurface)
789 // Extracting Basis Surface
790 surf2 = surf1.BasisSurface();
791 isOffset = Standard_True;
794 surf2 = new BRepAdaptor_HSurface( surf1 );
796 aSurf = surf1.Surface().Surface();
797 // aSurf->Transform(surf1.Trsf()) ;
798 aSurf = Handle( Geom_Surface )::DownCast( aSurf->Transformed( surf1.Trsf() ) );
800 if (surf2->GetType() == GeomAbs_Plane)
802 aPlane = surf2->Plane();
803 aSurfType = AIS_KOS_Plane;
805 Result = Standard_True;
808 else if (surf2->GetType() == GeomAbs_SurfaceOfExtrusion)
810 Handle( Adaptor3d_HCurve ) BasisCurve = surf2->BasisCurve();
811 gp_Dir ExtrusionDir = surf2->Direction();
812 if (BasisCurve->GetType() == GeomAbs_Line)
814 gp_Lin BasisLine = BasisCurve->Line();
815 gp_Dir LineDir = BasisLine.Direction();
816 gp_Pnt LinePos = BasisLine.Location();
817 gp_Pln thePlane( LinePos, LineDir ^ ExtrusionDir);
819 aSurfType = AIS_KOS_Plane;
821 Result = Standard_True;
825 if (Result == Standard_True && isOffset)
827 aSurf = (Handle( Geom_OffsetSurface )::DownCast( aSurf ))->Surface();
828 aPlane = (Handle( Geom_Plane )::DownCast( aSurf ))->Pln();
831 if (Result == Standard_False)
835 Handle( Standard_Type ) TheType = aSurf->DynamicType();
836 if (TheType == STANDARD_TYPE(Geom_CylindricalSurface) ||
837 TheType == STANDARD_TYPE(Geom_ConicalSurface) ||
838 TheType == STANDARD_TYPE(Geom_SphericalSurface) ||
839 TheType == STANDARD_TYPE(Geom_ToroidalSurface))
841 aSurf = (Handle( Geom_OffsetSurface )::DownCast( aSurf ))->Surface();
846 Offset = (Handle( Geom_OffsetSurface )::DownCast( aSurf ))->Offset();
847 aSurf = (Handle( Geom_OffsetSurface )::DownCast( aSurf ))->BasisSurface();
850 Handle( Standard_Type ) TheType = aSurf->DynamicType();
851 if (TheType == STANDARD_TYPE(Geom_CylindricalSurface))
852 aSurfType = AIS_KOS_Cylinder;
853 else if (TheType == STANDARD_TYPE(Geom_ConicalSurface))
854 aSurfType = AIS_KOS_Cone;
855 else if (TheType == STANDARD_TYPE(Geom_SphericalSurface))
856 aSurfType = AIS_KOS_Sphere;
857 else if (TheType == STANDARD_TYPE(Geom_ToroidalSurface))
858 aSurfType = AIS_KOS_Torus;
859 else if (TheType == STANDARD_TYPE(Geom_SurfaceOfRevolution))
860 aSurfType = AIS_KOS_Revolution;
861 else if (TheType == STANDARD_TYPE(Geom_SurfaceOfLinearExtrusion))
862 aSurfType = AIS_KOS_Extrusion;
864 aSurfType = AIS_KOS_OtherSurface;
870 //=======================================================================
871 //function : ProjectPointOnPlane
873 //=======================================================================
875 gp_Pnt AIS::ProjectPointOnPlane( const gp_Pnt & aPoint, const gp_Pln & aPlane )
877 gp_Vec aVec( aPlane.Location(), aPoint );
878 gp_Vec Normal = aPlane.Axis().Direction();
879 Normal = (aVec * Normal) * Normal;
881 return ( aPoint.Translated( -Normal ) );
884 //=======================================================================
885 //function : ProjectPointOnLine
887 //=======================================================================
889 gp_Pnt AIS::ProjectPointOnLine( const gp_Pnt & aPoint, const gp_Lin & aLine )
891 gp_XYZ LinLoc = aLine.Location().XYZ();
892 gp_XYZ LinDir = aLine.Direction().XYZ();
893 Standard_Real Parameter = (aPoint.XYZ() - LinLoc) * LinDir;
894 gp_Pnt Result( LinLoc + Parameter * LinDir );
898 //=======================================================================
899 //function : InitFaceLength
901 //=======================================================================
902 void AIS::InitFaceLength (const TopoDS_Face& aFace,
904 Handle(Geom_Surface) & aSurface,
905 AIS_KindOfSurface & aSurfaceType,
906 Standard_Real & anOffset)
908 AIS::GetPlaneFromFace( aFace, aPlane, aSurface, aSurfaceType, anOffset );
910 if (Abs( anOffset ) > Precision::Confusion())
912 aSurface = new Geom_OffsetSurface( aSurface, anOffset );
918 //=======================================================================
919 //function : InitAngleBetweenPlanarFaces
921 //=======================================================================
922 Standard_Boolean AIS::InitAngleBetweenPlanarFaces (const TopoDS_Face& theFirstFace,
923 const TopoDS_Face& theSecondFace,
925 gp_Pnt & theFirstAttach,
926 gp_Pnt & theSecondAttach,
927 const Standard_Boolean theIsFirstPointSet)
929 Handle(Geom_Plane) aFirstPlane = Handle(Geom_Plane)::DownCast (BRep_Tool::Surface (theFirstFace));
930 Handle(Geom_Plane) aSecondPlane = Handle(Geom_Plane)::DownCast (BRep_Tool::Surface (theSecondFace));
932 GeomAPI_IntSS aPlaneIntersector (aFirstPlane, aSecondPlane, Precision::Confusion());
934 // Fails if two planes haven't only one intersection line.
935 if (!aPlaneIntersector.IsDone())
937 return Standard_False;
940 if (aPlaneIntersector.NbLines() != 1)
942 return Standard_False;
945 // Get intersect line.
946 Handle(Geom_Curve) anIntersectCurve = aPlaneIntersector.Line (1);
948 Handle(Geom_Line) anIntersectLine = Handle(Geom_Line)::DownCast (anIntersectCurve);
950 if (anIntersectLine.IsNull())
952 return Standard_False;
955 gp_Lin anIntersectLin = anIntersectLine->Lin();
957 gp_Pnt aFirstCenter, aSecondCenter;
958 Standard_Real anU1Min, anU1Max, aV1Min, aV1Max;
959 Standard_Real anU2Min, anU2Max, aV2Min, aV2Max;
961 BRepTools::UVBounds (theFirstFace, anU1Min, anU1Max, aV1Min, aV1Max);
962 BRepTools::UVBounds (theSecondFace, anU2Min, anU2Max, aV2Min, aV2Max);
964 // Get first and second attach.
965 if (theIsFirstPointSet)
967 GeomAPI_ProjectPointOnSurf aProjector (theFirstAttach, aFirstPlane);
968 if (!aProjector.IsDone())
970 return Standard_False;
973 aFirstCenter = aProjector.Point (1);
977 aFirstCenter = aFirstPlane->Value ((anU1Min + anU1Max) * 0.5, (aV1Min + aV1Max) * 0.5);
980 aSecondCenter = aSecondPlane->Value ((anU2Min + anU2Max) * 0.5, (aV2Min + aV2Max) * 0.5);
982 GeomAPI_ProjectPointOnCurve aProj (aFirstCenter, anIntersectCurve);
983 theCenter = aProj.NearestPoint();
985 gp_Vec aFirstNormal = anIntersectLin.Direction() ^ aFirstPlane->Pln().Axis().Direction();
986 if (aFirstNormal * gp_Vec (theCenter, aFirstCenter) < 0.0)
988 aFirstNormal.Reverse();
990 theFirstAttach = theCenter.Translated (aFirstNormal);
992 gp_Vec aSecondNormal = anIntersectLin.Direction() ^ aSecondPlane->Pln().Axis().Direction();
993 if (aSecondNormal * gp_Vec (theCenter, aSecondCenter) < 0.0)
995 aSecondNormal.Reverse();
997 theSecondAttach = theCenter.Translated (aSecondNormal);
999 return Standard_True;
1002 //=======================================================================
1003 //function : InitAngleBetweenCurvilinearFaces
1005 //=======================================================================
1006 Standard_Boolean AIS::InitAngleBetweenCurvilinearFaces (const TopoDS_Face& theFirstFace,
1007 const TopoDS_Face& theSecondFace,
1008 const AIS_KindOfSurface theFirstSurfType,
1009 const AIS_KindOfSurface theSecondSurfType,
1011 gp_Pnt& theFirstAttach,
1012 gp_Pnt& theSecondAttach,
1013 const Standard_Boolean theIsFirstPointSet)
1015 Handle(Geom_Surface) aFirstSurf = BRep_Tool::Surface (theFirstFace);
1016 Handle(Geom_Surface) aSecondSurf = BRep_Tool::Surface (theSecondFace);
1018 // Find intersection curve between two surfaces.
1019 GeomAPI_IntSS aSurfaceIntersector (aFirstSurf, aSecondSurf, Precision::Confusion());
1021 // Fails if two planes haven't only one intersection line.
1022 if (!aSurfaceIntersector.IsDone())
1024 return Standard_False;
1027 if (aSurfaceIntersector.NbLines() != 1)
1029 return Standard_False;
1032 // Get intersect line.
1033 Handle(Geom_Curve) anIntersectCurve = aSurfaceIntersector.Line (1);
1035 Handle(Geom_Line) aFirstLine, aSecondLine;
1036 Standard_Real aFirstU = 0.0;
1037 Standard_Real aFirstV = 0.0;
1039 if (theIsFirstPointSet)
1041 GeomAPI_ProjectPointOnSurf aProjector (theFirstAttach, aFirstSurf);
1042 if (!aProjector.IsDone())
1044 return Standard_False;
1047 theFirstAttach = aProjector.Point (1);
1051 theFirstAttach = aFirstSurf->Value (aFirstU, aFirstV);
1054 aFirstLine = Handle(Geom_Line)::DownCast (aFirstSurf->UIso (aFirstU));
1056 if (theSecondSurfType == AIS_KOS_Cylinder)
1058 Handle(Geom_CylindricalSurface) aCylinder = Handle(Geom_CylindricalSurface)::DownCast (aSecondSurf);
1060 Standard_Real aSecondU = aCylinder->Cylinder().XAxis().Direction().Angle(
1061 gce_MakeDir (ProjectPointOnLine (theFirstAttach,
1062 gp_Lin (aCylinder->Cylinder().Axis())),
1065 aSecondLine = Handle(Geom_Line)::DownCast (aCylinder->UIso (aSecondU));
1067 else if (theSecondSurfType == AIS_KOS_Cone)
1069 Handle(Geom_ConicalSurface) aCone = Handle(Geom_ConicalSurface)::DownCast (aSecondSurf);
1071 gp_Dir anXdirection = aCone->Cone().XAxis().Direction();
1073 gp_Dir aToFirstAttach = gce_MakeDir (ProjectPointOnLine (theFirstAttach,
1074 gp_Lin (aCone->Cone().Axis())),
1077 Standard_Real aSecondU = anXdirection.Angle (aToFirstAttach);
1080 if (!anXdirection.IsEqual (aToFirstAttach, Precision::Angular()) &&
1081 !anXdirection.IsOpposite (aToFirstAttach, Precision::Angular()) &&
1082 (anXdirection ^ aToFirstAttach) * aCone->Cone().Axis().Direction() < 0.0)
1084 aSecondU = 2*M_PI - aSecondU;
1086 aSecondLine = Handle( Geom_Line )::DownCast (aCone->UIso(aSecondU));
1090 return Standard_False;
1093 // If angle can be computed between two lines.
1094 if (!(aFirstLine->Lin().Direction().IsEqual (aSecondLine->Lin().Direction(), Precision::Angular() )) &&
1095 !(aFirstLine->Lin().Direction().IsOpposite (aSecondLine->Lin().Direction(), Precision::Angular())))
1097 GeomAPI_ExtremaCurveCurve anIntersector (aFirstLine, aSecondLine);
1098 anIntersector.Points (1, theCenter, theCenter);
1100 // Move theFirstAttach on aFirstLine if it is on theCenter.
1101 if (theCenter.SquareDistance(theFirstAttach ) <= SquareTolerance)
1103 gp_Vec aDir (aFirstLine->Lin().Direction());
1104 theFirstAttach = theCenter.Translated (aDir);
1106 // theFirstAttach should be on theFirstSurf.
1107 Standard_Real anU, aV;
1108 if (theFirstSurfType == AIS_KOS_Cylinder)
1110 ElSLib::Parameters ((Handle(Geom_CylindricalSurface)::DownCast (aFirstSurf))->Cylinder(),
1111 theFirstAttach, anU, aV);
1113 theFirstAttach = ElSLib::Value (aFirstU, aV,
1114 (Handle( Geom_CylindricalSurface )::DownCast (aFirstSurf))->Cylinder() );
1116 else if (theFirstSurfType == AIS_KOS_Cone)
1118 ElSLib::Parameters ((Handle(Geom_ConicalSurface)::DownCast (aFirstSurf))->Cone(),
1119 theFirstAttach, anU, aV);
1120 theFirstAttach = ElSLib::Value (aFirstU, aV,
1121 (Handle(Geom_ConicalSurface)::DownCast (aFirstSurf))->Cone());
1125 return Standard_False;
1129 // Find theSecondAttach
1130 GeomAPI_ProjectPointOnSurf aProjector (theFirstAttach, aSecondSurf);
1131 if (!aProjector.IsDone())
1133 return Standard_False;
1135 Standard_Real anU, aV;
1136 aProjector.LowerDistanceParameters (anU, aV);
1137 theSecondAttach = aSecondSurf->Value (anU, aV);
1139 else // aFirstLine and aSecondLine are coincident
1141 gp_Vec aDir (aFirstLine->Lin().Direction());
1142 theFirstAttach = theCenter.Translated (aDir);
1143 theSecondAttach = theCenter.Translated (-aDir);
1145 return Standard_True;
1148 //=======================================================================
1149 //function : ComputeLengthBetweenCurvilinearFaces
1151 //=======================================================================
1152 void AIS::InitLengthBetweenCurvilinearFaces (const TopoDS_Face& theFirstFace,
1153 const TopoDS_Face& theSecondFace,
1154 Handle(Geom_Surface)& theFirstSurf,
1155 Handle(Geom_Surface)& theSecondSurf,
1156 gp_Pnt& theFirstAttach,
1157 gp_Pnt& theSecondAttach,
1158 gp_Dir& theDirOnPlane)
1160 GeomAPI_ProjectPointOnSurf aProjector;
1161 Standard_Real aPU, aPV;
1163 TopExp_Explorer anExplorer (theFirstFace, TopAbs_VERTEX);
1165 theFirstAttach = BRep_Tool::Pnt (TopoDS::Vertex (anExplorer.Current()));
1166 aProjector.Init (theFirstAttach, theFirstSurf);
1168 theFirstAttach = aProjector.NearestPoint();
1169 aProjector.LowerDistanceParameters (aPU, aPV);
1172 theFirstSurf->D1 (aPU, aPV, theFirstAttach, aD1U, aD1V);
1174 if (aD1U.SquareMagnitude() <= SquareTolerance || aD1V.SquareMagnitude() <= SquareTolerance)
1176 theFirstAttach = AIS::Farest (theFirstFace, theFirstAttach);
1177 aProjector.Init (theFirstAttach, theFirstSurf);
1178 aProjector.LowerDistanceParameters (aPU, aPV);
1179 theFirstSurf->D1 (aPU, aPV, theFirstAttach, aD1U, aD1V);
1185 theDirOnPlane = gp_Dir (aD1U);
1187 gp_Dir aFirstSurfN = gp_Dir (aD1U ^ aD1V);
1189 aProjector.Init (theFirstAttach, theSecondSurf);
1191 Standard_Integer aBestPointIndex = 0;
1192 Standard_Real aMinDist = RealLast();
1195 for (Standard_Integer aPointIt = 1; aPointIt <= aProjector.NbPoints(); aPointIt++)
1197 aProjector.Parameters (aPointIt, aPU, aPV);
1199 theSecondSurf->D1 (aPU, aPV, theSecondAttach, aD1U, aD1V);
1201 aLocalDir = aD1U.SquareMagnitude() <= SquareTolerance || aD1V.SquareMagnitude() <= SquareTolerance
1202 ? gp_Dir (gp_Vec (theFirstAttach, aProjector.Point (aPointIt)))
1203 : gp_Dir (aD1U ^ aD1V);
1205 if (aFirstSurfN.IsParallel (aLocalDir, Precision::Angular()) && aProjector.Distance (aPointIt) < aMinDist)
1207 aBestPointIndex = aPointIt;
1208 aMinDist = aProjector.Distance (aPointIt);
1212 if (aBestPointIndex == 0)
1214 theSecondAttach = theFirstAttach;
1218 theSecondAttach = aProjector.Point (aBestPointIndex);
1219 aProjector.Parameters (aBestPointIndex, aPU, aPV);
1221 // Now there is projection of FirstAttach onto SecondSurf in aProjector
1222 BRepTopAdaptor_FClass2d aClassifier (theSecondFace, Precision::Confusion());
1224 TopAbs_State aState =
1225 aClassifier.Perform (gp_Pnt2d (aPU, aPV), theSecondSurf->IsUPeriodic() || theSecondSurf->IsVPeriodic());
1227 if (aState == TopAbs_OUT || aState == TopAbs_UNKNOWN)
1229 theSecondAttach = AIS::Nearest (theSecondFace, theSecondAttach);
1234 gp_Pnt AIS::TranslatePointToBound( const gp_Pnt & aPoint, const gp_Dir & aDir, const Bnd_Box & aBndBox )
1236 if (aBndBox.IsOut( aPoint ))
1240 gp_Pnt Result(0.0,0.0,0.0);
1241 TColStd_Array2OfReal Bound( 1, 3, 1, 2 );
1242 TColStd_Array1OfReal Origin( 1, 3 );
1243 TColStd_Array1OfReal Dir( 1, 3 );
1246 aBndBox.Get( Bound(1,1), Bound(2,1), Bound(3,1), Bound(1,2), Bound(2,2), Bound(3,2) );
1247 aPoint.Coord( Origin(1), Origin(2), Origin(3) );
1248 aDir.Coord( Dir(1), Dir(2), Dir(3) );
1250 Bnd_Box EnlargedBox = aBndBox;
1251 EnlargedBox.Enlarge( aBndBox.GetGap() + Precision::Confusion() );
1253 Standard_Boolean IsFound = Standard_False;
1254 for (Standard_Integer i = 1; i <= 3; i++)
1256 if (Abs( Dir( i ) ) <= gp::Resolution())
1258 for (Standard_Integer j = 1; j <= 2; j++)
1260 t = (Bound( i, j ) - Origin( i )) / Dir( i );
1263 Result = aPoint.Translated( gp_Vec( aDir ) * t );
1264 if (! EnlargedBox.IsOut( Result ))
1266 IsFound = Standard_True;
1277 //=======================================================================
1278 //function : InDomain
1280 //=======================================================================
1282 Standard_Boolean AIS::InDomain(const Standard_Real fpar,
1283 const Standard_Real lpar,
1284 const Standard_Real para)
1288 return ((para >= fpar) && (para <= lpar));
1289 else { // fpar > lpar
1290 Standard_Real delta = 2*M_PI-fpar;
1291 Standard_Real lp, par, fp;
1294 while(lp > 2*M_PI) lp-=2*M_PI;
1295 while(par > 2*M_PI) par-=2*M_PI;
1297 return ((par >= fp) && (par <= lp));
1301 if (para >= (fpar+2*M_PI)) return Standard_True;
1302 if (para <= lpar) return Standard_True;
1303 return Standard_False;
1306 //=======================================================================
1307 //function : DistanceFromApex
1308 //purpose : calculates parametric length arc of ellipse
1309 //=======================================================================
1311 Standard_Real AIS::DistanceFromApex(const gp_Elips & elips,
1312 const gp_Pnt & Apex,
1313 const Standard_Real par)
1316 Standard_Real parApex = ElCLib::Parameter ( elips, Apex );
1317 if(parApex == 0.0 || parApex == M_PI)
1319 if(parApex == 0.0) //pos Apex
1320 dist = (par < M_PI) ? par : (2*M_PI - par);
1322 dist = (par < M_PI) ? ( M_PI - par) : ( par - M_PI );
1326 if(parApex == M_PI / 2) //pos Apex
1328 if(par <= parApex + M_PI && par > parApex) // 3/2*M_PI < par < M_PI/2
1329 dist = par - parApex;
1332 if(par > parApex + M_PI) // 3/2*M_PI < par < 2*M_PI
1333 dist = 2*M_PI - par + parApex;
1335 dist = parApex - par;
1338 else //neg Apex == 3/2*M_PI
1340 if(par <= parApex && par >= M_PI/2) // M_PI/2 < par < 3/2*M_PI
1341 dist = parApex - par;
1344 if(par > parApex) // 3/2*M_PI < par < 2*M_PI
1345 dist = par - parApex;
1347 dist = par + M_PI/2; // 0 < par < M_PI/2
1354 //=======================================================================
1355 //function : NearestApex
1357 //=======================================================================
1359 gp_Pnt AIS::NearestApex(const gp_Elips & elips,
1360 const gp_Pnt & pApex,
1361 const gp_Pnt & nApex,
1362 const Standard_Real fpara,
1363 const Standard_Real lpara,
1364 Standard_Boolean & IsInDomain)
1366 Standard_Real parP, parN;
1367 gp_Pnt EndOfArrow(0.0,0.0,0.0);
1368 IsInDomain = Standard_True;
1369 parP = ElCLib::Parameter ( elips, pApex );
1370 if(InDomain(fpara, lpara, parP)) EndOfArrow = pApex;
1373 parN = ElCLib::Parameter ( elips, nApex );
1374 if(InDomain(fpara, lpara, parN)) EndOfArrow = nApex;
1376 IsInDomain = Standard_False;
1377 Standard_Real posd = Min(DistanceFromApex (elips,pApex, fpara),
1378 DistanceFromApex (elips,pApex, lpara));
1379 Standard_Real negd = Min(DistanceFromApex (elips,nApex, fpara),
1380 DistanceFromApex (elips,nApex, lpara));
1390 //=======================================================================
1391 //function : ComputeProjEdgePresentation
1393 //=======================================================================
1395 void AIS::ComputeProjEdgePresentation (const Handle(Prs3d_Presentation)& aPresentation,
1396 const Handle(Prs3d_Drawer)& aDrawer,
1397 const TopoDS_Edge& anEdge,
1398 const Handle(Geom_Curve)& ProjCurve,
1399 const gp_Pnt& FirstP,
1400 const gp_Pnt& LastP,
1401 const Quantity_NameOfColor aColor,
1402 const Standard_Real aWidth,
1403 const Aspect_TypeOfLine aProjTOL,
1404 const Aspect_TypeOfLine aCallTOL)
1406 if (!aDrawer->HasOwnWireAspect()){
1407 aDrawer->SetWireAspect(new Prs3d_LineAspect(aColor,aProjTOL,2.));}
1410 // const Handle(Prs3d_LineAspect)& li = aDrawer->WireAspect();
1411 Handle(Prs3d_LineAspect) li = aDrawer->WireAspect();
1413 li->SetColor(aColor);
1414 li->SetTypeOfLine(aProjTOL);
1415 li->SetWidth(aWidth);
1418 Standard_Real pf, pl;
1419 TopLoc_Location loc;
1420 Handle(Geom_Curve) curve;
1421 Standard_Boolean isInfinite;
1422 curve = BRep_Tool::Curve(anEdge,loc,pf,pl);
1423 isInfinite = (Precision::IsInfinite(pf) || Precision::IsInfinite(pl));
1427 // Calculate presentation of the edge
1428 if (ProjCurve->IsInstance(STANDARD_TYPE(Geom_Line)) ) {
1430 // Handle(Geom_Line) gl (Handle(Geom_Line)::DownCast (ProjCurve));
1431 Handle(Geom_Line) gl = Handle(Geom_Line)::DownCast (ProjCurve);
1434 pf = ElCLib::Parameter(gl->Lin(),FirstP);
1435 pl = ElCLib::Parameter(gl->Lin(),LastP);
1436 BRepBuilderAPI_MakeEdge MakEd(gl->Lin(), pf, pl);
1440 BRepBuilderAPI_MakeEdge MakEd(gl->Lin());
1444 else if (ProjCurve->IsInstance(STANDARD_TYPE(Geom_Circle)) ) {
1446 // Handle(Geom_Circle) gc (Handle(Geom_Circle)::DownCast (ProjCurve));
1447 Handle(Geom_Circle) gc = Handle(Geom_Circle)::DownCast (ProjCurve);
1449 pf = ElCLib::Parameter(gc->Circ(),FirstP);
1450 pl = ElCLib::Parameter(gc->Circ(),LastP);
1451 BRepBuilderAPI_MakeEdge MakEd(gc->Circ(),pf, pl);
1454 StdPrs_WFShape::Add (aPresentation, E, aDrawer);
1456 //Calculate the presentation of line connections
1457 aDrawer->WireAspect()->SetTypeOfLine(aCallTOL);
1459 gp_Pnt ppf(0.0,0.0,0.0), ppl(0.0,0.0,0.0);
1460 ppf = BRep_Tool::Pnt( TopExp::FirstVertex(TopoDS::Edge(anEdge)));
1461 ppl = BRep_Tool::Pnt( TopExp::LastVertex(TopoDS::Edge(anEdge)));
1464 if (FirstP.SquareDistance (ppf) > SquareTolerance)
1466 BRepBuilderAPI_MakeEdge MakEd1 (FirstP, ppf);
1467 StdPrs_WFShape::Add (aPresentation, MakEd1.Edge(), aDrawer);
1471 BRepBuilderAPI_MakeVertex MakVert1 (FirstP);
1472 StdPrs_WFShape::Add (aPresentation, MakVert1.Vertex(), aDrawer);
1474 if (LastP.SquareDistance (ppl) > SquareTolerance)
1476 BRepBuilderAPI_MakeEdge MakEd2 (LastP, ppl);
1477 StdPrs_WFShape::Add (aPresentation, MakEd2.Edge(), aDrawer);
1481 BRepBuilderAPI_MakeVertex MakVert2 (LastP);
1482 StdPrs_WFShape::Add (aPresentation, MakVert2.Vertex(), aDrawer);
1485 BRepBuilderAPI_MakeEdge MakEd1 (FirstP, ppf);
1486 StdPrs_WFShape::Add (aPresentation, MakEd1.Edge(), aDrawer);
1487 BRepBuilderAPI_MakeEdge MakEd2 (LastP, ppl);
1488 StdPrs_WFShape::Add (aPresentation, MakEd2.Edge(), aDrawer);
1493 //=======================================================================
1494 //function : ComputeProjVertexPresentation
1496 //=======================================================================
1498 void AIS::ComputeProjVertexPresentation (const Handle( Prs3d_Presentation )& aPresentation,
1499 const Handle( Prs3d_Drawer )& aDrawer,
1500 const TopoDS_Vertex& aVertex,
1501 const gp_Pnt& ProjPoint,
1502 const Quantity_NameOfColor aColor,
1503 const Standard_Real aWidth,
1504 const Aspect_TypeOfMarker aProjTOM,
1505 const Aspect_TypeOfLine aCallTOL)
1507 if (!aDrawer->HasOwnPointAspect()){
1508 aDrawer->SetPointAspect(new Prs3d_PointAspect(aProjTOM, aColor,1));}
1511 // const Handle(Prs3d_PointAspect)& pa = aDrawer->PointAspect();
1512 Handle(Prs3d_PointAspect) pa = aDrawer->PointAspect();
1514 pa->SetColor(aColor);
1515 pa->SetTypeOfMarker(aProjTOM);
1518 // calculate the projection
1519 StdPrs_Point::Add(aPresentation, new Geom_CartesianPoint(ProjPoint), aDrawer);
1521 if (!aDrawer->HasOwnWireAspect()){
1522 aDrawer->SetWireAspect(new Prs3d_LineAspect(aColor,aCallTOL,2.));}
1525 // const Handle(Prs3d_LineAspect)& li = aDrawer->WireAspect();
1526 Handle(Prs3d_LineAspect) li = aDrawer->WireAspect();
1528 li->SetColor(aColor);
1529 li->SetTypeOfLine(aCallTOL);
1530 li->SetWidth(aWidth);
1533 // If the points are not mixed...
1534 if (!ProjPoint.IsEqual (BRep_Tool::Pnt (aVertex), Precision::Confusion()))
1536 // calculate the lines of recall
1537 BRepBuilderAPI_MakeEdge MakEd (ProjPoint, BRep_Tool::Pnt (aVertex));
1538 StdPrs_WFShape::Add (aPresentation, MakEd.Edge(), aDrawer);