1 // Copyright (C) 2007-2008 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
24 // Author: Peter KURNEV
26 #include <GEOMAlgo_Tools3D.ixx>
28 #include <Precision.hxx>
33 #include <gp_Pnt2d.hxx>
37 #include <Geom_Curve.hxx>
38 #include <Geom_Surface.hxx>
39 #include <Geom2d_Curve.hxx>
40 #include <GeomAPI_ProjectPointOnSurf.hxx>
42 #include <TopAbs_ShapeEnum.hxx>
43 #include <TopAbs_State.hxx>
45 #include <TopLoc_Location.hxx>
48 #include <TopoDS_Edge.hxx>
49 #include <TopoDS_CompSolid.hxx>
50 #include <TopoDS_Wire.hxx>
51 #include <TopoDS_Compound.hxx>
52 #include <TopoDS_Face.hxx>
53 #include <TopoDS_Vertex.hxx>
54 #include <TopoDS_Solid.hxx>
55 #include <TopoDS_Shell.hxx>
56 #include <TopoDS_Iterator.hxx>
59 #include <TopExp_Explorer.hxx>
61 #include <BRep_Builder.hxx>
62 #include <BRep_Tool.hxx>
64 #include <TopTools_ListOfShape.hxx>
65 #include <TopTools_IndexedMapOfShape.hxx>
66 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
67 #include <TopTools_IndexedMapOfShape.hxx>
68 #include <TopTools_ListIteratorOfListOfShape.hxx>
69 #include <TopTools_MapOfShape.hxx>
71 #include <BRepClass3d_SolidClassifier.hxx>
73 #include <IntTools_Context.hxx>
74 #include <IntTools_Tools.hxx>
76 #include <BOPTools_Tools3D.hxx>
77 #include <BOPTools_Tools2D.hxx>
78 #include <BOPTools_Tools.hxx>
80 #include <NMTTools_ListOfCoupleOfShape.hxx>
81 #include <NMTTools_ListIteratorOfListOfCoupleOfShape.hxx>
82 #include <NMTTools_CoupleOfShape.hxx>
83 #include <TopTools_DataMapOfShapeListOfShape.hxx>
84 #include <TopTools_DataMapOfShapeListOfShape.hxx>
85 #include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx>
86 #include <TopTools_MapOfShape.hxx>
87 #include <TopTools_MapIteratorOfMapOfShape.hxx>
89 #include <GeomAdaptor_Surface.hxx>
94 Standard_Boolean FindFacePairs (const TopoDS_Edge& ,
95 const TopTools_ListOfShape& ,
96 NMTTools_ListOfCoupleOfShape& );
100 Standard_Real AngleWithRef(const gp_Dir& ,
105 void GetApproxNormalToFaceOnEdge (const TopoDS_Edge& aE,
106 const TopoDS_Face& aF,
110 IntTools_Context& aCtx);
112 //=======================================================================
113 //function : IsInternalFace
115 //=======================================================================
116 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
117 const TopoDS_Solid& theSolid,
118 const TopTools_IndexedDataMapOfShapeListOfShape& theMEF,
119 const Standard_Real theTol,
120 IntTools_Context& theContext)
122 Standard_Boolean bRet;
123 Standard_Integer aNbF;
125 TopExp_Explorer aExp;
126 TopTools_ListIteratorOfListOfShape aItF;
130 // 1 Try to find an edge from theFace in theMEF
131 aExp.Init(theFace, TopAbs_EDGE);
132 for(; aExp.More(); aExp.Next()) {
133 const TopoDS_Edge& aE=TopoDS::Edge(aExp.Current());
134 if (!theMEF.Contains(aE)) {
138 const TopTools_ListOfShape& aLF=theMEF.FindFromKey(aE);
141 return bRet; // it can not be so
144 // aE is internal edge on aLF.First()
145 const TopoDS_Face& aF1=TopoDS::Face(aLF.First());
146 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aF1, aF1, theContext);
150 const TopoDS_Face& aF1=TopoDS::Face(aLF.First());
151 const TopoDS_Face& aF2=TopoDS::Face(aLF.Last());
153 if (aF2.IsSame(aF1) && BRep_Tool::IsClosed(aE, aF1)) {
154 // treat as it was for 1 face
155 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aF1, aF2, theContext);
160 return bRet; // it can not be so
162 else { // aNbF=2,4,6,8,...
163 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, aE, aLF, theContext);
166 }//for(; aExp.More(); aExp.Next()) {
168 //========================================
169 // 2. Classify face using classifier
172 TopTools_IndexedMapOfShape aBounds;
174 aState=GEOMAlgo_Tools3D::ComputeState(theFace, theSolid, theTol, aBounds, theContext);
175 bRet=(aState==TopAbs_IN);
179 //=======================================================================
180 //function : IsInternalFace
182 //=======================================================================
183 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
184 const TopoDS_Edge& theEdge,
185 const TopTools_ListOfShape& theLF,
186 IntTools_Context& theContext)
188 Standard_Boolean bRet;
189 Standard_Boolean aNbF;
195 const TopoDS_Face& aF1=TopoDS::Face(theLF.First());
196 const TopoDS_Face& aF2=TopoDS::Face(theLF.Last());
197 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, theEdge, aF1, aF2, theContext);
202 NMTTools_ListOfCoupleOfShape aLCFF;
203 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
205 FindFacePairs(theEdge, theLF, aLCFF);
207 aIt.Initialize(aLCFF);
208 for (; aIt.More(); aIt.Next()) {
209 const NMTTools_CoupleOfShape& aCSFF=aIt.Value();
211 const TopoDS_Face& aF1=TopoDS::Face(aCSFF.Shape1());
212 const TopoDS_Face& aF2=TopoDS::Face(aCSFF.Shape2());
213 bRet=GEOMAlgo_Tools3D::IsInternalFace(theFace, theEdge, aF1, aF2, theContext);
221 //=======================================================================
222 //function : IsInternalFace
224 //=======================================================================
225 Standard_Boolean GEOMAlgo_Tools3D::IsInternalFace(const TopoDS_Face& theFace,
226 const TopoDS_Edge& theEdge,
227 const TopoDS_Face& theFace1,
228 const TopoDS_Face& theFace2,
229 IntTools_Context& theContext)
231 Standard_Boolean bRet;
232 Standard_Real aT1, aT2, aT, aDt2D, aDt2Dx;
233 Standard_Real aA12, aA1x, aTwoPI;
234 gp_Pnt aPx, aPF, aPF1, aPF2;
235 gp_Pnt2d aP2D, aPF2D;
237 TopoDS_Edge aE1, aE2;
238 Handle(Geom_Curve)aC3D;
240 aC3D =BRep_Tool::Curve(theEdge, aT1, aT2);
241 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
245 aDt2D=BOPTools_Tools3D::MinStepIn2d();
247 BOPTools_Tools3D::PointNearEdge (theEdge, theFace, aT, aDt2Dx, aPF2D, aPF);
250 GEOMAlgo_Tools3D::GetEdgeOnFace(theEdge, theFace1, aE1);
251 if (aE1.Orientation()==TopAbs_INTERNAL) {
253 aE1.Orientation(TopAbs_FORWARD);
254 aE2.Orientation(TopAbs_REVERSED);
256 else if (theFace1==theFace2) {
258 aE1.Orientation(TopAbs_FORWARD);
259 aE2.Orientation(TopAbs_REVERSED);
262 GEOMAlgo_Tools3D::GetEdgeOnFace(theEdge, theFace2, aE2);
268 GetApproxNormalToFaceOnEdge (aE1, theFace1, aT, aPF1, aDNF1, theContext);
269 GetApproxNormalToFaceOnEdge (aE2, theFace2, aT, aPF2, aDNF2, theContext);
271 //BOPTools_Tools3D::GetApproxNormalToFaceOnEdge (aE1, theFace1, aT, aPF1, aDNF1);
272 //BOPTools_Tools3D::GetApproxNormalToFaceOnEdge (aE2, theFace2, aT, aPF2, aDNF2);
275 gp_Vec aVBF (aPx, aPF );
276 gp_Vec aVBF1(aPx, aPF1);
277 gp_Vec aVBF2(aPx, aPF2);
285 aA12=AngleWithRef(aDBF1, aDBF2, aDTF1);
290 aA1x=AngleWithRef(aDBF1, aDBF , aDTF1);
296 bRet=!bRet; //TopAbs_IN;
301 //=======================================================================
302 //function : GetFaceOff
304 //=======================================================================
305 void GEOMAlgo_Tools3D::GetFaceOff(const TopoDS_Edge& theE1,
306 const TopoDS_Face& theF1,
307 const NMTTools_ListOfCoupleOfShape& theLCSOff,
308 TopoDS_Face& theFOff)
310 Standard_Real aT, aT1, aT2, aAngle, aTwoPI, aAngleMin;
314 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
318 BRep_Tool::Range(theE1, aT1, aT2);
319 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
321 BOPTools_Tools2D::EdgeTangent(theE1, aT, aVTgt);
322 gp_Dir aDTtgt(aVTgt);
325 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge(theE1, theF1, aT, aPn1, aDN1);
327 aIt.Initialize(theLCSOff);
328 for (; aIt.More(); aIt.Next()) {
329 const NMTTools_CoupleOfShape& aCS=aIt.Value();
330 const TopoDS_Edge& aE2=TopoDS::Edge(aCS.Shape1());
331 const TopoDS_Face& aF2=TopoDS::Face(aCS.Shape2());
336 else if (aF2.IsSame(theF1)) {
340 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge (aE2, aF2, aT, aPn2, aDN2);
343 aAngle=AngleWithRef(aDN1, aDN2, aDTtgt);
345 aAngle=aTwoPI+aAngle;
349 if (aAngle<aAngleMin){
355 //=======================================================================
356 //function : GetEdgeOnFace
358 //=======================================================================
359 Standard_Boolean GEOMAlgo_Tools3D::GetEdgeOnFace(const TopoDS_Edge& theE1,
360 const TopoDS_Face& theF2,
363 Standard_Boolean bFound;
364 TopoDS_Iterator aItF, aItW;
366 bFound=Standard_False;
368 aItF.Initialize(theF2);
369 for (; aItF.More(); aItF.Next()) {
370 const TopoDS_Shape& aW=aItF.Value();
372 for (; aItW.More(); aItW.Next()) {
373 const TopoDS_Shape& aE=aItW.Value();
374 if (aE.IsSame(theE1)) {
375 theE2=TopoDS::Edge(aE);
383 //=======================================================================
384 //function : GetEdgeOff
386 //=======================================================================
387 Standard_Boolean GEOMAlgo_Tools3D::GetEdgeOff(const TopoDS_Edge& theE1,
388 const TopoDS_Face& theF2,
392 Standard_Boolean bFound;
393 TopAbs_Orientation aOr1, aOr1C, aOr2;
394 TopExp_Explorer anExp;
396 bFound=Standard_False;
397 aOr1=theE1.Orientation();
398 aOr1C=TopAbs::Reverse(aOr1);
400 anExp.Init(theF2, TopAbs_EDGE);
401 for (; anExp.More(); anExp.Next()) {
402 const TopoDS_Edge& aEF2=TopoDS::Edge(anExp.Current());
403 if (aEF2.IsSame(theE1)) {
404 aOr2=aEF2.Orientation();
414 //=======================================================================
415 // function: ComputeState
417 //=======================================================================
418 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Face& theF,
419 const TopoDS_Solid& theRef,
420 const Standard_Real theTol,
421 const TopTools_IndexedMapOfShape& theBounds,
422 IntTools_Context& theCtx)
425 TopExp_Explorer aExp;
430 aState=TopAbs_UNKNOWN;
432 aExp.Init(theF, TopAbs_EDGE);
433 for (; aExp.More(); aExp.Next()) {
434 const TopoDS_Edge& aSE=TopoDS::Edge(aExp.Current());
435 if (BRep_Tool::Degenerated(aSE)) {
439 if (!theBounds.Contains(aSE)) {
440 const TopoDS_Edge& aE=TopoDS::Edge(aSE);
441 aState= GEOMAlgo_Tools3D::ComputeState(aE, theRef, theTol, theCtx);
445 aE1=TopoDS::Edge(aSE);
448 // !!<- process edges that are all on theRef
450 BOPTools_Tools3D::PointNearEdge(aE1, theF, aP2D, aP3D);
451 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
456 //=======================================================================
457 // function: ComputeStateByOnePoint
459 //=======================================================================
460 TopAbs_State GEOMAlgo_Tools3D::ComputeStateByOnePoint(const TopoDS_Shape& theS,
461 const TopoDS_Solid& theRef,
462 const Standard_Real theTol,
463 IntTools_Context& theCtx)
466 TopAbs_ShapeEnum aType;
468 aState=TopAbs_UNKNOWN;
469 aType=theS.ShapeType();
470 if (aType==TopAbs_VERTEX) {
471 const TopoDS_Vertex& aV=TopoDS::Vertex(theS);
472 aState=GEOMAlgo_Tools3D::ComputeState(aV, theRef, theTol, theCtx);
474 else if (aType==TopAbs_EDGE) {
475 const TopoDS_Edge& aE=TopoDS::Edge(theS);
476 aState=GEOMAlgo_Tools3D::ComputeState(aE, theRef, theTol, theCtx);
480 //=======================================================================
481 // function: ComputeState
483 //=======================================================================
484 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Vertex& theV,
485 const TopoDS_Solid& theRef,
486 const Standard_Real theTol,
487 IntTools_Context& theCtx)
492 aP3D=BRep_Tool::Pnt(theV);
493 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
496 //=======================================================================
497 // function: ComputeState
499 //=======================================================================
500 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const TopoDS_Edge& theE,
501 const TopoDS_Solid& theRef,
502 const Standard_Real theTol,
503 IntTools_Context& theCtx)
505 Standard_Real aT1, aT2, aT = 0.;
507 Handle(Geom_Curve) aC3D;
510 aC3D = BRep_Tool::Curve(theE, aT1, aT2);
513 //it means that we are in degenerated edge
514 const TopoDS_Vertex& aV = TopExp::FirstVertex(theE);
516 return TopAbs_UNKNOWN;
518 aP3D=BRep_Tool::Pnt(aV);
521 Standard_Boolean bF2Inf, bL2Inf;
522 Standard_Real dT=10.;
524 bF2Inf = Precision::IsNegativeInfinite(aT1);
525 bL2Inf = Precision::IsPositiveInfinite(aT2);
527 if (bF2Inf && !bL2Inf) {
530 else if (!bF2Inf && bL2Inf) {
533 else if (bF2Inf && bL2Inf) {
537 aT=IntTools_Tools::IntermediatePoint(aT1, aT2);
542 aState=GEOMAlgo_Tools3D::ComputeState(aP3D, theRef, theTol, theCtx);
546 //=======================================================================
547 // function: ComputeState
549 //=======================================================================
550 TopAbs_State GEOMAlgo_Tools3D::ComputeState(const gp_Pnt& theP,
551 const TopoDS_Solid& theRef,
552 const Standard_Real theTol,
553 IntTools_Context& theCtx)
557 BRepClass3d_SolidClassifier& aSC=theCtx.SolidClassifier(theRef);
558 aSC.Perform(theP, theTol);
564 //=======================================================================
565 // function: IsSplitToReverse
567 //=======================================================================
568 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse(const TopoDS_Shape& theSp,
569 const TopoDS_Shape& theSr,
570 IntTools_Context& theCtx)
572 Standard_Boolean bRet;
573 TopAbs_ShapeEnum aType;
577 aType=theSp.ShapeType();
580 const TopoDS_Edge& aESp=TopoDS::Edge(theSp);
581 const TopoDS_Edge& aESr=TopoDS::Edge(theSr);
582 bRet=GEOMAlgo_Tools3D::IsSplitToReverse(aESp, aESr, theCtx);
587 const TopoDS_Face& aFSp=TopoDS::Face(theSp);
588 const TopoDS_Face& aFSr=TopoDS::Face(theSr);
589 bRet=GEOMAlgo_Tools3D::IsSplitToReverse(aFSp, aFSr, theCtx);
598 //=======================================================================
599 //function :IsSplitToReverse
601 //=======================================================================
602 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse(const TopoDS_Face& theFSp,
603 const TopoDS_Face& theFSr,
604 IntTools_Context& theContext)
606 Standard_Boolean bRet, bFound, bInFace;
607 Standard_Real aT1, aT2, aT, aU, aV, aScPr;
611 Handle(Geom_Surface) aSr, aSp;
612 TopAbs_Orientation aOrSr, aOrSp;
613 TopExp_Explorer anExp;
618 aSr=BRep_Tool::Surface(theFSr);
619 aSp=BRep_Tool::Surface(theFSp);
621 aOrSr=theFSr.Orientation();
622 aOrSp=theFSp.Orientation();
627 bFound=Standard_False;
628 anExp.Init(theFSp, TopAbs_EDGE);
629 for (; anExp.More(); anExp.Next()) {
630 aESp=TopoDS::Edge(anExp.Current());
631 if (!BRep_Tool::Degenerated(aESp)) {
632 if (!BRep_Tool::IsClosed(aESp, theFSp)) {
642 BRep_Tool::Range(aESp, aT1, aT2);
643 aT=BOPTools_Tools2D::IntermediatePoint(aT1, aT2);
644 BOPTools_Tools3D::GetApproxNormalToFaceOnEdge(aESp, theFSp, aT, aPFSp, aDNFSp);
646 // Parts of theContext.ComputeVS(..)
647 GeomAPI_ProjectPointOnSurf& aProjector=theContext.ProjPS(theFSr);
648 aProjector.Perform(aPFSp);
649 if (!aProjector.IsDone()) {
653 aProjector.LowerDistanceParameters(aU, aV);
654 gp_Pnt2d aP2D(aU, aV);
655 bInFace=theContext.IsPointInFace (theFSr, aP2D);
660 aSr->D1(aU, aV, aPFSr, aD1U, aD1V);
663 gp_Dir aDNFSr=aDD1U^aDD1V;
664 if (theFSr.Orientation()==TopAbs_REVERSED){
673 //=======================================================================
674 //function :IsSplitToReverse
676 //=======================================================================
677 Standard_Boolean GEOMAlgo_Tools3D::IsSplitToReverse(const TopoDS_Edge& theSplit,
678 const TopoDS_Edge& theEdge,
679 IntTools_Context& theContext)
681 Standard_Boolean bRet, aFlag, bIsDegenerated;
682 Standard_Real aTE, aTS, aScPr, aTa, aTb, aT1, aT2;
683 TopAbs_Orientation aOrSr, aOrSp;
684 Handle(Geom_Curve) aCEdge, aCSplit;
690 bIsDegenerated=(BRep_Tool::Degenerated(theSplit) ||
691 BRep_Tool::Degenerated(theEdge));
692 if (bIsDegenerated) {
696 aCEdge =BRep_Tool::Curve(theEdge , aT1, aT2);
697 aCSplit=BRep_Tool::Curve(theSplit, aTa, aTb);
699 if (aCEdge==aCSplit) {
700 aOrSr=theEdge.Orientation();
701 aOrSp=theSplit.Orientation();
706 aTS=BOPTools_Tools2D::IntermediatePoint(aTa, aTb);
707 aCSplit->D0(aTS, aP);
708 aFlag=BOPTools_Tools2D::EdgeTangent(theSplit, aTS, aVS);
711 aFlag=theContext.ProjectPointOnEdge(aP, theEdge, aTE);
712 aFlag=BOPTools_Tools2D::EdgeTangent(theEdge, aTE, aVE);
721 //=======================================================================
724 //=======================================================================
725 Standard_Integer GEOMAlgo_Tools3D::Sense (const TopoDS_Face& theF1,
726 const TopoDS_Face& theF2)
728 Standard_Integer iSense=0;
730 TopoDS_Edge aE1, aE2;
731 TopExp_Explorer anExp;
733 anExp.Init(theF1, TopAbs_EDGE);
734 for (; anExp.More(); anExp.Next()) {
735 aE1=TopoDS::Edge(anExp.Current());
736 if (!BRep_Tool::Degenerated(aE1)) {
737 if (!BRep_Tool::IsClosed(aE1, theF1)) {
743 anExp.Init(theF2, TopAbs_EDGE);
744 for (; anExp.More(); anExp.Next()) {
745 aE2=TopoDS::Edge(anExp.Current());
746 if (!BRep_Tool::Degenerated(aE2)) {
747 if (!BRep_Tool::IsClosed(aE2, theF2)) {
748 if (aE2.IsSame(aE1)) {
760 BOPTools_Tools3D::GetNormalToFaceOnEdge(aE1, theF1, aDNF1);
761 BOPTools_Tools3D::GetNormalToFaceOnEdge(aE2, theF2, aDNF2);
763 iSense=BOPTools_Tools3D::SenseFlag(aDNF1, aDNF2);
767 //=======================================================================
768 // function: CopyFace
770 //=======================================================================
771 void GEOMAlgo_Tools3D::CopyFace (const TopoDS_Face& theF1,
775 TopLoc_Location aLoc;
776 TopAbs_Orientation aOr;
780 Handle(Geom_Surface) aSurface=BRep_Tool::Surface(theF1, aLoc);
781 aTol=BRep_Tool::Tolerance(theF1);
782 aOr=theF1.Orientation();
784 aBB.MakeFace (theF2, aSurface, aLoc, aTol);
785 theF2.Orientation(aOr);
787 aIt.Initialize(theF1);
788 for (; aIt.More(); aIt.Next()) {
789 const TopoDS_Shape& aW=aIt.Value();
793 //=======================================================================
794 // function: MakeContainer
796 //=======================================================================
797 void GEOMAlgo_Tools3D::MakeContainer(const TopAbs_ShapeEnum theType,
803 case TopAbs_COMPOUND:{
805 aBB.MakeCompound(aC);
810 case TopAbs_COMPSOLID:{
811 TopoDS_CompSolid aCS;
812 aBB.MakeCompSolid(aCS);
819 aBB.MakeSolid(aSolid);
827 aBB.MakeShell(aShell);
843 //=======================================================================
844 // function: MakeConnexityBlock.
846 //=======================================================================
847 void GEOMAlgo_Tools3D::MakeConnexityBlock (const TopTools_ListOfShape& theLFIn,
848 const TopTools_IndexedMapOfShape& theMEAvoid,
849 TopTools_ListOfShape& theLCB)
851 Standard_Integer aNbF, aNbAdd1;
852 TopExp_Explorer aExp;
853 TopTools_IndexedDataMapOfShapeListOfShape aMEF;
854 TopTools_MapIteratorOfMapOfShape aItM, aItM1;
855 TopTools_MapOfShape aMCB, aMAdd, aMAdd1;
856 TopTools_ListIteratorOfListOfShape aIt;
859 aNbF=theLFIn.Extent();
860 aIt.Initialize(theLFIn);
861 for (; aIt.More(); aIt.Next()) {
862 const TopoDS_Shape& aF=aIt.Value();
863 TopExp::MapShapesAndAncestors(aF, TopAbs_EDGE, TopAbs_FACE, aMEF);
867 const TopoDS_Shape& aF1=theLFIn.First();
872 aItM.Initialize(aMAdd);
873 for (; aItM.More(); aItM.Next()) {
874 const TopoDS_Shape& aF=aItM.Key();
877 aExp.Init(aF, TopAbs_EDGE);
878 for (; aExp.More(); aExp.Next()) {
879 const TopoDS_Shape& aE=aExp.Current();
880 if (theMEAvoid.Contains(aE)){
884 const TopTools_ListOfShape& aLF=aMEF.FindFromKey(aE);
886 for (; aIt.More(); aIt.Next()) {
887 const TopoDS_Shape& aFx=aIt.Value();
888 if (aFx.IsSame(aF)) {
891 if (aMCB.Contains(aFx)) {
896 }//for (; aExp.More(); aExp.Next()){
898 }// for (; aItM.More(); aItM.Next()) {
900 aNbAdd1=aMAdd1.Extent();
906 aItM1.Initialize(aMAdd1);
907 for (; aItM1.More(); aItM1.Next()) {
908 const TopoDS_Shape& aFAdd=aItM1.Key();
916 aItM.Initialize(aMCB);
917 for (; aItM.More(); aItM.Next()) {
918 const TopoDS_Shape& aF=aItM.Key();
922 //=======================================================================
923 //function : FindFacePairs
925 //=======================================================================
926 Standard_Boolean FindFacePairs (const TopoDS_Edge& theE,
927 const TopTools_ListOfShape& thLF,
928 NMTTools_ListOfCoupleOfShape& theLCFF)
930 Standard_Boolean bFound;
931 Standard_Integer i, aNbCEF;
932 TopAbs_Orientation aOr, aOrC;
933 TopTools_MapOfShape aMFP;
934 TopoDS_Face aF1, aF2;
935 TopoDS_Edge aEL, aE1;
936 TopTools_ListIteratorOfListOfShape aItLF;
937 NMTTools_CoupleOfShape aCEF, aCFF;
938 NMTTools_ListOfCoupleOfShape aLCEF, aLCEFx;
939 NMTTools_ListIteratorOfListOfCoupleOfShape aIt;
941 bFound=Standard_True;
944 aItLF.Initialize(thLF);
945 for (; aItLF.More(); aItLF.Next()) {
946 const TopoDS_Face& aFL=TopoDS::Face(aItLF.Value());
948 bFound=GEOMAlgo_Tools3D::GetEdgeOnFace(theE, aFL, aEL);
950 return bFound; // it can not be so
958 aNbCEF=aLCEF.Extent();
963 aIt.Initialize(aLCEF);
964 for (i=0; aIt.More(); aIt.Next(), ++i) {
965 const NMTTools_CoupleOfShape& aCSx=aIt.Value();
966 const TopoDS_Shape& aEx=aCSx.Shape1();
967 const TopoDS_Shape& aFx=aCSx.Shape2();
969 aOr=aEx.Orientation();
972 aOrC=TopAbs::Reverse(aOr);
973 aE1=TopoDS::Edge(aEx);
974 aF1=TopoDS::Face(aFx);
986 GEOMAlgo_Tools3D::GetFaceOff(aE1, aF1, aLCEFx, aF2);
990 theLCFF.Append(aCFF);
999 aIt.Initialize(aLCEFx);
1000 for (; aIt.More(); aIt.Next()) {
1001 const NMTTools_CoupleOfShape& aCSx=aIt.Value();
1002 const TopoDS_Shape& aFx=aCSx.Shape2();
1003 if (!aMFP.Contains(aFx)) {
1008 aNbCEF=aLCEF.Extent();
1014 //=======================================================================
1015 //function : AngleWithRef
1017 //=======================================================================
1018 Standard_Real AngleWithRef(const gp_Dir& theD1,
1019 const gp_Dir& theD2,
1020 const gp_Dir& theDRef)
1022 Standard_Real aCosinus, aSinus, aBeta, aHalfPI, aScPr;
1027 const gp_XYZ& aXYZ1=theD1.XYZ();
1028 const gp_XYZ& aXYZ2=theD2.XYZ();
1029 aXYZ=aXYZ1.Crossed(aXYZ2);
1030 aSinus=aXYZ.Modulus();
1031 aCosinus=theD1*theD2;
1035 aBeta=aHalfPI*(1.-aCosinus);
1038 aBeta=2.*PI-aHalfPI*(3.+aCosinus);
1041 aScPr=aXYZ.Dot(theDRef.XYZ());
1047 //=======================================================================
1048 //function : GetApproxNormalToFaceOnEdge
1050 //=======================================================================
1051 void GetApproxNormalToFaceOnEdge (const TopoDS_Edge& aEx,
1052 const TopoDS_Face& aFx,
1056 IntTools_Context& aCtx)
1058 Standard_Boolean bReverse;
1059 Standard_Real aT1, aT2, dT, aU, aV;
1060 gp_Dir aDTT, aDNFT, aDBT;
1062 Handle(Geom_Curve) aC3D;
1063 Handle(Geom_Surface) aS;
1064 GeomAdaptor_Surface aGAS;
1065 GeomAbs_SurfaceType aTS;
1069 bReverse=Standard_False;
1072 if (aF.Orientation()==TopAbs_REVERSED){
1076 aF.Orientation(TopAbs_FORWARD);
1080 aC3D =BRep_Tool::Curve(aE, aT1, aT2);
1084 BOPTools_Tools3D::GetNormalToFaceOnEdge (aE, aF, aT, aDNFT);
1087 BOPTools_Tools3D::GetTangentToEdge(aE, aT, aDTT);
1092 dT=BOPTools_Tools3D::MinStepIn2d();//~1.e-5;
1094 //----------------------------------------------
1096 aS=BRep_Tool::Surface(aF);
1099 if (aTS==GeomAbs_BSplineSurface ||
1100 aTS==GeomAbs_BezierSurface ||
1101 aTS==GeomAbs_Plane) {//modified by NIZNHY-PKV Fri Dec 4 08:23:24 2009ft
1102 Standard_Real aTolEx, aTolFx, aTol, dUR, dVR, dR;
1104 aTolEx=BRep_Tool::Tolerance(aEx);
1105 aTolFx=BRep_Tool::Tolerance(aFx);
1106 aTol=2.*aTolEx+aTolFx;
1107 dUR=aGAS.UResolution(aTol);
1108 dVR=aGAS.VResolution(aTol);
1109 dR=(dUR>dVR)? dUR : dVR;
1115 //----------------------------------------------
1117 aPFx.SetXYZ(aPFT.XYZ()+dT*aDBT.XYZ());
1125 GeomAPI_ProjectPointOnSurf& aProjector=aCtx.ProjPS(aF);
1127 aProjector.Perform(aPFx);
1128 if(aProjector.IsDone()) {
1129 aProjector.LowerDistanceParameters (aU, aV);
1130 aS->D0(aU, aV, aPF);
1131 BOPTools_Tools3D::GetNormalToSurface (aS, aU, aV, aDNF);