2 // Created: Thu Mar 3 11:18:14 1994
3 // Author: Bruno DUMORTIER
5 // Modified: Mon Jan 12 10:50:10 1998
6 // Author: Joelle CHAUVET
8 // automatic management of origin and orientation
9 // with method Organize
10 // Modified: Mon Feb 23 09:28:46 1998
11 // Author: Joelle CHAUVET
13 // method Organize with option of projection for closed wires
14 // new method SameNumber with option to report cuts
15 // + utilities ComputeACR and InsertACR
16 // + processing of the case of last point section
17 // Modified: Thu Apr 30 15:24:17 1998
18 // Author: Joelle CHAUVET
20 // separation closed / open sections + debug
21 // Organize becomes ComputeOrigin and SearchOrigin
22 // Modified: Tue Jul 21 16:48:35 1998
23 // Author: Joelle CHAUVET
25 // limited case for Pnext of a twist (BUC60281)
26 // Modified: Thu Jul 23 11:38:36 1998
27 // Author: Joelle CHAUVET
29 // calculate the angle of rotation in SearchOrigin
30 // Modified: Fri Jul 31 15:14:19 1998
31 // Author: Joelle CHAUVET
33 // IntersectOnWire + MapVLV
34 // Modified: Mon Oct 12 09:42:33 1998
35 // Author: Joelle CHAUVET
37 // number of edges in EdgesFromVertex (CTS21570)
39 #include <BRepFill.ixx>
41 #include <BRepLib.hxx>
42 #include <BRepLib_FindSurface.hxx>
43 #include <BRepLib_MakeFace.hxx>
44 #include <BRepLib_MakeEdge.hxx>
45 #include <BRepLib_MakeVertex.hxx>
46 #include <BRepLib_MakeWire.hxx>
47 #include <BRepExtrema_ExtPC.hxx>
48 #include <BRepExtrema_DistShapeShape.hxx>
49 #include <BRep_Tool.hxx>
50 #include <BRepTools_WireExplorer.hxx>
52 #include <TopoDS_Face.hxx>
53 #include <TopoDS_Wire.hxx>
54 #include <TopoDS_Vertex.hxx>
55 #include <BRep_Builder.hxx>
56 #include <TopLoc_Location.hxx>
57 #include <TopExp_Explorer.hxx>
61 #include <gp_Pnt2d.hxx>
63 #include <gp_Dir2d.hxx>
64 #include <gp_Circ.hxx>
65 #include <gp_Elips.hxx>
66 #include <Geom_Curve.hxx>
67 #include <Geom_TrimmedCurve.hxx>
68 #include <Geom_Surface.hxx>
69 #include <Geom_Plane.hxx>
70 #include <Geom2d_Line.hxx>
71 #include <GeomFill_Generator.hxx>
72 #include <GeomAdaptor_Curve.hxx>
73 #include <BRepLProp.hxx>
74 #include <BRepGProp.hxx>
75 #include <GProp_GProps.hxx>
76 #include <GProp_PrincipalProps.hxx>
77 #include <GCPnts_AbscissaPoint.hxx>
78 #include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
79 #include <TopTools_DataMapOfShapeListOfShape.hxx>
80 #include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx>
81 #include <TopTools_ListIteratorOfListOfShape.hxx>
82 #include <TopTools_ListOfShape.hxx>
83 #include <TopTools_Array1OfShape.hxx>
84 #include <TopTools_SequenceOfShape.hxx>
85 #include <TopTools_HSequenceOfShape.hxx>
86 #include <BRepAdaptor_Curve.hxx>
87 #include <TopTools_IndexedMapOfShape.hxx>
89 #include <BRep_Tool.hxx>
92 #include <Precision.hxx>
94 #include <TColStd_Array1OfInteger.hxx>
95 #include <Standard_NoSuchObject.hxx>
98 static void MakeWire(const TopTools_Array1OfShape& Edges,
99 const Standard_Integer rangdeb,
100 const Standard_Boolean forward,
101 TopoDS_Wire& newwire)
104 Standard_Integer rang, nbEdges = Edges.Length();
105 BW.MakeWire(newwire);
107 for (rang=rangdeb;rang<=nbEdges;rang++) {
108 BW.Add(newwire,TopoDS::Edge(Edges(rang)));
110 for (rang=1;rang<rangdeb;rang++) {
111 BW.Add(newwire,TopoDS::Edge(Edges(rang)));
117 for (rang=rangdeb;rang>=1;rang--) {
118 E = TopoDS::Edge(Edges(rang));
119 BW.Add(newwire,E.Reversed());
121 for (rang=nbEdges;rang>rangdeb;rang--) {
122 E = TopoDS::Edge(Edges(rang));
123 BW.Add(newwire, E.Reversed());
126 newwire.Orientation(TopAbs_FORWARD);
129 static void CutEdge(const TopoDS_Edge& CurrentEdge,
130 const Standard_Real& Param,
133 const TopoDS_Vertex& VRef)
136 Standard_Real first,last;
137 Handle(Geom_Curve) C = BRep_Tool::Curve(CurrentEdge,first,last);
138 TopoDS_Vertex Vf, Vl, Vi;
139 B.MakeVertex(Vi, C->Value(Param), Precision::Confusion());
140 TopExp::Vertices(CurrentEdge, Vf, Vl);
141 if (VRef.IsSame(Vf)) {
142 E1 = BRepLib_MakeEdge(C,Vf,Vi, first,Param);
143 E2 = BRepLib_MakeEdge(C,Vi,Vl, Param,last);
146 E2 = BRepLib_MakeEdge(C,Vf,Vi, first,Param);
147 E1 = BRepLib_MakeEdge(C,Vi,Vl, Param,last);
152 static void TrimEdge (const TopoDS_Edge& CurrentEdge,
153 const TColStd_SequenceOfReal& CutValues,
154 const Standard_Real t0, const Standard_Real t1,
155 const Standard_Boolean SeqOrder,
156 TopTools_SequenceOfShape& S)
160 Standard_Integer j, ndec=CutValues.Length();
161 Standard_Real first,last,m0,m1;
162 Handle(Geom_Curve) C = BRep_Tool::Curve(CurrentEdge,first,last);
164 TopoDS_Vertex Vf,Vl,Vbid,V0,V1;
165 TopAbs_Orientation CurrentOrient = CurrentEdge.Orientation();
166 TopExp::Vertices(CurrentEdge,Vf,Vl);
170 // from first to last
173 for (j=1; j<=ndec; j++) {
175 m1 = (CutValues.Value(j)-t0)*(last-first)/(t1-t0)+first;
176 TopoDS_Edge CutE = BRepLib_MakeEdge(C,V0,Vbid,m0,m1);
177 CutE.Orientation(CurrentOrient);
180 V0 = TopExp::LastVertex(CutE);
183 TopoDS_Edge LastE = BRepLib_MakeEdge(C,V0,Vl,m0,last);
184 LastE.Orientation(CurrentOrient);
190 // from last to first
193 for (j=ndec; j>=1; j--) {
195 m0 = (CutValues.Value(j)-t0)*(last-first)/(t1-t0)+first;
196 TopoDS_Edge CutE = BRepLib_MakeEdge(C,Vbid,V1,m0,m1);
197 CutE.Orientation(CurrentOrient);
200 V1 = TopExp::FirstVertex(CutE);
203 TopoDS_Edge LastE = BRepLib_MakeEdge(C,Vf,V1,first,m1);
204 LastE.Orientation(CurrentOrient);
212 //=======================================================================
215 //=======================================================================
217 TopoDS_Face BRepFill::Face(const TopoDS_Edge& Edge1,
218 const TopoDS_Edge& Edge2 )
223 // Class BRep_Tool without fields and without Constructor :
226 TopLoc_Location L,L1,L2;
227 Standard_Real f1,f2,l1,l2, Tol;
229 // Handle(Geom_Curve) C1 = BT.Curve(Edge1,L1,f1,l1);
230 Handle(Geom_Curve) C1 = BRep_Tool::Curve(Edge1,L1,f1,l1);
231 // Handle(Geom_Curve) C2 = BT.Curve(Edge2,L2,f2,l2);
232 Handle(Geom_Curve) C2 = BRep_Tool::Curve(Edge2,L2,f2,l2);
234 // compute the location
235 Standard_Boolean SameLoc = Standard_False;
238 L1 = L2 = TopLoc_Location();
239 SameLoc = Standard_True;
242 // transform and trim the curves
244 TopoDS_Vertex V1f,V1l,V2f,V2l;
246 // create a new Handle
247 if (Abs(f1 - C1->FirstParameter()) > Precision::PConfusion() ||
248 Abs(l1 - C1->LastParameter()) > Precision::PConfusion() ) {
249 C1 = new Geom_TrimmedCurve(C1,f1,l1);
252 C1 = Handle(Geom_Curve)::DownCast(C1->Copy());
254 // eventually the curve is concerned
256 C1->Transform(L1.Transformation());
258 // it is set in the proper direction and its vertices are taken
259 if (Edge1.Orientation() == TopAbs_REVERSED) {
260 TopExp::Vertices(Edge1,V1l,V1f);
264 TopExp::Vertices(Edge1,V1f,V1l);
267 // a new Handle is created
268 if (Abs(f2 - C2->FirstParameter()) > Precision::PConfusion() ||
269 Abs(l2 - C2->LastParameter()) > Precision::PConfusion() ) {
270 C2 = new Geom_TrimmedCurve(C2,f2,l2);
273 C2 = Handle(Geom_Curve)::DownCast(C2->Copy());
275 // eventually the curve is concerned
277 C2->Transform(L2.Transformation());
279 // it is set in the proper direction and its vertices are taken
280 if (Edge2.Orientation() == TopAbs_REVERSED) {
281 TopExp::Vertices(Edge2,V2l,V2f);
285 TopExp::Vertices(Edge2,V2f,V2l);
288 // Are they closed edges?
289 Standard_Boolean Closed = V1f.IsSame(V1l) && V2f.IsSame(V2l);
292 GeomFill_Generator Generator;
293 Generator.AddCurve( C1);
294 Generator.AddCurve( C2);
295 Generator.Perform( Precision::PConfusion());
297 Handle(Geom_Surface) Surf = Generator.Surface();
298 Handle(Geom_Curve) Iso;
300 B.MakeFace(Face,Surf,Precision::Confusion());
302 // make the missing edges
303 Surf->Bounds(f1,l1,f2,l2);
305 TopoDS_Edge Edge3, Edge4;
307 Iso = Surf->UIso(f1);
308 // Tol = Max(BT.Tolerance(V1f), BT.Tolerance(V2f));
309 Tol = Max(BRep_Tool::Tolerance(V1f), BRep_Tool::Tolerance(V2f));
310 if (Iso->Value(f2).Distance(Iso->Value(l2)) > Tol) {
311 B.MakeEdge(Edge3,Iso,Precision::Confusion());
315 B.Degenerated(Edge3, Standard_True);
317 V1f.Orientation(TopAbs_FORWARD);
319 V2f.Orientation(TopAbs_REVERSED);
321 B.Range(Edge3,f2,l2);
327 Iso = Surf->UIso(l1);
328 // Tol = Max(BT.Tolerance(V1l), BT.Tolerance(V2l));
329 Tol = Max(BRep_Tool::Tolerance(V1l), BRep_Tool::Tolerance(V2l));
330 if (Iso->Value(l2).Distance(Iso->Value(f2)) > Tol) {
331 B.MakeEdge(Edge4,Iso,Precision::Confusion());
335 B.Degenerated(Edge4, Standard_True);
337 V1l.Orientation(TopAbs_FORWARD);
339 V2l.Orientation(TopAbs_REVERSED);
341 B.Range(Edge4,f2,l2);
352 B.Add(W,Edge2.Reversed());
359 Standard_Real T = Precision::Confusion();
361 if ( Edge1.Orientation() == TopAbs_REVERSED ) {
362 B.UpdateEdge(Edge1,new Geom2d_Line(gp_Pnt2d(0,f2),gp_Dir2d(-1,0)),Face,T);
363 B.Range(Edge1,Face,-l1,-f1);
366 B.UpdateEdge(Edge1,new Geom2d_Line(gp_Pnt2d(0,f2),gp_Dir2d(1,0)),Face,T);
367 B.Range(Edge1,Face,f1,l1);
370 if ( Edge2.Orientation() == TopAbs_REVERSED ) {
371 B.UpdateEdge(Edge2,new Geom2d_Line(gp_Pnt2d(0,l2),gp_Dir2d(-1,0)),Face,T);
372 B.Range(Edge2,Face,-l1,-f1);
375 B.UpdateEdge(Edge2,new Geom2d_Line(gp_Pnt2d(0,l2),gp_Dir2d(1,0)),Face,T);
376 B.Range(Edge2,Face,f1,l1);
381 new Geom2d_Line(gp_Pnt2d(l1,0),gp_Dir2d(0,1)),
382 new Geom2d_Line(gp_Pnt2d(f1,0),gp_Dir2d(0,1)),Face,T);
385 B.UpdateEdge(Edge3,new Geom2d_Line(gp_Pnt2d(f1,0),gp_Dir2d(0,1)),Face,T);
386 B.UpdateEdge(Edge4,new Geom2d_Line(gp_Pnt2d(l1,0),gp_Dir2d(0,1)),Face,T);
389 // Set the non parameter flag;
390 B.SameParameter(Edge1,Standard_False);
391 B.SameParameter(Edge2,Standard_False);
392 B.SameParameter(Edge3,Standard_False);
393 B.SameParameter(Edge4,Standard_False);
394 B.SameRange(Edge1,Standard_False);
395 B.SameRange(Edge2,Standard_False);
396 B.SameRange(Edge3,Standard_False);
397 B.SameRange(Edge4,Standard_False);
399 BRepLib::SameParameter(Face);
401 if ( SameLoc) Face.Move(L);
406 //=======================================================================
409 //=======================================================================
411 TopoDS_Shell BRepFill::Shell(const TopoDS_Wire& Wire1,
412 const TopoDS_Wire& Wire2 )
417 TopoDS_Edge Edge1, Edge2, Edge3, Edge4, Couture;
420 // Class BRep_Tool without fields and without Constructor :
427 Standard_Boolean Closed = Wire1.Closed() && Wire2.Closed();
429 Standard_Boolean thefirst = Standard_True;
431 ex1.Init(Wire1,TopAbs_EDGE);
432 ex2.Init(Wire2,TopAbs_EDGE);
434 while ( ex1.More() && ex2.More() ) {
436 Edge1 = TopoDS::Edge(ex1.Current());
437 Edge2 = TopoDS::Edge(ex2.Current());
439 Standard_Boolean Periodic = Edge1.Closed() && Edge2.Closed();
444 TopLoc_Location L,L1,L2;
445 Standard_Real f1,l1,f2,l2,Tol;
447 Handle(Geom_Curve) C1 = BRep_Tool::Curve(Edge1,L1,f1,l1);
448 Handle(Geom_Curve) C2 = BRep_Tool::Curve(Edge2,L2,f2,l2);
450 // compute the location
451 Standard_Boolean SameLoc = Standard_False;
454 L1 = L2 = TopLoc_Location();
455 SameLoc = Standard_True;
458 // transform and trim the curves
460 TopoDS_Vertex V1f,V1l,V2f,V2l;
463 if (Abs(f1 - C1->FirstParameter()) > Precision::PConfusion() ||
464 Abs(l1 - C1->LastParameter()) > Precision::PConfusion() ) {
465 C1 = new Geom_TrimmedCurve(C1,f1,l1);
468 C1 = Handle(Geom_Curve)::DownCast(C1->Copy());
471 C1->Transform(L1.Transformation());
473 if (Edge1.Orientation() == TopAbs_REVERSED) {
474 TopExp::Vertices(Edge1,V1l,V1f);
478 TopExp::Vertices(Edge1,V1f,V1l);
480 if (Abs(f2 - C2->FirstParameter()) > Precision::PConfusion() ||
481 Abs(l2 - C2->LastParameter()) > Precision::PConfusion() ) {
482 C2 = new Geom_TrimmedCurve(C2,f2,l2);
485 C2 = Handle(Geom_Curve)::DownCast(C2->Copy());
488 C2->Transform(L2.Transformation());
490 if (Edge2.Orientation() == TopAbs_REVERSED) {
491 TopExp::Vertices(Edge2,V2l,V2f);
495 TopExp::Vertices(Edge2,V2f,V2l);
497 GeomFill_Generator Generator;
498 Generator.AddCurve( C1);
499 Generator.AddCurve( C2);
500 Generator.Perform( Precision::PConfusion());
502 Handle(Geom_Surface) Surf = Generator.Surface();
503 Handle(Geom_Curve) Iso;
505 B.MakeFace(Face,Surf,Precision::Confusion());
507 // make the missing edges
508 Surf->Bounds(f1,l1,f2,l2);
511 Iso = Surf->UIso(f1);
512 // Tol = Max(BT.Tolerance(V1f), BT.Tolerance(V2f));
513 Tol = Max(BRep_Tool::Tolerance(V1f), BRep_Tool::Tolerance(V2f));
514 if (Iso->Value(f2).Distance(Iso->Value(l2)) > Tol) {
515 B.MakeEdge(Edge3,Iso,Precision::Confusion());
519 B.Degenerated(Edge3, Standard_True);
521 V1f.Orientation(TopAbs_FORWARD);
523 V2f.Orientation(TopAbs_REVERSED);
525 B.Range(Edge3,f2,l2);
530 thefirst = Standard_False;
537 if ( Closed && !ex1.More() && !ex2.More() ) {
541 Iso = Surf->UIso(l1);
542 // Tol = Max(BT.Tolerance(V1l), BT.Tolerance(V2l));
543 Tol = Max(BRep_Tool::Tolerance(V1l), BRep_Tool::Tolerance(V2l));
544 if (Iso->Value(l2).Distance(Iso->Value(f2)) > Tol) {
545 B.MakeEdge(Edge4,Iso,Precision::Confusion());
549 B.Degenerated(Edge4, Standard_True);
551 V1l.Orientation(TopAbs_FORWARD);
553 V2l.Orientation(TopAbs_REVERSED);
555 B.Range(Edge4,f2,l2);
565 B.Add(W,Edge2.Reversed());
570 if ( SameLoc) Face.Move( L);
576 Standard_Real T = Precision::Confusion();
578 if ( Edge1.Orientation() == TopAbs_REVERSED ) {
579 B.UpdateEdge(Edge1,new Geom2d_Line(gp_Pnt2d(0,f2),gp_Dir2d(-1,0)),
581 B.Range(Edge1,Face,-l1,-f1);
584 B.UpdateEdge(Edge1,new Geom2d_Line(gp_Pnt2d(0,f2),gp_Dir2d(1,0)),
586 B.Range(Edge1,Face,f1,l1);
589 if ( Edge2.Orientation() == TopAbs_REVERSED ) {
590 B.UpdateEdge(Edge2,new Geom2d_Line(gp_Pnt2d(0,l2),gp_Dir2d(-1,0)),
592 B.Range(Edge2,Face,-l1,-f1);
595 B.UpdateEdge(Edge2,new Geom2d_Line(gp_Pnt2d(0,l2),gp_Dir2d(1,0)),
597 B.Range(Edge2,Face,f1,l1);
602 new Geom2d_Line(gp_Pnt2d(l1,0),gp_Dir2d(0,1)),
603 new Geom2d_Line(gp_Pnt2d(f1,0),gp_Dir2d(0,1)),
607 B.UpdateEdge(Edge3,new Geom2d_Line(gp_Pnt2d(f1,0),gp_Dir2d(0,1)),Face,T);
608 B.UpdateEdge(Edge4,new Geom2d_Line(gp_Pnt2d(l1,0),gp_Dir2d(0,1)),Face,T);
611 // Set the non parameter flag;
612 B.SameParameter(Edge1,Standard_False);
613 B.SameParameter(Edge2,Standard_False);
614 B.SameParameter(Edge3,Standard_False);
615 B.SameParameter(Edge4,Standard_False);
616 B.SameRange(Edge1,Standard_False);
617 B.SameRange(Edge2,Standard_False);
618 B.SameRange(Edge3,Standard_False);
619 B.SameRange(Edge4,Standard_False);
622 BRepLib::SameParameter(Shell);
626 //=======================================================================
629 //=======================================================================
631 void BRepFill::Axe (const TopoDS_Shape& Spine,
632 const TopoDS_Wire& Profile,
634 Standard_Boolean& ProfOnSpine,
635 const Standard_Real Tol)
637 gp_Pnt Loc,Loc1,Loc2;
638 gp_Vec Tang,Tang1,Tang2,Normal;
640 Handle(Geom_Surface) S;
645 // normal to the Spine.
646 if (Spine.ShapeType() == TopAbs_FACE) {
647 aFace = TopoDS::Face(Spine);
648 S = BRep_Tool::Surface(TopoDS::Face(Spine), L);
649 if ( !S->IsKind(STANDARD_TYPE(Geom_Plane))) {
650 BRepLib_FindSurface FS(TopoDS::Face(Spine), -1, Standard_True);
656 Standard_NoSuchObject::Raise
657 ("BRepFill_Evolved : The Face is not planar");
661 else if (Spine.ShapeType() == TopAbs_WIRE) {
662 aFace = BRepLib_MakeFace(TopoDS::Wire(Spine),Standard_True);
663 S = BRep_Tool::Surface(aFace, L);
666 if (S.IsNull()) Standard_DomainError::Raise("BRepFill_Evolved::Axe");
669 S = Handle(Geom_Surface)::DownCast(S->Transformed(L.Transformation()));
671 Normal = Handle(Geom_Plane)::DownCast(S)->Pln().Axis().Direction();
673 // Find vertex of the profile closest to the spine.
674 Standard_Real DistMin = Precision::Infinite();
676 // Standard_Real Tol2 = Tol*Tol;
677 Standard_Real Tol2 = 1.e-10;
678 TopExp_Explorer PE, SE;
679 BRepExtrema_ExtPC BE;
680 Standard_Real Par =0.,f,l;
681 // Standard_Real D1,D2;
684 // First check if there is contact Vertex Vertex.
685 Standard_Boolean IsOnVertex = Standard_False;
686 SE.Init(aFace.Oriented(TopAbs_FORWARD),TopAbs_VERTEX);
687 // modified by NIZHNY-EAP Wed Feb 23 12:31:52 2000 ___BEGIN___
688 // for (;SE.More() && !IsOnVertex ; SE.Next()) {
689 for (;SE.More(); SE.Next()) {
690 P1 = BRep_Tool::Pnt(TopoDS::Vertex(SE.Current()));
692 PE.Init(Profile,TopAbs_VERTEX);
693 for ( ; PE.More(); PE.Next()) {
694 P2 = BRep_Tool::Pnt(TopoDS::Vertex(PE.Current()));
695 Standard_Real DistP1P2 = P1.SquareDistance(P2);
696 IsOnVertex = (DistP1P2 <= Tol2);
697 if (IsOnVertex) break;
699 // otherwise SE.Next() is done and VonF is wrong
700 if (IsOnVertex) break;
701 // modified by NIZHNY-EAP Wed Jan 26 09:08:36 2000 ___END___
705 // try to find on which edge which shared this vertex,
706 // the profile must be considered.
707 // E1, E2 : those two edges.
708 TopTools_IndexedDataMapOfShapeListOfShape Map;
709 TopExp::MapShapesAndAncestors(aFace.Oriented(TopAbs_FORWARD),
714 const TopoDS_Vertex& VonF = TopoDS::Vertex(SE.Current());
715 const TopTools_ListOfShape& List = Map.FindFromKey(VonF);
716 const TopoDS_Edge& E1 = TopoDS::Edge(List.First());
717 const TopoDS_Edge& E2 = TopoDS::Edge(List. Last());
719 Handle(Geom_Curve) CE1 = BRep_Tool::Curve(E1,L,f,l);
720 Standard_Real Par1 = BRep_Tool::Parameter(VonF,E1,aFace);
721 CE1->D1(Par1,Loc1,Tang1);
722 if (!L.IsIdentity()) {
723 Tang1.Transform(L.Transformation());
724 Loc1.Transform(L.Transformation());
726 if (E1.Orientation() == TopAbs_REVERSED) Tang1.Reverse();
728 Handle(Geom_Curve) CE2 = BRep_Tool::Curve(E2,L,f,l);
729 Standard_Real Par2 = BRep_Tool::Parameter(VonF,E2,aFace);
730 CE2->D1(Par2,Loc2,Tang2);
731 if (!L.IsIdentity()) {
732 Tang2.Transform(L.Transformation());
733 Loc2.Transform(L.Transformation());
735 if (E2.Orientation() == TopAbs_REVERSED) Tang2.Reverse();
737 // modified by NIZHNY-EAP Wed Feb 2 15:38:41 2000 ___BEGIN___
740 Standard_Real sca1=0., sca2=0.;
741 TopoDS_Vertex V1, V2;
743 for (PE.Init(Profile,TopAbs_EDGE); PE.More(); PE.Next()) {
744 E = TopoDS::Edge(PE.Current());
745 TopExp::Vertices(E, V1, V2);
746 P1 = BRep_Tool::Pnt(V1);
747 P2 = BRep_Tool::Pnt(V2);
749 sca1 += Abs(Tang1.Dot(vec));
750 sca2 += Abs(Tang2.Dot(vec));
752 // modified by NIZHNY-EAP Wed Feb 2 15:38:44 2000 ___END___
754 if ( Abs(sca1) < Abs(sca2)) {
765 SE.Init(aFace.Oriented(TopAbs_FORWARD),TopAbs_EDGE);
766 for ( ; SE.More(); SE.Next()) {
767 const TopoDS_Edge& E = TopoDS::Edge(SE.Current());
769 for (PE.Init(Profile,TopAbs_VERTEX) ; PE.More(); PE.Next()) {
770 Dist = Precision::Infinite();
771 const TopoDS_Vertex& V = TopoDS::Vertex(PE.Current());
775 for (Standard_Integer i = 1; i <= BE.NbExt(); i++) {
777 Dist = sqrt (BE.SquareDistance(i));
778 Par = BE.Parameter(i);
784 if (Dist < DistMin) {
786 BRepAdaptor_Curve BAC(E);
787 BAC.D1 (Par,Loc,Tang);
788 if (E.Orientation() == TopAbs_REVERSED) Tang.Reverse();
794 ProfOnSpine = (DistMin < Tol);
795 //Construction AxeProf;
796 gp_Ax3 A3 (Loc,Normal,Tang);
801 //=======================================================================
802 //function : SearchOrigin
803 //purpose : Cut and orientate a closed wire.
804 //=======================================================================
806 void BRepFill::SearchOrigin(TopoDS_Wire & W,
809 const Standard_Real Tol)
812 Standard_NoSuchObject::
813 Raise("BRepFill::SearchOrigin : the wire must be closed");
816 Standard_Boolean NewVertex = Standard_False;
817 Standard_Real theparam = 1.e101, angle;
819 TopoDS_Edge E, Eref, E1 , E2;
821 // Class BRep_Tool without fields and without Constructor :
824 W.Orientation(TopAbs_FORWARD); //to avoid composing the orientations
826 // Calculate the distance
827 B.MakeVertex(V, P, Tol);
828 BRepExtrema_DistShapeShape DSS(V, W);
830 Standard_Integer isol = 1;
831 Standard_Real dss = P.Distance(DSS.PointOnShape2(isol));
832 for (Standard_Integer iss=2; iss<=DSS.NbSolution(); iss++)
833 if (dss > P.Distance(DSS.PointOnShape2(iss))) {
834 dss = P.Distance(DSS.PointOnShape2(iss));
837 TopoDS_Shape supp = DSS.SupportOnShape2(isol);
838 if (DSS.SupportTypeShape2(isol)==BRepExtrema_IsVertex) {
839 V = TopoDS::Vertex(supp);
842 TopoDS_Vertex Vf, Vl;
843 Standard_Real d, dist;
844 E = TopoDS::Edge(supp);
845 TopExp::Vertices(E, Vf, Vl);
846 // dist = P.Distance(BT.Pnt(Vf));
847 dist = P.Distance(BRep_Tool::Pnt(Vf));
851 // d = P.Distance(BT.Pnt(Vl));
852 d = P.Distance(BRep_Tool::Pnt(Vl));
853 if ((d<Tol) && (d<dist)) {
857 NewVertex = (dist > Tol);
859 DSS.ParOnEdgeS2(isol, theparam);
865 cout << "BRepFill::SearchOrigine : Echec Distance" << endl;
869 Standard_Integer ii, rangdeb=0, NbEdges=0;
870 Standard_Boolean forward;
871 BRepTools_WireExplorer exp;
873 // Calculate the number of edges
874 for(exp.Init(W); exp.More(); exp.Next()) NbEdges++;
880 // Construct the Table and calculate rangdeb
881 TopTools_Array1OfShape Edges(1, NbEdges);
882 for(exp.Init(W), ii=1; exp.More(); exp.Next(), ii++) {
884 if (NewVertex && E.IsSame(Eref)) {
886 CutEdge(E, theparam, E1, E2, exp.CurrentVertex());
895 if (!NewVertex && V.IsSame(exp.CurrentVertex())) {
899 if (rangdeb == 0) rangdeb = NbEdges;
901 // Calculate the direction of parsing
902 E = TopoDS::Edge(Edges(rangdeb));
904 // theparam = BT.Parameter(V, E);
905 theparam = BRep_Tool::Parameter(V, E);
907 BRepAdaptor_Curve AC(E);
910 AC.D1(theparam, Pe, Ve);
911 if (E.Orientation()==TopAbs_REVERSED) {
914 angle = Ve.Angle(Dir);
915 if (angle > M_PI) angle = 2*M_PI - angle;
916 forward = (angle <= M_PI/2);
919 MakeWire( Edges, rangdeb, forward, W);
920 W.Closed(Standard_True);
925 //=======================================================================
926 //function : ComputeACR
928 //=======================================================================
930 void BRepFill::ComputeACR(const TopoDS_Wire& wire,
931 TColStd_Array1OfReal& ACR)
933 // calculate the reduced curvilinear abscisses and the length of the wire
934 BRepTools_WireExplorer anExp;
935 Standard_Integer nbEdges=0, i;
939 for(anExp.Init(wire); anExp.More(); anExp.Next()) {
941 TopoDS_Edge Ecur = TopoDS::Edge(anExp.Current());
942 ACR(nbEdges) = ACR(nbEdges-1);
943 if (!BRep_Tool::Degenerated(Ecur)) {
944 BRepAdaptor_Curve anEcur(Ecur);
945 ACR(nbEdges) += GCPnts_AbscissaPoint::Length(anEcur);
949 // total length of the wire
950 ACR(0) = ACR(nbEdges);
952 // reduced curvilinear abscisses
953 if (ACR(0)>Precision::Confusion()) {
954 for (i=1; i<=nbEdges; i++) {
965 //=======================================================================
966 //function : InsertACR
968 //=======================================================================
970 TopoDS_Wire BRepFill::InsertACR(const TopoDS_Wire& wire,
971 const TColStd_Array1OfReal& ACRcuts,
972 const Standard_Real prec)
974 // calculate ACR of the wire to be cut
975 BRepTools_WireExplorer anExp;
976 Standard_Integer nbEdges=0;
977 for(anExp.Init(wire); anExp.More(); anExp.Next()) {
980 TColStd_Array1OfReal ACRwire(0,nbEdges);
981 ComputeACR(wire, ACRwire);
983 Standard_Integer i, j, nmax=ACRcuts.Length();
984 TColStd_Array1OfReal paradec(1,nmax);
987 Standard_Real t0,t1=0;
990 // processing edge by edge
991 for(anExp.Init(wire); anExp.More(); anExp.Next()) {
994 t1 = ACRwire(nbEdges);
996 // parameters of cut on this edge
997 Standard_Integer ndec=0;
998 for (i=1; i<=ACRcuts.Length(); i++ ) {
999 if (t0+prec<ACRcuts(i) && ACRcuts(i)<t1-prec) {
1001 paradec(ndec) = ACRcuts(i);
1005 TopoDS_Edge E = anExp.Current();
1006 TopoDS_Vertex V = anExp.CurrentVertex();
1008 if (ndec==0 || BRep_Tool::Degenerated(E)) {
1013 // it is necessary to cut the edge
1014 // following the direction of parsing of the wire
1015 Standard_Boolean SO = (V.IsSame(TopExp::FirstVertex(E)));
1016 TopTools_SequenceOfShape SE;
1018 TColStd_SequenceOfReal SR;
1020 // the wire is always FORWARD
1021 // it is necesary to modify the parameter of cut6 if the edge is REVERSED
1022 if (E.Orientation() == TopAbs_FORWARD) {
1023 for (j=1; j<=ndec; j++) SR.Append(paradec(j));
1026 for (j=1; j<=ndec; j++) SR.Append(t0+t1-paradec(ndec+1-j));
1028 TrimEdge(E,SR,t0,t1,SO,SE);
1029 for (j=1; j<=SE.Length(); j++) {
1030 MW.Add(TopoDS::Edge(SE.Value(j)));
1036 TopAbs_Orientation Orien = wire.Orientation();
1037 TopoDS_Shape aLocalShape = MW.Wire();
1038 aLocalShape.Orientation(Orien);
1039 TopoDS_Wire wres = TopoDS::Wire(aLocalShape);
1040 // TopoDS_Wire wres = TopoDS::Wire(MW.Wire().Oriented(Orien));