0022312: Translation of french commentaries in OCCT files
[occt.git] / src / BRepAlgo / BRepAlgo_Loop.cxx
CommitLineData
7fd59977 1// File: BRepAlgo_Loop.cxx
2// Created: Fri Nov 10 16:25:22 1995
3// Author: Yves FRICAUD
4// <yfr@stylox>
5
6#include <stdio.h>
7
8#include <BRepAlgo_Loop.ixx>
9
10#include <BRep_Builder.hxx>
11#include <BRepAlgo_FaceRestrictor.hxx>
12#include <BRep_Tool.hxx>
13
14#include <Geom2d_Curve.hxx>
15#include <Geom_Surface.hxx>
16#include <TopExp.hxx>
17#include <TopTools_SequenceOfShape.hxx>
18#include <TopTools_MapOfShape.hxx>
19#include <TopTools_ListIteratorOfListOfShape.hxx>
20#include <TopTools_DataMapIteratorOfDataMapOfShapeListOfShape.hxx>
21
22#include <TopoDS.hxx>
23#include <TopoDS_Vertex.hxx>
24#include <TopoDS_Wire.hxx>
25#include <gp_Pnt.hxx>
26#include <gp_Pnt2d.hxx>
27#include <Precision.hxx>
28#include <BRep_TVertex.hxx>
29#include <BRep_TEdge.hxx>
30#include <TopExp_Explorer.hxx>
31#include <TopoDS_Iterator.hxx>
32#include <TopTools_DataMapIteratorOfDataMapOfShapeShape.hxx>
33
34#ifdef DRAW
35#include <DBRep.hxx>
36#endif
37#ifdef DEB
38Standard_Boolean AffichLoop = Standard_False;
39Standard_Integer NbLoops = 0;
40Standard_Integer NbWires = 1;
41static char* name = new char[100];
42#endif
43
44//=======================================================================
45//function : BRepAlgo_Loop
46//purpose :
47//=======================================================================
48
49BRepAlgo_Loop::BRepAlgo_Loop()
50{
51}
52
53
54//=======================================================================
55//function : Init
56//purpose :
57//=======================================================================
58
59void BRepAlgo_Loop::Init(const TopoDS_Face& F)
60{
61 myConstEdges.Clear();
62 myVerOnEdges.Clear();
63 myNewWires .Clear();
64 myNewFaces .Clear();
65 myNewEdges .Clear();
66 myFace = F;
67}
68
69
70//=======================================================================
71//function : Bubble
72//purpose : Ordonne la sequence de vertex en parametre croissant.
73//=======================================================================
74
75static void Bubble(const TopoDS_Edge& E,
76 TopTools_SequenceOfShape& Seq)
77{
78 Standard_Boolean Invert = Standard_True;
79 Standard_Integer NbPoints = Seq.Length();
80 Standard_Real U1,U2;
81 TopoDS_Vertex V1,V2;
82
83 while (Invert) {
84 Invert = Standard_False;
85 for ( Standard_Integer i = 1; i < NbPoints; i++) {
86 TopoDS_Shape aLocalV = Seq.Value(i) .Oriented(TopAbs_INTERNAL);
87 V1 = TopoDS::Vertex(aLocalV);
88 aLocalV = Seq.Value(i+1).Oriented(TopAbs_INTERNAL);
89 V2 = TopoDS::Vertex(aLocalV);
90// V1 = TopoDS::Vertex(Seq.Value(i) .Oriented(TopAbs_INTERNAL));
91// V2 = TopoDS::Vertex(Seq.Value(i+1).Oriented(TopAbs_INTERNAL));
92
93 U1 = BRep_Tool::Parameter(V1,E);
94 U2 = BRep_Tool::Parameter(V2,E);
95 if (U2 < U1) {
96 Seq.Exchange(i,i+1);
97 Invert = Standard_True;
98 }
99 }
100 }
101}
102
103
104
105//=======================================================================
106//function : AddEdges
107//purpose :
108//=======================================================================
109
110void BRepAlgo_Loop::AddEdge (TopoDS_Edge& E,
111 const TopTools_ListOfShape& LV)
112{
113 myVerOnEdges.Bind(E,LV);
114}
115
116
117//=======================================================================
118//function : AddConstEdges
119//purpose :
120//=======================================================================
121
122void BRepAlgo_Loop::AddConstEdge (const TopoDS_Edge& E)
123{
124 myConstEdges.Append(E);
125}
126
127//=======================================================================
128//function : AddConstEdges
129//purpose :
130//=======================================================================
131
132void BRepAlgo_Loop::AddConstEdges(const TopTools_ListOfShape& LE)
133{
134 TopTools_ListIteratorOfListOfShape itl(LE);
135 for (; itl.More(); itl.Next()) {
136 myConstEdges.Append(itl.Value());
137 }
138}
139
140
141//=======================================================================
142//function : UpdateClosedEdge
143//purpose : Si le premier ou dernier vertex d intersection
144// coincide avec le vertex de fermeture il est supprime de SV.
145// il sera ajoute au debut et a la fin de SV par l appelant.
146//=======================================================================
147
148static TopoDS_Vertex UpdateClosedEdge(const TopoDS_Edge& E,
149 TopTools_SequenceOfShape& SV)
150{
151 TopoDS_Vertex VB [2], V1, V2, VRes;
152 gp_Pnt P,PC;
153 Standard_Boolean OnStart = 0, OnEnd = 0;
154 //// modified by jgv, 13.04.04 for OCC5634 ////
155 TopExp::Vertices (E,V1,V2);
156 //Standard_Real Tol = Precision::Confusion();
157 Standard_Real Tol = BRep_Tool::Tolerance( V1 );
158 ///////////////////////////////////////////////
159
160 if (SV.IsEmpty()) return VRes;
161
162 VB[0] = TopoDS::Vertex(SV.First());
163 VB[1] = TopoDS::Vertex(SV.Last ());
164 PC = BRep_Tool::Pnt(V1);
165
166 for ( Standard_Integer i = 0 ; i < 2 ; i++) {
167 P = BRep_Tool::Pnt(VB [i]);
168 if (P.IsEqual(PC,Tol)) {
169 VRes = VB [i];
170 if (i == 0) OnStart = Standard_True;
171 else OnEnd = Standard_True;
172 }
173 }
174 if (OnStart && OnEnd) {
175 if (!VB[0].IsSame(VB[1])) {
176#ifdef DEB
177 if (AffichLoop)
178 cout <<" Deux vertex different sur vertex de fermeture"<<endl;
179#endif
180 }
181 else {
182 SV.Remove(1);
183 if (!SV.IsEmpty()) SV.Remove(SV.Length());
184 }
185 }
186 else if (OnStart) SV.Remove(1);
187 else if (OnEnd ) SV.Remove(SV.Length());
188
189 return VRes;
190}
191
192
193
194//=======================================================================
195//function : RemovePendingEdges
196//purpose :
197//=======================================================================
198
199static void RemovePendingEdges(TopTools_DataMapOfShapeListOfShape& MVE)
200{
201 //--------------------------------
202 // Suppression des edges pendants.
203 //--------------------------------
204 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape Mapit;
205 TopTools_ListOfShape ToRemove;
206 TopTools_ListIteratorOfListOfShape itl;
207 Standard_Boolean YaSupress = Standard_True;
208 TopoDS_Vertex V1,V2;
209
210 while (YaSupress) {
211 YaSupress = Standard_False;
212 TopTools_ListOfShape VToRemove;
213 TopTools_MapOfShape EToRemove;
214
215 for (Mapit.Initialize(MVE); Mapit.More(); Mapit.Next()) {
216
217 if (Mapit.Value().IsEmpty()) {
218 VToRemove.Append(Mapit.Key());
219 }
220 if (Mapit.Value().Extent() == 1) {
221 const TopoDS_Edge& E = TopoDS::Edge(Mapit.Value().First());
222 TopExp::Vertices(E,V1,V2) ;
223 if (!V1.IsSame(V2)) {
224 VToRemove.Append(Mapit.Key());
225 EToRemove.Add(Mapit.Value().First());
226 }
227 }
228 }
229
230 if (!VToRemove.IsEmpty()) {
231 YaSupress = Standard_True;
232 for (itl.Initialize(VToRemove); itl.More(); itl.Next()) {
233 MVE.UnBind(itl.Value());
234 }
235 if (!EToRemove.IsEmpty()) {
236 for (Mapit.Initialize(MVE); Mapit.More(); Mapit.Next()) {
237 TopTools_ListOfShape& LE = MVE.ChangeFind(Mapit.Key());
238 itl.Initialize(LE);
239 while (itl.More()) {
240 if (EToRemove.Contains(itl.Value())) {
241 LE.Remove(itl);
242 }
243 else itl.Next();
244 }
245 }
246 }
247 }
248 }
249}
250//=======================================================================
251//function : SamePnt2d
252//purpose :
253//=======================================================================
254
255static Standard_Boolean SamePnt2d(TopoDS_Vertex V,
256 TopoDS_Edge& E1,
257 TopoDS_Edge& E2,
258 TopoDS_Face& F)
259{
260 Standard_Real f1,f2,l1,l2;
261 gp_Pnt2d P1,P2;
262 TopoDS_Shape aLocalF = F.Oriented(TopAbs_FORWARD);
263 TopoDS_Face FF = TopoDS::Face(aLocalF);
264// TopoDS_Face FF = TopoDS::Face(F.Oriented(TopAbs_FORWARD));
265 Handle(Geom2d_Curve) C1 = BRep_Tool::CurveOnSurface(E1,FF,f1,l1);
266 Handle(Geom2d_Curve) C2 = BRep_Tool::CurveOnSurface(E2,FF,f2,l2);
267 if (E1.Orientation () == TopAbs_FORWARD) P1 = C1->Value(f1);
268 else P1 = C1->Value(l1);
269
270 if (E2.Orientation () == TopAbs_FORWARD) P2 = C2->Value(l2);
271 else P2 = C2->Value(f2);
272 Standard_Real Tol = 100*BRep_Tool::Tolerance(V);
273 Standard_Real Dist = P1.Distance(P2);
274 return Dist < Tol;
275}
276
277//=======================================================================
278//function : SelectEdge
279//purpose : Trouve l edge <NE> connexe a <CE> par le vertex <CV> dans
280// la liste <LE>. <NE> est supprime de la liste. Si <CE> est
281// aussi dans la liste <LE> avec la meme orientation, il est
282// supprime de la liste.
283//=======================================================================
284
285static Standard_Boolean SelectEdge(const TopoDS_Face& F,
286 const TopoDS_Edge& CE,
287 const TopoDS_Vertex& CV,
288 TopoDS_Edge& NE,
289 TopTools_ListOfShape& LE)
290{
291 TopTools_ListIteratorOfListOfShape itl;
292 NE.Nullify();
293#ifdef DEB
294 if (AffichLoop) {
295 if ( LE.Extent() > 2) {
296 cout <<"vertex sur plus de 2 edges dans une face."<<endl;
297 }
298 }
299#endif
300 for ( itl.Initialize(LE); itl.More(); itl.Next()) {
301 if (itl.Value().IsEqual(CE)) {
302 LE.Remove(itl);
303 break;
304 }
305 }
306 if (LE.Extent() > 1) {
307 //--------------------------------------------------------------
308 // Plusieurs edges possibles.
309 // - Test les edges differentes de CE , Selection de l edge
310 // pour lequel CV a les U,V les plus proches dans la face
311 // que ceux correspondant a CE.
312 // - Si plusieurs edge donne des representation < la tolerance.
313 // discrimination sur les tangentes.
314 //--------------------------------------------------------------
315 TopLoc_Location L;
316 Standard_Real f,l;
317 TopoDS_Face FForward = F;
318 FForward.Orientation(TopAbs_FORWARD);
319
320 Handle(Geom2d_Curve) C = BRep_Tool::CurveOnSurface(CE,FForward,f,l);
321 Standard_Integer k = 1, kmin = 0;
322 Standard_Real dist,distmin = 100*BRep_Tool::Tolerance(CV);
323 Standard_Real u ;
324 if (CE.Orientation () == TopAbs_FORWARD) u = l;
325 else u = f;
326
327 gp_Pnt2d P2,PV = C->Value(u);
328
329 for ( itl.Initialize(LE); itl.More(); itl.Next()) {
330 const TopoDS_Edge& E = TopoDS::Edge(itl.Value());
331 if (!E.IsSame(CE)) {
332 C = BRep_Tool::CurveOnSurface(E,FForward,f,l);
333 if (E.Orientation () == TopAbs_FORWARD) u = f;
334 else u = l;
335 P2 = C->Value(u);
336 dist = PV.Distance(P2);
337 if ( dist <= distmin) {
338 kmin = k;
339 distmin = dist;
340 }
341 }
342 k++;
343 }
344 if (kmin == 0) return Standard_False;
345
346 k = 1; itl.Initialize(LE);
347 while (k < kmin) {k++; itl.Next();}
348 NE = TopoDS::Edge(itl.Value());
349 LE.Remove(itl);
350 }
351 else if (LE.Extent() == 1) {
352 NE = TopoDS::Edge(LE.First());
353 LE.RemoveFirst();
354 }
355 else {
356 return Standard_False;
357 }
358#ifdef DRAW
359 if (AffichLoop) {
360 DBRep::Set("Selected",NE);
361 }
362
363#endif
364 return Standard_True;
365}
366//=======================================================================
367//function : Store
368//purpose :
369//=======================================================================
370
371static void PurgeNewEdges(TopTools_DataMapOfShapeListOfShape& NewEdges,
372 const TopTools_MapOfShape& UsedEdges)
373{
374 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape it(NewEdges);
375 for (; it.More(); it.Next()) {
376 TopTools_ListOfShape& LNE = NewEdges.ChangeFind(it.Key());
377 TopTools_ListIteratorOfListOfShape itL(LNE);
378 while (itL.More()) {
379 const TopoDS_Shape& NE = itL.Value();
380 if (!UsedEdges.Contains(NE)) {
381 LNE.Remove(itL);
382 }
383 else {
384 itL.Next();
385 }
386 }
387 }
388
389}
390
391//=======================================================================
392//function : Store
393//purpose :
394//=======================================================================
395
396static void StoreInMVE (const TopoDS_Face& F,
397 TopoDS_Edge& E,
398 TopTools_DataMapOfShapeListOfShape& MVE,
399 Standard_Boolean& YaCouture,
400 TopTools_DataMapOfShapeShape& VerticesForSubstitute )
401{
402 TopoDS_Vertex V1, V2, V;
403 TopTools_ListOfShape Empty;
404
405 Standard_Real Tol = 0.001; //5.e-05; //5.e-07;
406// gp_Pnt P1, P2, P;
407 gp_Pnt P1, P;
408 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape Mapit;
409 BRep_Builder BB;
410 for (Mapit.Initialize( MVE ); Mapit.More(); Mapit.Next())
411 {
412 V = TopoDS::Vertex( Mapit.Key() );
413 P = BRep_Tool::Pnt( V );
414 TopTools_ListOfShape VList;
415 TopoDS_Iterator VerExp( E );
416 for (; VerExp.More(); VerExp.Next())
417 VList.Append( VerExp.Value() );
418 TopTools_ListIteratorOfListOfShape itl( VList );
419 for (; itl.More(); itl.Next())
420 {
421 V1 = TopoDS::Vertex( itl.Value() );
422 P1 = BRep_Tool::Pnt( V1 );
423 if (P.IsEqual( P1, Tol ) && !V.IsSame(V1))
424 {
425 V.Orientation( V1.Orientation() );
426 if (VerticesForSubstitute.IsBound( V1 ))
427 {
428 TopoDS_Shape OldNewV = VerticesForSubstitute( V1 );
429 if (! OldNewV.IsSame( V ))
430 {
431 VerticesForSubstitute.Bind( OldNewV, V );
432 VerticesForSubstitute( V1 ) = V;
433 }
434 }
435 else
436 {
437 if (VerticesForSubstitute.IsBound( V ))
438 {
439 TopoDS_Shape NewNewV = VerticesForSubstitute( V );
440 if (! NewNewV.IsSame( V1 ))
441 VerticesForSubstitute.Bind( V1, NewNewV );
442 }
443 else
444 {
445 VerticesForSubstitute.Bind( V1, V );
446 TopTools_DataMapIteratorOfDataMapOfShapeShape mapit( VerticesForSubstitute );
447 for (; mapit.More(); mapit.Next())
448 if (mapit.Value().IsSame( V1 ))
449 VerticesForSubstitute( mapit.Key() ) = V;
450 }
451 }
452 E.Free( Standard_True );
453 BB.Remove( E, V1 );
454 BB.Add( E, V );
455 }
456 }
457 }
458
459 TopExp::Vertices(E,V1,V2);
460 if( V1.IsNull() && V2.IsNull() ){ YaCouture = Standard_False; return; }
461 if (!MVE.IsBound(V1)) {
462 MVE.Bind(V1,Empty);
463 }
464 MVE(V1).Append(E);
465 if (!V1.IsSame(V2)) {
466 if (!MVE.IsBound(V2)) {
467 MVE.Bind(V2,Empty);
468 }
469 MVE(V2).Append(E);
470 }
471 TopLoc_Location L ;
472 Handle(Geom_Surface) S = BRep_Tool::Surface(F,L);
473 if (BRep_Tool::IsClosed(E,S,L)) {
474 MVE(V2).Append(E.Reversed());
475 if (!V1.IsSame(V2)) {
476 MVE(V1).Append(E.Reversed());
477 }
478 YaCouture = Standard_True;
479 }
480}
481
482//=======================================================================
483//function : Perform
484//purpose :
485//=======================================================================
486
487void BRepAlgo_Loop::Perform()
488{
489 TopTools_DataMapIteratorOfDataMapOfShapeListOfShape Mapit;
490 TopTools_ListIteratorOfListOfShape itl;
491 TopoDS_Vertex V1,V2;
492 Standard_Boolean YaCouture = Standard_False;
493
494#ifdef DEB
495 if (AffichLoop) {
496 cout <<"NewLoop"<<endl;
497 Standard_Integer NbEdges = 1;
498 NbLoops++;
499#ifdef DRAW
500 sprintf(name,"FLoop_%d",NbLoops);
501 DBRep::Set(name,myFace);
502#endif
503 for (Mapit.Initialize(myVerOnEdges); Mapit.More(); Mapit.Next()) {
504 const TopoDS_Edge& E = TopoDS::Edge(Mapit.Key());
505#ifdef DRAW
506 sprintf(name,"EEE_%d_%d",NbLoops,NbEdges++);
507 DBRep::Set(name,E);
508#endif
509 }
510 for (itl.Initialize(myConstEdges); itl.More(); itl.Next()) {
511 const TopoDS_Edge& E = TopoDS::Edge(itl.Value());
512#ifdef DRAW
513 sprintf(name,"EEE_%d_%d",NbLoops,NbEdges++);
514 DBRep::Set(name,E);
515#endif
516 }
517 }
518#endif
519
520 //------------------------------------------------
521 // Decoupe des edges
522 //------------------------------------------------
523 for (Mapit.Initialize(myVerOnEdges); Mapit.More(); Mapit.Next()) {
524 TopTools_ListOfShape LCE;
525
526 CutEdge (TopoDS::Edge(Mapit.Key()),Mapit.Value(), LCE);
527
528 myNewEdges.Bind(Mapit.Key(),LCE);
529 }
530 //-----------------------------------
531 // Construction map vertex => edges
532 //-----------------------------------
533 TopTools_DataMapOfShapeListOfShape MVE;
534
535 // ajout des edges decoupees.
536 for (Mapit.Initialize(myNewEdges); Mapit.More(); Mapit.Next()) {
537 for (itl.Initialize(myNewEdges(Mapit.Key())); itl.More(); itl.Next()) {
538 TopoDS_Edge& E = TopoDS::Edge(itl.Value());
539 StoreInMVE(myFace,E,MVE,YaCouture,myVerticesForSubstitute);
540 }
541 }
542
543 // ajout des edges const
544 // Les edges de couture peuvent etre doubles ou non dans myConstEdges
545 // => appel une seule fois StoreInMVE qui se charge de les doubler
546 TopTools_MapOfShape DejaVu;
547 for (itl.Initialize(myConstEdges); itl.More(); itl.Next()) {
548 TopoDS_Edge& E = TopoDS::Edge(itl.Value());
549 if (DejaVu.Add(E))
550 StoreInMVE(myFace,E,MVE,YaCouture,myVerticesForSubstitute);
551 }
552
553#ifdef DRAW
554 if (AffichLoop) {
555 cout <<"NewLoop"<<endl;
556 Standard_Integer NbEdges = 1;
557 TopTools_MapOfShape Done;
558 for (Mapit.Initialize(MVE); Mapit.More();Mapit.Next()) {
559 for (itl.Initialize(Mapit.Value()); itl.More(); itl.Next()) {
560 TopoDS_Edge& E = TopoDS::Edge(itl.Value());
561 if (Done.Add(E)) {
562 sprintf(name,"EEC_%d_%d",NbLoops,NbEdges++);
563 DBRep::Set(name,E);
564 }
565 }
566 }
567 }
568#endif
569
570 //-----------------------------------------------
571 // Construction des wires et des nouvelles faces.
572 //----------------------------------------------
573 TopoDS_Vertex VF,VL,CV;
574 TopoDS_Edge CE,NE,EF;
575 BRep_Builder B;
576 TopoDS_Wire NW;
577 Standard_Boolean End;
578
579 TopTools_MapOfShape UsedEdges;
580
581 while (!MVE.IsEmpty()) {
582 B.MakeWire(NW);
583 //--------------------------------
584 // Suppression des edges pendants.
585 //--------------------------------
586 RemovePendingEdges(MVE);
587
588 if (MVE.IsEmpty()) break;
589 //--------------------------------
590 // Edge de depart.
591 //--------------------------------
592 Mapit.Initialize(MVE);
593 EF = CE = TopoDS::Edge(Mapit.Value().First());
594 TopExp::Vertices(CE,V1,V2);
595 //--------------------------------
596 // VF vertex debut du nouveau wire
597 //--------------------------------
598 if (CE.Orientation() == TopAbs_FORWARD) { CV = VF = V1;}
599 else { CV = VF = V2;}
600 if (!MVE.IsBound(CV)) continue;
601 for ( itl.Initialize(MVE(CV)); itl.More(); itl.Next()) {
602 if (itl.Value().IsEqual(CE)) {
603 MVE(CV).Remove(itl);
604 break;
605 }
606 }
607 End = Standard_False;
608
609 while (!End) {
610 //-------------------------------
611 // Construction d un wire.
612 //-------------------------------
613 TopExp::Vertices(CE,V1,V2);
614 if (!CV.IsSame(V1)) CV = V1; else CV = V2;
615
616 B.Add (NW,CE);
617 UsedEdges.Add(CE);
618
619 if (!MVE.IsBound(CV) || MVE(CV).IsEmpty()) {
620 End = Standard_True;
621 }
622 else {
623 End = !SelectEdge(myFace,CE,CV,NE,MVE(CV));
624 if (!End) {
625 CE = NE;
626 if (MVE(CV).IsEmpty()) MVE.UnBind(CV);
627 }
628 }
629 }
630 //--------------------------------------------------
631 // Ajout du nouveau wire dans l ensemble des wires
632 //------------------------------------------------
633 Standard_Real Tol = 0.001; //5.e-05; //5.e-07;
634 TopExp_Explorer explo( NW, TopAbs_VERTEX );
635 for (; explo.More(); explo.Next())
636 {
637 const TopoDS_Vertex& aV = TopoDS::Vertex( explo.Current() );
638 Handle(BRep_TVertex)& TV = *((Handle(BRep_TVertex)*) &(aV).TShape());
639 TV->Tolerance( Tol );
640 TV->Modified( Standard_True );
641 }
642 for (explo.Init( NW, TopAbs_EDGE ); explo.More(); explo.Next())
643 {
644 const TopoDS_Edge& aE = TopoDS::Edge( explo.Current() );
645 Handle(BRep_TEdge)& TE = *((Handle(BRep_TEdge)*) &(aE).TShape());
646 TE->Tolerance( Tol );
647 TE->Modified( Standard_True );
648 }
649
650 if (VF.IsSame(CV) && SamePnt2d(VF,EF,CE,myFace))
651 myNewWires.Append (NW);
652 else {
653#ifdef DEB
654 cout <<"BRepAlgo_Loop: Open Wire"<<endl;
655 if (AffichLoop)
656 cout << "OpenWire is : NW_"<<NbLoops<<"_"<<NbWires<<endl;
657#endif
658 }
659#ifdef DRAW
660 if (AffichLoop) {
661 sprintf(name,"NW_%d_%d",NbLoops,NbWires++);
662 DBRep::Set(name,NW);
663 }
664#endif
665 }
666
667 PurgeNewEdges(myNewEdges,UsedEdges);
668}
669
670//=======================================================================
671//function : CutEdges
672//purpose :
673//=======================================================================
674
675void BRepAlgo_Loop::CutEdge (const TopoDS_Edge& E,
676 const TopTools_ListOfShape& VOnE,
677 TopTools_ListOfShape& NE ) const
678{
679 TopoDS_Shape aLocalE = E.Oriented(TopAbs_FORWARD);
680 TopoDS_Edge WE = TopoDS::Edge(aLocalE);
681// TopoDS_Edge WE = TopoDS::Edge(E.Oriented(TopAbs_FORWARD));
682
683 Standard_Real U1,U2;
684 TopoDS_Vertex V1,V2;
685 TopTools_SequenceOfShape SV;
686 TopTools_ListIteratorOfListOfShape it(VOnE);
687 BRep_Builder B;
688
689 for ( ; it.More(); it.Next()) {
690 SV.Append(it.Value());
691 }
692 //--------------------------------
693 // Tri des vertex sur l edge.
694 //--------------------------------
695 Bubble (WE,SV);
696
697 Standard_Integer NbVer = SV.Length();
698 //----------------------------------------------------------------
699 // Construction des nouvelles edges.
700 // Remarque : les vertex extremites de l edges ne sont pas
701 // forcement dans la liste des vertex
702 //----------------------------------------------------------------
703 if (SV.IsEmpty()) {
704 NE.Append(E);
705 return;
706 }
707 TopoDS_Vertex VF,VL;
708 Standard_Real f,l;
709 BRep_Tool::Range(WE,f,l);
710 TopExp::Vertices(WE,VF,VL);
711
712 if (NbVer == 2) {
713 if (SV(1).IsEqual(VF) && SV(2).IsEqual(VL)) {
714 NE.Append(E);
715#ifdef DRAW
716 if (AffichLoop) {
717 DBRep::Set("ECOpied",E);
718 }
719#endif
720 return;
721 }
722 }
723 //----------------------------------------------------
724 // Traitement des edges fermes
725 // Si un vertex d intersection est sur le vertex
726 // commun il doit apparaitre eb debut et en fin de SV.
727 //----------------------------------------------------
728 TopoDS_Vertex VCEI;
729 if (!VF.IsNull() && VF.IsSame(VL)) {
730 VCEI = UpdateClosedEdge(WE,SV);
731 if (!VCEI.IsNull()) {
732 TopoDS_Shape aLocalV = VCEI.Oriented(TopAbs_FORWARD);
733 VF = TopoDS::Vertex(aLocalV);
734 aLocalV = VCEI.Oriented(TopAbs_REVERSED);
735 VL = TopoDS::Vertex(aLocalV);
736// VF = TopoDS::Vertex(VCEI.Oriented(TopAbs_FORWARD));
737// VL = TopoDS::Vertex(VCEI.Oriented(TopAbs_REVERSED));
738 }
739 SV.Prepend(VF);
740 SV.Append(VL);
741 }
742 else {
743 //-----------------------------------------
744 // Ajout eventuel des extremites de l edge.
745 //-----------------------------------------
746 if (!VF.IsNull() && !VF.IsSame(SV.First())) SV.Prepend(VF);
747 if (!VL.IsNull() && !VL.IsSame(SV.Last ())) SV.Append (VL);
748 }
749
750 while (!SV.IsEmpty()) {
751 while (!SV.IsEmpty() &&
752 SV.First().Orientation() != TopAbs_FORWARD) {
753 SV.Remove(1);
754 }
755 if (SV.IsEmpty())
756 break;
757 V1 = TopoDS::Vertex(SV.First());
758 SV.Remove(1);
759 if (SV.IsEmpty())
760 break;
761 if (SV.First().Orientation() == TopAbs_REVERSED) {
762 V2 = TopoDS::Vertex(SV.First());
763 SV.Remove(1);
764 //-------------------------------------------
765 // Copie de l edge et restriction par V1 V2.
766 //-------------------------------------------
767 TopoDS_Shape NewEdge = WE.EmptyCopied();
768 TopoDS_Shape aLocalEdge = V1.Oriented(TopAbs_FORWARD);
769 B.Add (NewEdge,aLocalEdge);
770 aLocalEdge = V2.Oriented(TopAbs_REVERSED);
771 B.Add (TopoDS::Edge(NewEdge),aLocalEdge);
772// B.Add (NewEdge,V1.Oriented(TopAbs_FORWARD));
773// B.Add (NewEdge,V2.Oriented(TopAbs_REVERSED));
774 if (V1.IsSame(VF))
775 U1 = f;
776 else
777// U1=BRep_Tool::Parameter
778// (TopoDS::Vertex(V1.Oriented(TopAbs_INTERNAL)),WE);
779 {
780 TopoDS_Shape aLocalV = V1.Oriented(TopAbs_INTERNAL);
781 U1=BRep_Tool::Parameter(TopoDS::Vertex(aLocalV),WE);
782 }
783 if (V2.IsSame(VL))
784 U2 = l;
785 else
786 {
787 TopoDS_Shape aLocalV = V2.Oriented(TopAbs_INTERNAL);
788 U2=BRep_Tool::Parameter(TopoDS::Vertex(aLocalV),WE);
789// U2=BRep_Tool::Parameter
790// (TopoDS::Vertex(V2.Oriented(TopAbs_INTERNAL)),WE);
791 }
792 B.Range (TopoDS::Edge(NewEdge),U1,U2);
793#ifdef DRAW
794 if (AffichLoop) {
795 DBRep::Set("Cut",NewEdge);
796 }
797#endif
798 NE.Append(NewEdge.Oriented(E.Orientation()));
799 }
800 }
801
802 //Remove edges with size <= tolerance
803 Standard_Real Tol = 0.001; //5.e-05; //5.e-07;
804 it.Initialize(NE);
805 while (it.More())
806 {
807 // skl : I change "E" to "EE"
808 TopoDS_Edge EE = TopoDS::Edge( it.Value() );
809 Standard_Real fpar, lpar;
810 BRep_Tool::Range( EE, fpar, lpar );
811 if (lpar - fpar <= Precision::Confusion())
812 NE.Remove(it);
813 else
814 {
815 gp_Pnt2d pf, pl;
816 BRep_Tool::UVPoints( EE, myFace, pf, pl );
817 if (pf.Distance(pl) <= Tol && !EE.Closed())
818 NE.Remove(it);
819 else
820 it.Next();
821 }
822 }
823}
824
825//=======================================================================
826//function : NewWires
827//purpose :
828//=======================================================================
829
830const TopTools_ListOfShape& BRepAlgo_Loop::NewWires() const
831{
832 return myNewWires;
833}
834
835//=======================================================================
836//function : NewFaces
837//purpose :
838//=======================================================================
839
840const TopTools_ListOfShape& BRepAlgo_Loop::NewFaces() const
841{
842 return myNewFaces;
843}
844
845//=======================================================================
846//function : WiresToFaces
847//purpose :
848//=======================================================================
849
850void BRepAlgo_Loop::WiresToFaces()
851{
852 if (!myNewWires.IsEmpty()) {
853 BRepAlgo_FaceRestrictor FR;
854 TopoDS_Shape aLocalS = myFace.Oriented(TopAbs_FORWARD);
855 FR.Init (TopoDS::Face(aLocalS),Standard_False);
856// FR.Init (TopoDS::Face(myFace.Oriented(TopAbs_FORWARD)),
857// Standard_False);
858 TopTools_ListIteratorOfListOfShape it(myNewWires);
859 for (; it.More(); it.Next()) {
860 FR.Add(TopoDS::Wire(it.Value()));
861 }
862
863 FR.Perform();
864
865 if (FR.IsDone()) {
866 TopAbs_Orientation OriF = myFace.Orientation();
867 for (; FR.More(); FR.Next()) {
868 myNewFaces.Append(FR.Current().Oriented(OriF));
869 }
870 }
871 }
872}
873
874
875//=======================================================================
876//function : NewEdges
877//purpose :
878//=======================================================================
879
880const TopTools_ListOfShape& BRepAlgo_Loop::NewEdges(const TopoDS_Edge& E) const
881{
882 return myNewEdges(E);
883}
884
885//=======================================================================
886//function : GetVerticesForSubstitute
887//purpose :
888//=======================================================================
889
890void BRepAlgo_Loop::GetVerticesForSubstitute( TopTools_DataMapOfShapeShape& VerVerMap ) const
891{
892 VerVerMap = myVerticesForSubstitute;
893}
894//=======================================================================
895//function : VerticesForSubstitute
896//purpose :
897//=======================================================================
898
899void BRepAlgo_Loop::VerticesForSubstitute( TopTools_DataMapOfShapeShape& VerVerMap )
900{
901 myVerticesForSubstitute = VerVerMap;
902}