1 // Copyright (C) 2007-2011 CEA/DEN, EDF R&D, OPEN CASCADE
3 // Copyright (C) 2003-2007 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 // Lesser General Public License for more details.
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
22 // File : GEOMAlgo_Tools3D.cxx
23 // Author : Peter KURNEV
25 #include <GEOMAlgo_Tools3D.ixx>
27 #include <NMTTools_ListOfCoupleOfShape.hxx>
28 #include <NMTTools_ListIteratorOfListOfCoupleOfShape.hxx>
29 #include <NMTTools_CoupleOfShape.hxx>
31 #include <Basics_OCCTVersion.hxx>
33 #include <Precision.hxx>
38 #include <gp_Pnt2d.hxx>
41 #include <gp_Dir2d.hxx>
43 #include <Geom_Curve.hxx>
44 #include <Geom_Surface.hxx>
46 #include <Geom2d_Curve.hxx>
47 #include <Geom2d_TrimmedCurve.hxx>
48 #include <Geom2d_Line.hxx>
50 #include <Geom2dHatch_Intersector.hxx>
51 #include <Geom2dHatch_Hatcher.hxx>
53 #include <HatchGen_Domain.hxx>
55 #include <GeomAPI_ProjectPointOnSurf.hxx>
57 #include <TopAbs_ShapeEnum.hxx>
58 #include <TopAbs_State.hxx>
60 #include <TopLoc_Location.hxx>
63 #include <TopoDS_Edge.hxx>
64 #include <TopoDS_CompSolid.hxx>
65 #include <TopoDS_Wire.hxx>
66 #include <TopoDS_Compound.hxx>
67 #include <TopoDS_Face.hxx>
68 #include <TopoDS_Vertex.hxx>
69 #include <TopoDS_Solid.hxx>
70 #include <TopoDS_Shell.hxx>
71 #include <TopoDS_Iterator.hxx>
74 #include <TopExp_Explorer.hxx>
76 #include <BRep_Builder.hxx>
77 #include <BRep_Tool.hxx>
79 #include <TopTools_ListOfShape.hxx>
80 #include <TopTools_IndexedMapOfShape.hxx>
81 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
82 #include <TopTools_IndexedMapOfShape.hxx>
83 #include <TopTools_ListIteratorOfListOfShape.hxx>
84 #include <TopTools_MapOfShape.hxx>
86 #include <BRepClass3d_SolidClassifier.hxx>
87 #include <BRepTools.hxx>
89 #include <IntTools_Context.hxx>
90 #include <IntTools_Tools.hxx>
92 #include <BOPTools_Tools3D.hxx>
93 #include <BOPTools_Tools2D.hxx>
94 #include <BOPTools_Tools.hxx>
96 #include <TopTools_DataMapOfShapeListOfShape.hxx>
97 #include <TopTools_DataMapOfShapeListOfShape.hxx>
98 #include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx>
99 #include <TopTools_MapOfShape.hxx>
100 #include <TopTools_MapIteratorOfMapOfShape.hxx>
102 #include <GeomAdaptor_Surface.hxx>
106 Standard_Boolean FindFacePairs (const TopoDS_Edge& ,
107 const TopTools_ListOfShape& ,
108 NMTTools_ListOfCoupleOfShape& );
112 Standard_Real AngleWithRef(const gp_Dir& ,
117 void GetApproxNormalToFaceOnEdge (const TopoDS_Edge& aE,
118 const TopoDS_Face& aF,
122 #if OCC_VERSION_LARGE > 0x06050200
123 const Handle(IntTools_Context)& aCtx);
125 IntTools_Context& aCtx);
128 //=======================================================================
129 //function : IsInternalFace
131 //=======================================================================
132 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
133 const TopoDS_Solid& theSolid,
134 const TopTools_IndexedDataMapOfShapeListOfShape& theMEF,
135 const Standard_Real theTol,
136 #if OCC_VERSION_LARGE > 0x06050200
137 const Handle(IntTools_Context)& theContext)
139 IntTools_Context& theContext)
142 Standard_Boolean bRet;
143 Standard_Integer aNbF;
145 TopExp_Explorer aExp;
146 TopTools_ListIteratorOfListOfShape aItF;
150 // 1 Try to find an edge from theFace in theMEF
151 aExp.Init(theFace, TopAbs_EDGE);
152 for(; aExp.More(); aExp.Next()) {
153 const TopoDS_Edge& aE=TopoDS::Edge(aExp.Current());
154 if (!theMEF.Contains(aE)) {
158 const TopTools_ListOfShape& aLF=theMEF.FindFromKey(aE);
161 return bRet; // it can not be so
164 // aE is internal edge on aLF.First()
165 const TopoDS_Face& aF1=TopoDS::Face(aLF.First());
166 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aF1, aF1, theContext);
170 const TopoDS_Face& aF1=TopoDS::Face(aLF.First());
171 const TopoDS_Face& aF2=TopoDS::Face(aLF.Last());
173 if (aF2.IsSame(aF1) && BRep_Tool::IsClosed(aE, aF1)) {
174 // treat as it was for 1 face
175 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aF1, aF2, theContext);
180 return bRet; // it can not be so
182 else { // aNbF=2,4,6,8,...
183 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aLF, theContext);
186 }//for(; aExp.More(); aExp.Next()) {
188 //========================================
189 // 2. Classify face using classifier
192 TopTools_IndexedMapOfShape aBounds;
194 aState=GEOMAlgo_Tools3D::ComputeState(theFace, theSolid, theTol, aBounds, theContext);
195 bRet=(aState==TopAbs_IN);
199 //=======================================================================
200 //function : IsInternalFace
202 //=======================================================================
203 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
204 const TopoDS_Edge& theEdge,
205 const TopTools_ListOfShape& theLF,
206 #if OCC_VERSION_LARGE > 0x06050200
207 const Handle(IntTools_Context)& theContext)
209 IntTools_Context& theContext)
212 Standard_Boolean bRet;
213 Standard_Boolean aNbF;
219 const TopoDS_Face& aF1=TopoDS::Face(theLF.First());
220 const TopoDS_Face& aF2=TopoDS::Face(theLF.Last());
221 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, theEdge, aF1, aF2, theContext);
226 NMTTools_ListOfCoupleOfShape aLCFF;
227 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
229 FindFacePairs(theEdge, theLF, aLCFF);
231 aIt.Initialize(aLCFF);
232 for (; aIt.More(); aIt.Next()) {
233 const NMTTools_CoupleOfShape& aCSFF=aIt.Value();
235 const TopoDS_Face& aF1=TopoDS::Face(aCSFF.Shape1());
236 const TopoDS_Face& aF2=TopoDS::Face(aCSFF.Shape2());
237 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, theEdge, aF1, aF2, theContext);
245 //=======================================================================
246 //function : IsInternalFace
248 //=======================================================================
249 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
250 const TopoDS_Edge& theEdge,
251 const TopoDS_Face& theFace1,
252 const TopoDS_Face& theFace2,
253 #if OCC_VERSION_LARGE > 0x06050200
254 const Handle(IntTools_Context)& theContext)
256 IntTools_Context& theContext)
259 Standard_Boolean bRet;
260 Standard_Real aT1, aT2, aT, aDt2D, aDt2Dx;
261 Standard_Real aA12, aA1x, aTwoPI;
262 gp_Pnt aPx, aPF, aPF1, aPF2;
263 gp_Pnt2d aP2D, aPF2D;
265 TopoDS_Edge aE1, aE2;
266 Handle(Geom_Curve)aC3D;
268 aC3D =BRep_Tool::Curve(theEdge, aT1, aT2);
269 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
273 aDt2D=BOPTools_Tools3D::MinStepIn2d();
275 BOPTools_Tools3D::PointNearEdge (theEdge, theFace, aT, aDt2Dx, aPF2D, aPF);
278 GEOMAlgo_Tools3D::GetEdgeOnFace(theEdge, theFace1, aE1);
279 if (aE1.Orientation()==TopAbs_INTERNAL) {
281 aE1.Orientation(TopAbs_FORWARD);
282 aE2.Orientation(TopAbs_REVERSED);
284 else if (theFace1==theFace2) {
286 aE1.Orientation(TopAbs_FORWARD);
287 aE2.Orientation(TopAbs_REVERSED);
290 GEOMAlgo_Tools3D::GetEdgeOnFace(theEdge, theFace2, aE2);
296 GetApproxNormalToFaceOnEdge (aE1, theFace1, aT, aPF1, aDNF1, theContext);
297 GetApproxNormalToFaceOnEdge (aE2, theFace2, aT, aPF2, aDNF2, theContext);
300 gp_Vec aVBF (aPx, aPF );
301 gp_Vec aVBF1(aPx, aPF1);
302 gp_Vec aVBF2(aPx, aPF2);
310 aA12=AngleWithRef(aDBF1, aDBF2, aDTF1);
315 aA1x=AngleWithRef(aDBF1, aDBF , aDTF1);
321 bRet=!bRet; //TopAbs_IN;
326 //=======================================================================
327 //function : GetFaceOff
329 //=======================================================================
330 void GEOMAlgo_Tools3D::GetFaceOff(const TopoDS_Edge& theE1,
331 const TopoDS_Face& theF1,
332 const NMTTools_ListOfCoupleOfShape& theLCSOff,
333 TopoDS_Face& theFOff)
335 Standard_Real aT, aT1, aT2, aAngle, aTwoPI, aAngleMin;
339 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
343 BRep_Tool::Range(theE1, aT1, aT2);
344 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
346 BOPTools_Tools2D::EdgeTangent(theE1, aT, aVTgt);
347 gp_Dir aDTtgt(aVTgt);
350 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge(theE1, theF1, aT, aPn1, aDN1);
352 aIt.Initialize(theLCSOff);
353 for (; aIt.More(); aIt.Next()) {
354 const NMTTools_CoupleOfShape& aCS=aIt.Value();
355 const TopoDS_Edge& aE2=TopoDS::Edge(aCS.Shape1());
356 const TopoDS_Face& aF2=TopoDS::Face(aCS.Shape2());
361 else if (aF2.IsSame(theF1)) {
365 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge (aE2, aF2, aT, aPn2, aDN2);
368 aAngle=AngleWithRef(aDN1, aDN2, aDTtgt);
370 aAngle=aTwoPI+aAngle;
374 if (aAngle<aAngleMin){
380 //=======================================================================
381 //function : GetEdgeOnFace
383 //=======================================================================
384 Standard_Boolean GEOMAlgo_Tools3D::GetEdgeOnFace(const TopoDS_Edge& theE1,
385 const TopoDS_Face& theF2,
388 Standard_Boolean bFound;
389 TopoDS_Iterator aItF, aItW;
391 bFound=Standard_False;
393 aItF.Initialize(theF2);
394 for (; aItF.More(); aItF.Next()) {
395 const TopoDS_Shape& aW=aItF.Value();
397 for (; aItW.More(); aItW.Next()) {
398 const TopoDS_Shape& aE=aItW.Value();
399 if (aE.IsSame(theE1)) {
400 theE2=TopoDS::Edge(aE);
408 //=======================================================================
409 //function : GetEdgeOff
411 //=======================================================================
412 Standard_Boolean GEOMAlgo_Tools3D::GetEdgeOff (const TopoDS_Edge& theE1,
413 const TopoDS_Face& theF2,
417 Standard_Boolean bFound;
418 TopAbs_Orientation aOr1, aOr1C, aOr2;
419 TopExp_Explorer anExp;
421 bFound=Standard_False;
422 aOr1=theE1.Orientation();
423 aOr1C=TopAbs::Reverse(aOr1);
425 anExp.Init(theF2, TopAbs_EDGE);
426 for (; anExp.More(); anExp.Next()) {
427 const TopoDS_Edge& aEF2=TopoDS::Edge(anExp.Current());
428 if (aEF2.IsSame(theE1)) {
429 aOr2=aEF2.Orientation();
439 //=======================================================================
440 // function: ComputeState
442 //=======================================================================
443 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Face& theF,
444 const TopoDS_Solid& theRef,
445 const Standard_Real theTol,
446 const TopTools_IndexedMapOfShape& theBounds,
447 #if OCC_VERSION_LARGE > 0x06050200
448 const Handle(IntTools_Context)& theCtx)
450 IntTools_Context& theCtx)
454 TopExp_Explorer aExp;
459 aState=TopAbs_UNKNOWN;
461 aExp.Init(theF, TopAbs_EDGE);
462 for (; aExp.More(); aExp.Next()) {
463 const TopoDS_Edge& aSE=TopoDS::Edge(aExp.Current());
464 if (BRep_Tool::Degenerated(aSE)) {
468 if (!theBounds.Contains(aSE)) {
469 const TopoDS_Edge& aE=TopoDS::Edge(aSE);
470 aState= GEOMAlgo_Tools3D::ComputeState(aE, theRef, theTol, theCtx);
474 aE1=TopoDS::Edge(aSE);
477 // !!<- process edges that are all on theRef
479 BOPTools_Tools3D::PointNearEdge(aE1, theF, aP2D, aP3D);
480 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
485 //=======================================================================
486 // function: ComputeStateByOnePoint
488 //=======================================================================
489 TopAbs_State GEOMAlgo_Tools3D::ComputeStateByOnePoint(const TopoDS_Shape& theS,
490 const TopoDS_Solid& theRef,
491 const Standard_Real theTol,
492 #if OCC_VERSION_LARGE > 0x06050200
493 const Handle(IntTools_Context)& theCtx)
495 IntTools_Context& theCtx)
499 TopAbs_ShapeEnum aType;
501 aState=TopAbs_UNKNOWN;
502 aType=theS.ShapeType();
503 if (aType==TopAbs_VERTEX) {
504 const TopoDS_Vertex& aV=TopoDS::Vertex(theS);
505 aState=GEOMAlgo_Tools3D::ComputeState(aV, theRef, theTol, theCtx);
507 else if (aType==TopAbs_EDGE) {
508 const TopoDS_Edge& aE=TopoDS::Edge(theS);
509 aState=GEOMAlgo_Tools3D::ComputeState(aE, theRef, theTol, theCtx);
513 //=======================================================================
514 // function: ComputeState
516 //=======================================================================
517 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Vertex& theV,
518 const TopoDS_Solid& theRef,
519 const Standard_Real theTol,
520 #if OCC_VERSION_LARGE > 0x06050200
521 const Handle(IntTools_Context)& theCtx)
523 IntTools_Context& theCtx)
529 aP3D=BRep_Tool::Pnt(theV);
530 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
533 //=======================================================================
534 // function: ComputeState
536 //=======================================================================
537 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Edge& theE,
538 const TopoDS_Solid& theRef,
539 const Standard_Real theTol,
540 #if OCC_VERSION_LARGE > 0x06050200
541 const Handle(IntTools_Context)& theCtx)
543 IntTools_Context& theCtx)
546 Standard_Real aT1, aT2, aT = 0.;
548 Handle(Geom_Curve) aC3D;
551 aC3D = BRep_Tool::Curve(theE, aT1, aT2);
554 //it means that we are in degenerated edge
555 const TopoDS_Vertex& aV = TopExp::FirstVertex(theE);
557 return TopAbs_UNKNOWN;
559 aP3D=BRep_Tool::Pnt(aV);
562 Standard_Boolean bF2Inf, bL2Inf;
563 Standard_Real dT=10.;
565 bF2Inf = Precision::IsNegativeInfinite(aT1);
566 bL2Inf = Precision::IsPositiveInfinite(aT2);
568 if (bF2Inf && !bL2Inf) {
571 else if (!bF2Inf && bL2Inf) {
574 else if (bF2Inf && bL2Inf) {
578 aT=IntTools_Tools::IntermediatePoint(aT1, aT2);
583 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
587 //=======================================================================
588 // function: ComputeState
590 //=======================================================================
591 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const gp_Pnt& theP,
592 const TopoDS_Solid& theRef,
593 const Standard_Real theTol,
594 #if OCC_VERSION_LARGE > 0x06050200
595 const Handle(IntTools_Context)& theCtx)
597 IntTools_Context& theCtx)
602 #if OCC_VERSION_LARGE > 0x06050200
603 BRepClass3d_SolidClassifier& aSC=theCtx->SolidClassifier(theRef);
605 BRepClass3d_SolidClassifier& aSC=theCtx.SolidClassifier(theRef);
607 aSC.Perform(theP, theTol);
613 //=======================================================================
614 // function: IsSplitToReverse
616 //=======================================================================
617 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse (const TopoDS_Shape& theSp,
618 const TopoDS_Shape& theSr,
619 #if OCC_VERSION_LARGE > 0x06050200
620 const Handle(IntTools_Context)& theCtx)
622 IntTools_Context& theCtx)
625 Standard_Boolean bRet;
626 TopAbs_ShapeEnum aType;
630 aType=theSp.ShapeType();
633 const TopoDS_Edge& aESp=TopoDS::Edge(theSp);
634 const TopoDS_Edge& aESr=TopoDS::Edge(theSr);
635 bRet=GEOMAlgo_Tools3D::IsSplitToReverse(aESp, aESr, theCtx);
640 const TopoDS_Face& aFSp=TopoDS::Face(theSp);
641 const TopoDS_Face& aFSr=TopoDS::Face(theSr);
642 bRet=GEOMAlgo_Tools3D::IsSplitToReverse(aFSp, aFSr, theCtx);
651 //=======================================================================
652 //function :IsSplitToReverse
654 //=======================================================================
655 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse (const TopoDS_Face& theFSp,
656 const TopoDS_Face& theFSr,
657 #if OCC_VERSION_LARGE > 0x06050200
658 const Handle(IntTools_Context)& theContext)
660 IntTools_Context& theContext)
663 Standard_Boolean bRet, bFound, bInFace;
664 Standard_Real aT1, aT2, aT, aU, aV, aScPr;
668 Handle(Geom_Surface) aSr, aSp;
669 TopAbs_Orientation aOrSr, aOrSp;
670 TopExp_Explorer anExp;
675 aSr=BRep_Tool::Surface(theFSr);
676 aSp=BRep_Tool::Surface(theFSp);
678 aOrSr=theFSr.Orientation();
679 aOrSp=theFSp.Orientation();
684 bFound=Standard_False;
685 anExp.Init(theFSp, TopAbs_EDGE);
686 for (; anExp.More(); anExp.Next()) {
687 aESp=TopoDS::Edge(anExp.Current());
688 if (!BRep_Tool::Degenerated(aESp)) {
689 if (!BRep_Tool::IsClosed(aESp, theFSp)) {
696 //modified by NIZNHY-PKV Tue Nov 22 10:50:30 2011f
698 Standard_Boolean bFlag;
699 Standard_Integer iErr;
702 iErr=GEOMAlgo_Tools3D::PntInFace(theFSp, aPFSp, aP2DFSp);
707 aP2DFSp.Coord(aU, aV);
708 bFlag=BOPTools_Tools3D::GetNormalToSurface(aSp, aU, aV, aDNFSp);
714 BRep_Tool::Range(aESp, aT1, aT2);
715 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
716 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge(aESp, theFSp, aT, aPFSp, aDNFSp);
723 BRep_Tool::Range(aESp, aT1, aT2);
724 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
725 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge(aESp, theFSp, aT, aPFSp, aDNFSp);
727 //modified by NIZNHY-PKV Tue Nov 22 10:50:37 2011t
729 // Parts of theContext.ComputeVS(..)
730 #if OCC_VERSION_LARGE > 0x06050200
731 GeomAPI_ProjectPointOnSurf& aProjector=theContext->ProjPS(theFSr);
733 GeomAPI_ProjectPointOnSurf& aProjector=theContext.ProjPS(theFSr);
735 aProjector.Perform(aPFSp);
736 if (!aProjector.IsDone()) {
740 aProjector.LowerDistanceParameters(aU, aV);
741 gp_Pnt2d aP2D(aU, aV);
742 #if OCC_VERSION_LARGE > 0x06050200
743 bInFace=theContext->IsPointInFace (theFSr, aP2D);
745 bInFace=theContext.IsPointInFace (theFSr, aP2D);
751 aSr->D1(aU, aV, aPFSr, aD1U, aD1V);
754 gp_Dir aDNFSr=aDD1U^aDD1V;
755 if (theFSr.Orientation()==TopAbs_REVERSED){
764 //=======================================================================
765 //function :IsSplitToReverse
767 //=======================================================================
768 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse (const TopoDS_Edge& theSplit,
769 const TopoDS_Edge& theEdge,
770 #if OCC_VERSION_LARGE > 0x06050200
771 const Handle(IntTools_Context)& theContext)
773 IntTools_Context& theContext)
776 Standard_Boolean bRet, aFlag, bIsDegenerated;
777 Standard_Real aTE, aTS, aScPr, aTa, aTb, aT1, aT2;
778 TopAbs_Orientation aOrSr, aOrSp;
779 Handle(Geom_Curve) aCEdge, aCSplit;
785 bIsDegenerated=(BRep_Tool::Degenerated(theSplit) ||
786 BRep_Tool::Degenerated(theEdge));
787 if (bIsDegenerated) {
791 aCEdge =BRep_Tool::Curve(theEdge , aT1, aT2);
792 aCSplit=BRep_Tool::Curve(theSplit, aTa, aTb);
794 if (aCEdge==aCSplit) {
795 aOrSr=theEdge.Orientation();
796 aOrSp=theSplit.Orientation();
801 aTS=BOPTools_Tools2D::IntermediatePoint(aTa, aTb);
802 aCSplit->D0(aTS, aP);
803 aFlag=BOPTools_Tools2D::EdgeTangent(theSplit, aTS, aVS);
806 #if OCC_VERSION_LARGE > 0x06050200
807 aFlag=theContext->ProjectPointOnEdge(aP, theEdge, aTE);
809 aFlag=theContext.ProjectPointOnEdge(aP, theEdge, aTE);
811 aFlag=BOPTools_Tools2D::EdgeTangent(theEdge, aTE, aVE);
820 //=======================================================================
823 //=======================================================================
824 Standard_Integer GEOMAlgo_Tools3D::Sense (const TopoDS_Face& theF1,
825 const TopoDS_Face& theF2)
827 Standard_Integer iSense=0;
829 TopoDS_Edge aE1, aE2;
830 TopExp_Explorer anExp;
832 anExp.Init(theF1, TopAbs_EDGE);
833 for (; anExp.More(); anExp.Next()) {
834 aE1=TopoDS::Edge(anExp.Current());
835 if (!BRep_Tool::Degenerated(aE1)) {
836 if (!BRep_Tool::IsClosed(aE1, theF1)) {
842 anExp.Init(theF2, TopAbs_EDGE);
843 for (; anExp.More(); anExp.Next()) {
844 aE2=TopoDS::Edge(anExp.Current());
845 if (!BRep_Tool::Degenerated(aE2)) {
846 if (!BRep_Tool::IsClosed(aE2, theF2)) {
847 if (aE2.IsSame(aE1)) {
859 BOPTools_Tools3D::GetNormalToFaceOnEdge(aE1, theF1, aDNF1);
860 BOPTools_Tools3D::GetNormalToFaceOnEdge(aE2, theF2, aDNF2);
862 iSense=BOPTools_Tools3D::SenseFlag(aDNF1, aDNF2);
866 //=======================================================================
867 // function: CopyFace
869 //=======================================================================
870 void GEOMAlgo_Tools3D::CopyFace (const TopoDS_Face& theF1,
874 TopLoc_Location aLoc;
875 TopAbs_Orientation aOr;
879 Handle(Geom_Surface) aSurface=BRep_Tool::Surface(theF1, aLoc);
880 aTol=BRep_Tool::Tolerance(theF1);
881 aOr=theF1.Orientation();
883 aBB.MakeFace (theF2, aSurface, aLoc, aTol);
884 theF2.Orientation(aOr);
886 aIt.Initialize(theF1);
887 for (; aIt.More(); aIt.Next()) {
888 const TopoDS_Shape& aW=aIt.Value();
892 //=======================================================================
893 // function: MakeContainer
895 //=======================================================================
896 void GEOMAlgo_Tools3D::MakeContainer(const TopAbs_ShapeEnum theType,
902 case TopAbs_COMPOUND:{
904 aBB.MakeCompound(aC);
909 case TopAbs_COMPSOLID:{
910 TopoDS_CompSolid aCS;
911 aBB.MakeCompSolid(aCS);
918 aBB.MakeSolid(aSolid);
926 aBB.MakeShell(aShell);
942 //=======================================================================
943 // function: MakeConnexityBlock.
945 //=======================================================================
946 void GEOMAlgo_Tools3D::MakeConnexityBlock (const TopTools_ListOfShape& theLFIn,
947 const TopTools_IndexedMapOfShape& theMEAvoid,
948 TopTools_ListOfShape& theLCB)
950 Standard_Integer aNbF, aNbAdd1;
951 TopExp_Explorer aExp;
952 TopTools_IndexedDataMapOfShapeListOfShape aMEF;
953 TopTools_MapIteratorOfMapOfShape aItM, aItM1;
954 TopTools_MapOfShape aMCB, aMAdd, aMAdd1;
955 TopTools_ListIteratorOfListOfShape aIt;
958 aNbF=theLFIn.Extent();
959 aIt.Initialize(theLFIn);
960 for (; aIt.More(); aIt.Next()) {
961 const TopoDS_Shape& aF=aIt.Value();
962 TopExp::MapShapesAndAncestors(aF, TopAbs_EDGE, TopAbs_FACE, aMEF);
966 const TopoDS_Shape& aF1=theLFIn.First();
971 aItM.Initialize(aMAdd);
972 for (; aItM.More(); aItM.Next()) {
973 const TopoDS_Shape& aF=aItM.Key();
976 aExp.Init(aF, TopAbs_EDGE);
977 for (; aExp.More(); aExp.Next()) {
978 const TopoDS_Shape& aE=aExp.Current();
979 if (theMEAvoid.Contains(aE)){
983 const TopTools_ListOfShape& aLF=aMEF.FindFromKey(aE);
985 for (; aIt.More(); aIt.Next()) {
986 const TopoDS_Shape& aFx=aIt.Value();
987 if (aFx.IsSame(aF)) {
990 if (aMCB.Contains(aFx)) {
995 }//for (; aExp.More(); aExp.Next()){
997 }// for (; aItM.More(); aItM.Next()) {
999 aNbAdd1=aMAdd1.Extent();
1005 aItM1.Initialize(aMAdd1);
1006 for (; aItM1.More(); aItM1.Next()) {
1007 const TopoDS_Shape& aFAdd=aItM1.Key();
1015 aItM.Initialize(aMCB);
1016 for (; aItM.More(); aItM.Next()) {
1017 const TopoDS_Shape& aF=aItM.Key();
1021 //=======================================================================
1022 //function : FindFacePairs
1024 //=======================================================================
1025 Standard_Boolean FindFacePairs (const TopoDS_Edge& theE,
1026 const TopTools_ListOfShape& thLF,
1027 NMTTools_ListOfCoupleOfShape& theLCFF)
1029 Standard_Boolean bFound;
1030 Standard_Integer i, aNbCEF;
1031 TopAbs_Orientation aOr, aOrC;
1032 TopTools_MapOfShape aMFP;
1033 TopoDS_Face aF1, aF2;
1034 TopoDS_Edge aEL, aE1;
1035 TopTools_ListIteratorOfListOfShape aItLF;
1036 NMTTools_CoupleOfShape aCEF, aCFF;
1037 NMTTools_ListOfCoupleOfShape aLCEF, aLCEFx;
1038 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
1040 bFound=Standard_True;
1043 aItLF.Initialize(thLF);
1044 for (; aItLF.More(); aItLF.Next()) {
1045 const TopoDS_Face& aFL=TopoDS::Face(aItLF.Value());
1047 bFound=GEOMAlgo_Tools3D::GetEdgeOnFace(theE, aFL, aEL);
1049 return bFound; // it can not be so
1052 aCEF.SetShape1(aEL);
1053 aCEF.SetShape2(aFL);
1057 aNbCEF=aLCEF.Extent();
1062 aIt.Initialize(aLCEF);
1063 for (i=0; aIt.More(); aIt.Next(), ++i) {
1064 const NMTTools_CoupleOfShape& aCSx=aIt.Value();
1065 const TopoDS_Shape& aEx=aCSx.Shape1();
1066 const TopoDS_Shape& aFx=aCSx.Shape2();
1068 aOr=aEx.Orientation();
1071 aOrC=TopAbs::Reverse(aOr);
1072 aE1=TopoDS::Edge(aEx);
1073 aF1=TopoDS::Face(aFx);
1079 aLCEFx.Append(aCSx);
1085 GEOMAlgo_Tools3D::GetFaceOff(aE1, aF1, aLCEFx, aF2);
1087 aCFF.SetShape1(aF1);
1088 aCFF.SetShape2(aF2);
1089 theLCFF.Append(aCFF);
1098 aIt.Initialize(aLCEFx);
1099 for (; aIt.More(); aIt.Next()) {
1100 const NMTTools_CoupleOfShape& aCSx=aIt.Value();
1101 const TopoDS_Shape& aFx=aCSx.Shape2();
1102 if (!aMFP.Contains(aFx)) {
1107 aNbCEF=aLCEF.Extent();
1113 //=======================================================================
1114 //function : AngleWithRef
1116 //=======================================================================
1117 Standard_Real AngleWithRef(const gp_Dir& theD1,
1118 const gp_Dir& theD2,
1119 const gp_Dir& theDRef)
1121 Standard_Real aCosinus, aSinus, aBeta, aHalfPI, aScPr;
1126 const gp_XYZ& aXYZ1=theD1.XYZ();
1127 const gp_XYZ& aXYZ2=theD2.XYZ();
1128 aXYZ=aXYZ1.Crossed(aXYZ2);
1129 aSinus=aXYZ.Modulus();
1130 aCosinus=theD1*theD2;
1134 aBeta=aHalfPI*(1.-aCosinus);
1137 aBeta=2.*M_PI-aHalfPI*(3.+aCosinus);
1140 aScPr=aXYZ.Dot(theDRef.XYZ());
1146 //=======================================================================
1147 //function : GetApproxNormalToFaceOnEdge
1149 //=======================================================================
1150 void GetApproxNormalToFaceOnEdge (const TopoDS_Edge& aEx,
1151 const TopoDS_Face& aFx,
1155 #if OCC_VERSION_LARGE > 0x06050200
1156 const Handle(IntTools_Context)& aCtx)
1158 IntTools_Context& aCtx)
1161 Standard_Boolean bReverse;
1162 Standard_Real aT1, aT2, dT, aU, aV;
1163 gp_Dir aDTT, aDNFT, aDBT;
1165 Handle(Geom_Curve) aC3D;
1166 Handle(Geom_Surface) aS;
1167 GeomAdaptor_Surface aGAS;
1168 GeomAbs_SurfaceType aTS;
1172 bReverse=Standard_False;
1175 if (aF.Orientation()==TopAbs_REVERSED){
1179 aF.Orientation(TopAbs_FORWARD);
1183 aC3D =BRep_Tool::Curve(aE, aT1, aT2);
1187 BOPTools_Tools3D::GetNormalToFaceOnEdge (aE, aF, aT, aDNFT);
1190 BOPTools_Tools3D::GetTangentToEdge(aE, aT, aDTT);
1195 dT=BOPTools_Tools3D::MinStepIn2d();//~1.e-5;
1197 //----------------------------------------------
1199 aS=BRep_Tool::Surface(aF);
1202 if (aTS==GeomAbs_BSplineSurface ||
1203 aTS==GeomAbs_BezierSurface ||
1204 aTS==GeomAbs_Plane){
1205 Standard_Real aTolEx, aTolFx, aTol, dUR, dVR, dR;
1207 aTolEx=BRep_Tool::Tolerance(aEx);
1208 aTolFx=BRep_Tool::Tolerance(aFx);
1209 aTol=2.*aTolEx+aTolFx;
1210 dUR=aGAS.UResolution(aTol);
1211 dVR=aGAS.VResolution(aTol);
1212 dR=(dUR>dVR)? dUR : dVR;
1217 else if (GeomAbs_Torus ||
1218 aTS==GeomAbs_Cylinder){
1219 Standard_Real aTolEx, aTolFx, aTol;
1221 aTolEx=BRep_Tool::Tolerance(aEx);
1222 aTolFx=BRep_Tool::Tolerance(aFx);
1223 aTol=2.*aTolEx+aTolFx;
1229 //----------------------------------------------
1231 aPFx.SetXYZ(aPFT.XYZ()+dT*aDBT.XYZ());
1239 #if OCC_VERSION_LARGE > 0x06050200
1240 GeomAPI_ProjectPointOnSurf& aProjector=aCtx->ProjPS(aF);
1242 GeomAPI_ProjectPointOnSurf& aProjector=aCtx.ProjPS(aF);
1245 aProjector.Perform(aPFx);
1246 if(aProjector.IsDone()) {
1247 aProjector.LowerDistanceParameters (aU, aV);
1248 aS->D0(aU, aV, aPF);
1249 BOPTools_Tools3D::GetNormalToSurface (aS, aU, aV, aDNF);
1256 //modified by NIZNHY-PKV Tue Nov 22 10:36:59 2011f
1257 //=======================================================================
1258 //function : PntInFace
1260 //=======================================================================
1261 Standard_Integer GEOMAlgo_Tools3D::PntInFace(const TopoDS_Face& aF,
1265 Standard_Boolean bIsDone, bHasFirstPoint, bHasSecondPoint;
1266 Standard_Integer iErr, aIx, aNbDomains, i;
1267 Standard_Real aUMin, aUMax, aVMin, aVMax;
1268 Standard_Real aVx, aUx, aV1, aV2, aU1, aU2, aEpsT;
1269 Standard_Real aTotArcIntr, aTolTangfIntr, aTolHatch2D, aTolHatch3D;
1270 gp_Dir2d aD2D (0., 1.);
1273 Handle(Geom2d_Curve) aC2D;
1274 Handle(Geom2d_TrimmedCurve) aCT2D;
1275 Handle(Geom2d_Line) aL2D;
1276 Handle(Geom_Surface) aS;
1277 TopAbs_Orientation aOrE;
1279 TopExp_Explorer aExp;
1284 aTolTangfIntr=1.e-10;
1286 Geom2dHatch_Intersector aIntr(aTotArcIntr, aTolTangfIntr);
1287 Geom2dHatch_Hatcher aHatcher(aIntr,
1288 aTolHatch2D, aTolHatch3D,
1289 Standard_True, Standard_False);
1295 aFF.Orientation (TopAbs_FORWARD);
1297 aS=BRep_Tool::Surface(aFF);
1298 BRepTools::UVBounds(aFF, aUMin, aUMax, aVMin, aVMax);
1301 aExp.Init (aFF, TopAbs_EDGE);
1302 for (; aExp.More() ; aExp.Next()) {
1303 const TopoDS_Edge& aE=*((TopoDS_Edge*)&aExp.Current());
1304 aOrE=aE.Orientation();
1306 aC2D=BRep_Tool::CurveOnSurface (aE, aFF, aU1, aU2);
1307 if (aC2D.IsNull() ) {
1311 if (fabs(aU1-aU2) < aEpsT) {
1316 aCT2D=new Geom2d_TrimmedCurve(aC2D, aU1, aU2);
1317 aHatcher.AddElement(aCT2D, aOrE);
1318 }// for (; aExp.More() ; aExp.Next()) {
1321 aUx=IntTools_Tools::IntermediatePoint(aUMin, aUMax);
1322 aP2D.SetCoord(aUx, 0.);
1323 aL2D=new Geom2d_Line (aP2D, aD2D);
1324 Geom2dAdaptor_Curve aHCur(aL2D);
1326 aIx=aHatcher.AddHatching(aHCur) ;
1330 bIsDone=aHatcher.TrimDone(aIx);
1336 aHatcher.ComputeDomains(aIx);
1337 bIsDone=aHatcher.IsDone(aIx);
1344 aNbDomains=aHatcher.NbDomains(aIx);
1345 for (i=1; i<=aNbDomains; ++i) {
1346 const HatchGen_Domain& aDomain=aHatcher.Domain (aIx, i) ;
1347 bHasFirstPoint=aDomain.HasFirstPoint();
1348 if (!bHasFirstPoint) {
1353 aV1=aDomain.FirstPoint().Parameter();
1355 bHasSecondPoint=aDomain.HasSecondPoint();
1356 if (!bHasSecondPoint) {
1361 aV2=aDomain.SecondPoint().Parameter();
1363 aVx=IntTools_Tools::IntermediatePoint(aV1, aV2);
1368 aS->D0(aUx, aVx, aPx);
1370 theP2D.SetCoord(aUx, aVx);
1375 //modified by NIZNHY-PKV Tue Nov 22 10:37:01 2011t