0025453: SIGSEGV in BRepFill_Sweep::BuildShell
[occt.git] / src / BRepFill / BRepFill_Sweep.cxx
CommitLineData
b311480e 1// Created on: 1998-01-07
2// Created by: Philippe MANGIN
3// Copyright (c) 1998-1999 Matra Datavision
973c2be1 4// Copyright (c) 1999-2014 OPEN CASCADE SAS
b311480e 5//
973c2be1 6// This file is part of Open CASCADE Technology software library.
b311480e 7//
d5f74e42 8// This library is free software; you can redistribute it and/or modify it under
9// the terms of the GNU Lesser General Public License version 2.1 as published
973c2be1 10// by the Free Software Foundation, with special exception defined in the file
11// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12// distribution for complete text of the license and disclaimer of any warranty.
b311480e 13//
973c2be1 14// Alternatively, this file may be used under the terms of Open CASCADE
15// commercial license or contractual agreement.
7fd59977 16
17#include <stdio.h>
18
19#include <BRepFill_Sweep.ixx>
20
21#include <BRepFill_SectionLaw.hxx>
22//#include <BRepFill_TrimCorner.hxx>
23#include <BRepFill_CurveConstraint.hxx>
24
25#include <GeomFill_SectionLaw.hxx>
26#include <GeomFill_LocationLaw.hxx>
27#include <GeomFill_Sweep.hxx>
28
29// modified by NIZHNY-MKK Wed Oct 22 12:25:45 2003
30#include <BRepFill_TrimShellCorner.hxx>
31
32//#include <GeomPlate_BuildPlateSurface.hxx>
33//#include <GeomPlate_Surface.hxx>
34//#include <GeomPlate_PointConstraint.hxx>
35
36#include <gp_Pnt2d.hxx>
37#include <gp_Vec2d.hxx>
38#include <Bnd_Box.hxx>
39
40#include <Geom_Surface.hxx>
41#include <Geom_SurfaceOfRevolution.hxx>
42#include <Geom_RectangularTrimmedSurface.hxx>
43#include <Geom_Plane.hxx>
44#include <Geom_Curve.hxx>
45#include <Geom_BezierCurve.hxx>
46#include <Geom_BSplineCurve.hxx>
47#include <Geom2d_Line.hxx>
48#include <Geom2d_Curve.hxx>
49#include <Geom2d_TrimmedCurve.hxx>
50#include <GeomLib.hxx>
51#include <GeomLib_IsPlanarSurface.hxx>
52#include <BRepLib_FindSurface.hxx>
53#include <GeomConvert_ApproxSurface.hxx>
54
55#include <BRepAdaptor_HCurve.hxx>
56#include <BRepAdaptor_HCurve2d.hxx>
57#include <BRepAdaptor_HSurface.hxx>
58#include <Adaptor3d_HCurveOnSurface.hxx>
59#include <GeomAdaptor_HSurface.hxx>
60#include <GeomAdaptor_HCurve.hxx>
61#include <Geom2dAdaptor_HCurve.hxx>
62#include <Approx_CurveOnSurface.hxx>
63#include <Approx_SameParameter.hxx>
64#include <GCPnts_AbscissaPoint.hxx>
65
66#include <BRep_Builder.hxx>
67#include <BRep_Tool.hxx>
68#include <BRep_ListIteratorOfListOfCurveRepresentation.hxx>
69#include <BRep_TEdge.hxx>
70#include <BRep_TVertex.hxx>
71#include <BRep_CurveRepresentation.hxx>
72#include <BRep_GCurve.hxx>
73
74#include <BRepLib.hxx>
75#include <BRepLib_MakeEdge.hxx>
76#include <BRepLib_MakeFace.hxx>
77#include <BRepLib_FaceError.hxx>
78
79#include <TopoDS.hxx>
80#include <TopoDS_Edge.hxx>
81#include <TopoDS_Face.hxx>
82#include <TopoDS_Compound.hxx>
83#include <TopoDS_Shell.hxx>
84#include <TopExp.hxx>
85#include <TopExp_Explorer.hxx>
86#include <TopAbs_Orientation.hxx>
87
88#include <TColStd_HArray1OfInteger.hxx>
89#include <TColStd_Array2OfInteger.hxx>
90#include <TColStd_Array1OfReal.hxx>
91#include <TColStd_Array2OfReal.hxx>
92#include <TColGeom_Array2OfSurface.hxx>
93#include <TColgp_Array1OfPnt.hxx>
c8ea5b8e 94#include <TColStd_Array1OfBoolean.hxx>
7fd59977 95
96#include <TopTools_Array1OfShape.hxx>
97#include <TopTools_Array2OfShape.hxx>
98#include <TopTools_HArray2OfShape.hxx>
99#include <TopTools_HArray1OfShape.hxx>
100#include <TopTools_ListIteratorOfListOfShape.hxx>
101#include <TopTools_ListOfShape.hxx>
102#include <TopTools_IndexedDataMapOfShapeListOfShape.hxx>
c8ea5b8e 103#include <TopTools_SequenceOfShape.hxx>
7fd59977 104#include <BRepTools_WireExplorer.hxx>
105
106#include <Standard_ConstructionError.hxx>
107#include <Precision.hxx>
108#include <BRepBuilderAPI_MakeWire.hxx>
109
110#include <BRepTools_Substitution.hxx>
111#include <TopTools_DataMapIteratorOfDataMapOfShapeShape.hxx>
112#include <TopoDS_Iterator.hxx>
113
114//OCC500(apo)
115#include <BRepCheck_Edge.hxx>
116
117#ifdef DRAW
118#include <Draw.hxx>
119#include <DrawTrSurf.hxx>
120#include <DBRep.hxx>
121static Standard_Boolean Affich = 0;
122#endif
123
124//=======================================================================
125//function : NumberOfPoles
126//purpose :
127//=======================================================================
128static Standard_Integer NumberOfPoles(const TopoDS_Wire& W)
129{
130 Standard_Integer NbPoints = 0;
131
132 TopoDS_Iterator iter(W);
133 for (; iter.More(); iter.Next())
134 {
135 BRepAdaptor_Curve c(TopoDS::Edge(iter.Value()));
136
137 Standard_Real dfUf = c.FirstParameter();
138 Standard_Real dfUl = c.LastParameter();
139 if (IsEqual(dfUf,dfUl))
140 // Degenerate
141 continue;
142
143 switch (c.GetType())
144 {
145 case GeomAbs_BezierCurve:
146 {
147 // Put all poles for bezier
148 Handle(Geom_BezierCurve) GC = c.Bezier();
149 Standard_Integer iNbPol = GC->NbPoles();
150 if ( iNbPol >= 2)
151 NbPoints += iNbPol;
152 break;
153 }
154 case GeomAbs_BSplineCurve:
155 {
156 // Put all poles for bspline
157 Handle(Geom_BSplineCurve) GC = c.BSpline();
158 Standard_Integer iNbPol = GC->NbPoles();
159 if ( iNbPol >= 2)
160 NbPoints += iNbPol;
161 break;
162 }
163 case GeomAbs_Line:
164 {
165 NbPoints += 2;
166 break;
167 }
168 case GeomAbs_Circle:
169 case GeomAbs_Ellipse:
170 case GeomAbs_Hyperbola:
171 case GeomAbs_Parabola:
172 {
173 NbPoints += 4;
174 break;
175 }
176 default:
177 NbPoints += 15 + c.NbIntervals(GeomAbs_C3);
178 } // switch (c.GetType()) ...
179 } // for (; iter.More(); iter.Next())
180
181 return NbPoints;
182}
183
184//=======================================================================
185//function : HasPCurves
186//purpose :
187//=======================================================================
188static Standard_Boolean HasPCurves(const TopoDS_Edge& E)
189{
190 Standard_Boolean haspcurves = Standard_False;
191
192 BRep_ListIteratorOfListOfCurveRepresentation itcr
193 ((*((Handle(BRep_TEdge)*)&E.TShape()))->Curves());
194 for (; itcr.More(); itcr.Next())
195 {
196 const Handle(BRep_CurveRepresentation)& cr = itcr.Value();
197 if (cr->IsCurveOnSurface())
198 {
199 haspcurves = Standard_True;
200 break;
201 }
202 }
203 return haspcurves;
204}
205
206//=======================================================================
207//function : Translate
0d969553 208//purpose : Copy a column from one table to another.
7fd59977 209//=======================================================================
210static void Translate(const Handle(TopTools_HArray2OfShape)& ArrayIn,
211 const Standard_Integer In,
212 Handle(TopTools_HArray2OfShape)& ArrayOut,
213 const Standard_Integer Out)
214{
215 Standard_Integer ii, Nb;
216 Nb = ArrayOut->ColLength();
217 for (ii=1; ii<=Nb; ii++) {
218 ArrayOut->SetValue(ii, Out, ArrayIn->Value(ii, In));
219 }
220}
221
222
223//=======================================================================
224//function : Box
0d969553 225//purpose : Bounding box of a section.
7fd59977 226//=======================================================================
227static void Box(Handle(GeomFill_SectionLaw)& Sec,
228 const Standard_Real U,
229 Bnd_Box& Box)
230
231{
232 Standard_Integer NbPoles, bid;
233 Box.SetVoid();
234 Sec->SectionShape(NbPoles, bid, bid);
235 TColgp_Array1OfPnt Poles(1, NbPoles);
236 TColStd_Array1OfReal W(1, NbPoles);
237 Sec->D0(U, Poles, W);
238 for (Standard_Integer ii=1; ii<=NbPoles; ii++) {
239 Box.Add(Poles(ii));
240 }
241}
242
243//=======================================================================
244//function : Couture
0d969553
Y
245//purpose : Check if E is an edge of sewing on S
246// and make the representation HadHoc
7fd59977 247//=======================================================================
248static Handle(Geom2d_Curve) Couture(const TopoDS_Edge& E,
249 const Handle(Geom_Surface)& S,
250 const TopLoc_Location& L)
251{
252 TopLoc_Location l = L.Predivided(E.Location());
253 Standard_Boolean Eisreversed = (E.Orientation() == TopAbs_REVERSED);
254
255 // find the representation
256 BRep_ListIteratorOfListOfCurveRepresentation itcr
257 ((*((Handle(BRep_TEdge)*)&E.TShape()))->ChangeCurves());
258
259 while (itcr.More()) {
260 Handle(BRep_CurveRepresentation)& cr = itcr.Value();
261 if (cr->IsCurveOnSurface(S,l)) {
262 Handle(BRep_GCurve)& GC = *((Handle(BRep_GCurve)*)&cr);
263 if (GC->IsCurveOnClosedSurface() && Eisreversed)
264 return GC->PCurve2();
265 else
266 return GC->PCurve();
267 }
268 itcr.Next();
269 }
270 Handle(Geom2d_Curve) pc;
271 pc.Nullify();
272 return pc;
273}
274
275//=======================================================================
276//function : CheckSameParameter
0d969553 277//purpose : Check a posteriori that sameparameter has worked correctly
7fd59977 278//=======================================================================
279
280static Standard_Boolean CheckSameParameter
281(const Handle(Adaptor3d_HCurve)& C3d,
471ce736 282 const Handle(Geom2d_Curve)& Pcurv,
7fd59977 283 const Handle(Adaptor3d_HSurface)& S,
284 const Standard_Real tol3d,
285 Standard_Real& tolreached)
286{
287 tolreached = 0.;
288 Standard_Real f = C3d->FirstParameter();
289 Standard_Real l = C3d->LastParameter();
290 Standard_Integer nbp = 45;
291 Standard_Real step = 1./(nbp -1);
292 for(Standard_Integer i = 0; i < nbp; i++){
293 Standard_Real t,u,v;
294 t = step * i;
295 t = (1-t) * f + t * l;
296 Pcurv->Value(t).Coord(u,v);
297 gp_Pnt pS = S->Value(u,v);
298 gp_Pnt pC = C3d->Value(t);
299 Standard_Real d2 = pS.SquareDistance(pC);
300 tolreached = Max(tolreached,d2);
301 }
302 tolreached = sqrt(tolreached);
303 if(tolreached > tol3d){
304 tolreached *= 2.;
305 return Standard_False;
306 }
307 tolreached *= 2.;
308 tolreached = Max(tolreached,Precision::Confusion());
309 return Standard_True;
310}
311
312//=======================================================================
313//function : SameParameter
0d969553
Y
314//purpose : Encapsulation of Sameparameter
315// Boolean informs if the pcurve was computed or not...
316// The tolerance is always OK.
7fd59977 317//=======================================================================
318
319static Standard_Boolean SameParameter(TopoDS_Edge& E,
320 Handle(Geom2d_Curve)& Pcurv,
321 const Handle(Geom_Surface)& Surf,
322 const Standard_Real tol3d,
323 Standard_Real& tolreached)
324{
325 //Handle(BRepAdaptor_HCurve) C3d = new (BRepAdaptor_HCurve)(E);
326 Standard_Real f, l;
327 Handle(Geom_Curve) C3d = BRep_Tool::Curve( E, f, l );
328 GeomAdaptor_Curve GAC3d( C3d, f, l );
329 Handle(GeomAdaptor_HCurve) HC3d = new GeomAdaptor_HCurve( GAC3d );
330
331 Handle(GeomAdaptor_HSurface) S = new (GeomAdaptor_HSurface)(Surf);
332 Standard_Real ResTol;
333
334 if(CheckSameParameter( HC3d, Pcurv, S, tol3d, tolreached ))
335 return Standard_True;
336
337 if (!HasPCurves(E))
338 {
339 Handle(Geom2dAdaptor_HCurve) HC2d = new Geom2dAdaptor_HCurve( Pcurv );
340 Approx_CurveOnSurface AppCurve(HC2d, S, HC2d->FirstParameter(), HC2d->LastParameter(),
341 Precision::Confusion(), GeomAbs_C1, 10, 10, Standard_True);
342 if (AppCurve.IsDone() && AppCurve.HasResult())
343 {
344 C3d = AppCurve.Curve3d();
345 tolreached = AppCurve.MaxError3d();
346 BRep_Builder B;
347 B.UpdateEdge( E, C3d, tolreached );
348 return Standard_True;
349 }
350 }
351
352 Approx_SameParameter sp( HC3d, Pcurv, S, tol3d );
353 if(sp.IsDone() && !sp.IsSameParameter()) Pcurv = sp.Curve2d();
354 else if(!sp.IsDone() && !sp.IsSameParameter()){
0797d9d3 355#ifdef OCCT_DEBUG
7fd59977 356 cout<<"echec SameParameter"<<endl;
357#endif
358 return Standard_False;
359 }
360
361 ResTol = sp.TolReached();
362 if(ResTol > tolreached ){
0797d9d3 363#ifdef OCCT_DEBUG
0d969553
Y
364 cout<<"SameParameter : Tolerance not reached!"<<endl;
365 cout<<"tol visee : "<<tol3d<<" tol obtained : "<<ResTol<<endl;
7fd59977 366#endif
367 return Standard_False;
368 }
369 else {
370 tolreached = 1.1*ResTol;
371 if(sp.IsDone() && !sp.IsSameParameter()) Pcurv = sp.Curve2d();
372 }
373 return Standard_True;
374}
375
376//=======================================================================
0d969553
Y
377//Objet : Orientate an edge of natural restriction
378// : General
7fd59977 379//=======================================================================
380static void Oriente(const Handle(Geom_Surface)& S,
381 TopoDS_Edge& E)
382{
383 gp_Pnt2d P;
384 gp_Vec2d D, URef(1, 0), VRef(0, 1);
385 Standard_Boolean isuiso, isfirst, isopposite;
386 Standard_Real UFirst, ULast, VFirst, VLast, f, l;
387 S->Bounds(UFirst, ULast, VFirst, VLast);
388 Handle(Geom2d_Curve) C;
389 TopLoc_Location bid;
390
391 C = BRep_Tool::CurveOnSurface(E, S, bid, f, l);
392 C->D1((f+l)/2, P, D);
393
394 isuiso = D.IsParallel(VRef, 0.1);
395
396 if ( isuiso ) {
397 isfirst = (Abs (P.X()-UFirst) < Precision::Confusion());
398 isopposite = D.IsOpposite(VRef, 0.1);
399 E.Orientation(TopAbs_REVERSED);
400 }
401 else {
402 isfirst = (Abs (P.Y()-VFirst) < Precision::Confusion());
403 isopposite = D.IsOpposite(URef, 0.1);
404 E.Orientation(TopAbs_FORWARD);
405 }
406
407 if (!isfirst) E.Reverse();
408 if (isopposite) E.Reverse();
409}
410//OCC500(apo)->
411static void UpdateEdgeOnPlane(const TopoDS_Face& F, const TopoDS_Edge& E,
412 const BRep_Builder& BB)
413{
414 Standard_Real f, l;
415 Handle(Geom2d_Curve) C2d = BRep_Tool::CurveOnSurface(E,F,f,l);
416 Handle(Geom_Surface) S = BRep_Tool::Surface(F);
417 TopLoc_Location Loc;
418 Standard_Real Tol = BRep_Tool::Tolerance(E);
419 BB.UpdateEdge(E, C2d, S, Loc, Tol);
420 BRepCheck_Edge Check(E);
421 Tol = Max(Tol,Check.Tolerance());
422 BB.UpdateEdge(E, Tol);
423 TopoDS_Vertex V;
424 Tol *= 1.01;
425 V = TopExp::FirstVertex(E);
426 if(BRep_Tool::Tolerance(V) < Tol) BB.UpdateVertex(V, Tol);
427 V = TopExp::LastVertex(E);
428 if(BRep_Tool::Tolerance(V) < Tol) BB.UpdateVertex(V, Tol);
429}
430//<-OCC500(apo)
431//=======================================================================
432//Function : BuildFace
0d969553
Y
433//Objet : Construct a Face via a surface and 4 Edges (natural borders)
434// : Only one Hypothesis : isos u and v are switched :
435// Edge1/3 are iso u (recp v)
436// Edge2/4 are iso v (recp u)
7fd59977 437//=======================================================================
438static void BuildFace(const Handle(Geom_Surface)& S,
439 const TopoDS_Edge& E1,
440 const TopoDS_Edge& E2,
441 const TopoDS_Edge& E3,
442 const TopoDS_Edge& E4,
443 TopTools_DataMapOfShapeShape& EEmap,
444 const Standard_Boolean ExchUV,
445 const Standard_Boolean UReverse,
446 TopoDS_Face& F)
447{
448 Standard_Real Tol;
449// Class BRep_Tool without fields and without Constructor :
450// BRep_Tool BT;
451 TopoDS_Edge e1, e2, E;
452 TopoDS_Wire WW;
453 BRep_Builder BB;
454 BRepBuilderAPI_MakeWire B;
455 TopoDS_Iterator Iter;
456 //gp_Pnt2d P;
457
0d969553 458 //Is the surface planar ?
7fd59977 459 Standard_Real Tol1, Tol2, Tol3, Tol4;
460 Tol1 = BRep_Tool::Tolerance( E1 );
461 Tol2 = BRep_Tool::Tolerance( E2 );
462 Tol3 = BRep_Tool::Tolerance( E3 );
463 Tol4 = BRep_Tool::Tolerance( E4 );
464// Tol = Min( BT.Tolerance(E1), BT.Tolerance(E2));
465 Tol = Min( Tol1, Tol2 );
466// Tol = Min(Tol, Min(BT.Tolerance(E3),BT.Tolerance(E4)));
467 Tol = Min( Tol, Min( Tol3, Tol4 ) );
468 Standard_Boolean IsPlan = Standard_False;
469 Handle(Geom_Plane) thePlane;
470
471 if (!E1.IsSame(E3) && !E2.IsSame(E4)) //exclude cases with seam edges: they are not planar
472 {
473 GeomLib_IsPlanarSurface IsP(S, Tol);
474 if (IsP.IsPlanar())
475 {
476 IsPlan = Standard_True;
477 thePlane = new Geom_Plane( IsP.Plan() );
478 }
479 else
480 {
481 Handle(BRep_TEdge)& TE1 = *((Handle(BRep_TEdge)*)&E1.TShape());
482 Handle(BRep_TEdge)& TE2 = *((Handle(BRep_TEdge)*)&E2.TShape());
483 Handle(BRep_TEdge)& TE3 = *((Handle(BRep_TEdge)*)&E3.TShape());
484 Handle(BRep_TEdge)& TE4 = *((Handle(BRep_TEdge)*)&E4.TShape());
485 TE1->Tolerance( Precision::Confusion() );
486 TE2->Tolerance( Precision::Confusion() );
487 TE3->Tolerance( Precision::Confusion() );
488 TE4->Tolerance( Precision::Confusion() );
489
490 TopoDS_Wire theWire = BRepLib_MakeWire( E1, E2, E3, E4 );
491 Standard_Integer NbPoints = NumberOfPoles( theWire );
492 if (NbPoints <= 100) //limitation for CPU
493 {
494 BRepLib_FindSurface FS( theWire, -1, Standard_True );
495 if (FS.Found())
496 {
497 IsPlan = Standard_True;
498 thePlane = Handle(Geom_Plane)::DownCast(FS.Surface());
499 }
500 }
501 BB.UpdateEdge( E1, Tol1 );
502 BB.UpdateEdge( E2, Tol2 );
503 BB.UpdateEdge( E3, Tol3 );
504 BB.UpdateEdge( E4, Tol4 );
505 }
506 }
507
0d969553 508 // Construction of the wire
7fd59977 509// B.MakeWire(WW);
510 e1 = E1;
511 Oriente(S, e1);
512// if (!IsPlan || !BT.Degenerated(e1))
513 if (!IsPlan || !BRep_Tool::Degenerated(e1))
514 B.Add(e1);
515
516 e2 = E2;
517 Oriente(S, e2);
518// if (!IsPlan || !BT.Degenerated(e2))
519 if (!IsPlan || !BRep_Tool::Degenerated(e2))
520 {
521 B.Add(e2);
522 if (!BRep_Tool::Degenerated(e2))
523 {
524 WW = B.Wire();
525 TopoDS_Shape NewEdge;
526 //take the last edge added to WW
527 for (Iter.Initialize( WW ); Iter.More(); Iter.Next())
528 NewEdge = Iter.Value();
529 if (! e2.IsSame(NewEdge))
530 EEmap.Bind( e2, NewEdge );
531 }
532 }
533
534 if (E3.IsSame(E1)) {
535 E = e1;
536 E.Reverse();
537 }
538 else {
539 E = E3;
540 Oriente(S, E);
541 }
542// if (!IsPlan || !BT.Degenerated(E))
543 if (!IsPlan || !BRep_Tool::Degenerated(E))
544 {
545 B.Add(E);
546 if (!BRep_Tool::Degenerated(E))
547 {
548 WW = B.Wire();
549 TopoDS_Shape NewEdge;
550 //take the last edge added to WW
551 for (Iter.Initialize( WW ); Iter.More(); Iter.Next())
552 NewEdge = Iter.Value();
553 if (! E.IsSame(NewEdge))
554 EEmap.Bind( E, NewEdge );
555 }
556 }
557
558 if (E4.IsSame(E2)) {
559 E = e2;
560 E.Reverse();
561 }
562 else {
563 E = E4;
564 Oriente(S, E);
565 }
566// if (!IsPlan || !BT.Degenerated(E))
567 if (!IsPlan || !BRep_Tool::Degenerated(E))
568 {
569 B.Add(E);
570 if (!BRep_Tool::Degenerated(E))
571 {
572 WW = B.Wire();
573 TopoDS_Shape NewEdge;
574 //take the last edge added to WW
575 for (Iter.Initialize( WW ); Iter.More(); Iter.Next())
576 NewEdge = Iter.Value();
577 if (! E.IsSame(NewEdge))
578 EEmap.Bind( E, NewEdge );
579 }
580 }
581
582 WW = B.Wire();
583#if DRAW
c0695321
A
584 if (Affich)
585 DBRep::Set("wire-on-face", WW);
7fd59977 586#endif
587
0d969553
Y
588// Construction of the face.
589 if (IsPlan) { // Suspend representation 2d
590 // and construct face Plane
7fd59977 591
592 //BRepLib_MakeFace MkF(IsP.Plan(), WW);
593 gp_Pnt aPnt;
594 gp_Vec DU, DV, NS, NP;
595 Standard_Real Ufirst, Ulast, Vfirst, Vlast;
596 S->Bounds( Ufirst, Ulast, Vfirst, Vlast );
597 S->D1( (Ufirst+Ulast)/2., (Vfirst+Vlast)/2., aPnt, DU, DV );
598 NS = DU ^ DV;
599 NP = thePlane->Pln().Axis().Direction();
600 if (NS.Dot(NP) < 0.)
601 thePlane->UReverse();
602 BRepLib_MakeFace MkF( thePlane, WW );
603 if (MkF.Error() != BRepLib_FaceDone) {
0797d9d3 604#ifdef OCCT_DEBUG
7fd59977 605 BRepLib_FaceError Err = MkF.Error();
606 cout << "Planar Face Error :" << Err << endl;
607#endif
608 }
609 else {
610 Handle(Geom2d_Curve) NullC2d;
611 TopLoc_Location Loc;
612 BB.UpdateEdge( E1, NullC2d, S, Loc, Tol1 );
613 BB.UpdateEdge( E2, NullC2d, S, Loc, Tol2 );
614 BB.UpdateEdge( E3, NullC2d, S, Loc, Tol3 );
615 BB.UpdateEdge( E4, NullC2d, S, Loc, Tol4 );
616
617 F = MkF.Face();
618 UpdateEdgeOnPlane(F,E1,BB);
619 UpdateEdgeOnPlane(F,E2,BB);
620 UpdateEdgeOnPlane(F,E3,BB);
621 UpdateEdgeOnPlane(F,E4,BB);
622/*OCC500(apo)->
623 TopLoc_Location Loc;
624 Handle(Geom2d_Curve) NC;
625 NC.Nullify();
626// B.UpdateEdge(E1, NC, S, Loc, BT.Tolerance(E1));
627 BB.UpdateEdge(E1, NC, S, Loc, BRep_Tool::Tolerance(E1));
628// B.UpdateEdge(E2, NC, S, Loc, BT.Tolerance(E2));
629 BB.UpdateEdge(E2, NC, S, Loc, BRep_Tool::Tolerance(E2));
630// B.UpdateEdge(E3, NC, S, Loc, BT.Tolerance(E3));
631 BB.UpdateEdge(E3, NC, S, Loc, BRep_Tool::Tolerance(E3));
632// B.UpdateEdge(E4, NC, S, Loc, BT.Tolerance(E4));
633 BB.UpdateEdge(E4, NC, S, Loc, BRep_Tool::Tolerance(E4));
634<-OCC500(apo)*/
635 }
636 }
637
638 if (!IsPlan) {// Cas Standard : Ajout
639 BB.MakeFace(F, S, Precision::Confusion());
640 BB.Add(F, WW);
641 }
642
643 // Reorientation
644 if (ExchUV) F.Reverse();
645 if (UReverse) F.Reverse();
646}
647
648
649//=======================================================================
650//Fonction : BuildEdge
0d969553 651//Objet : Construct non-closed Edge
7fd59977 652//=======================================================================
653static TopoDS_Edge BuildEdge(Handle(Geom_Curve)& C3d,
654 Handle(Geom2d_Curve)& C2d,
655 Handle(Geom_Surface)& S,
656 const TopoDS_Vertex& VF,
657 const TopoDS_Vertex& VL,
658 const Standard_Real f,
659 const Standard_Real l,
660 const Standard_Real Tol3d)
661{
662 gp_Pnt P1, P2, P;
663 Standard_Real Tol1, Tol2, Tol, d;
664// Class BRep_Tool without fields and without Constructor :
665// BRep_Tool BT;
666 BRep_Builder B;
667 TopoDS_Edge E;
668
669// P1 = BT.Pnt(VF);
670 P1 = BRep_Tool::Pnt(VF);
671// Tol1 = BT.Tolerance(VF);
672 Tol1 = BRep_Tool::Tolerance(VF);
673// P2 = BT.Pnt(VL);
674 P2 = BRep_Tool::Pnt(VL);
675// Tol2 = BT.Tolerance(VF);
676 Tol2 = BRep_Tool::Tolerance(VF);
677 Tol = Max(Tol1, Tol2);
678
679 if (VF.IsSame(VL) ||
680 (P1.Distance(P2) < Tol ) ) {
0d969553 681 // Degenerated case
7fd59977 682 gp_Pnt2d P2d;
683 C2d->D0(f, P2d);
684 S->D0(P2d.X(), P2d.Y(), P);
685 d = P1.Distance(P);
686 if (d > Tol) Tol = d;
687 C2d->D0(l, P2d);
688 S->D0(P2d.X(), P2d.Y(), P);
689 d = P2.Distance(P);
690 if (d > Tol) Tol = d;
691
692 B.UpdateVertex(VF, Tol);
693 B.UpdateVertex(VL, Tol);
694
695 B.MakeEdge(E);
696 B.UpdateEdge(E,C2d,S,TopLoc_Location(), Tol);
697 B.Add(E,VF);
698 B.Add(E,VL);
699 B.Range(E,f,l);
700 B.Degenerated(E, Standard_True);
701
702 return E;
703 }
704
705 C3d->D0(f, P);
706 d = P1.Distance(P);
707 if (d > Tol1)
708 B.UpdateVertex(VF, d);
709
710// P1 = BT.Pnt(VL);
711 P1 = BRep_Tool::Pnt(VL);
712 C3d->D0(l, P);
713 d = P2.Distance(P);
714 if (d > Tol2)
715 B.UpdateVertex(VL, d);
716
717 BRepLib_MakeEdge MkE (C3d, VF, VL, f, l);
0d969553 718 if (!MkE.IsDone()) { // Error of construction !!
7fd59977 719#ifdef DRAW
720 char name[100];
721 sprintf(name,"firstvertex_error");
722 DBRep::Set(name, VF);
723 sprintf(name,"lastvertex_error");
724 DBRep::Set(name, VL);
725 sprintf(name,"curve3d_error");
726 char* Temp = name ;
727 DrawTrSurf::Set(Temp, C3d);
728// DrawTrSurf::Set(name, C3d);
729 Standard_ConstructionError::Raise("BRepFill_Sweep::BuildEdge");
730#endif
731 }
732
733 E = MkE.Edge();
734 TopLoc_Location Loc;
735 B.UpdateEdge(E, C2d, S, Loc, Tol3d);
736
737 return E;
738}
739
740
741//=======================================================================
742//Fonction : Filling
0d969553 743//Objet : Construct the faces of filling
7fd59977 744//=======================================================================
745static Standard_Boolean Filling(const TopoDS_Shape& EF,
746 const TopoDS_Shape& F1,
747 const TopoDS_Shape& EL,
748 const TopoDS_Shape& F2,
749 TopTools_DataMapOfShapeShape& EEmap,
750 const Standard_Real Tol,
751 const gp_Ax2& Axe,
752 const gp_Vec& TangentOnPart1,
753 TopoDS_Edge& Aux1,
754 TopoDS_Edge& Aux2,
755 TopoDS_Face& Result)
756{
757 BRep_Builder B;
758// Class BRep_Tool without fields and without Constructor :
759// BRep_Tool BT;
760// Standard_Integer NbInt =0;
761// Standard_Real Tol3d = Tol;
762 Standard_Boolean WithE3, WithE4;
763
0d969553 764// Return constraints
7fd59977 765 TopoDS_Vertex V1, V2, Vf, Vl;
766 TopoDS_Edge E1, E2, E3, E4;
767 E1 = TopoDS::Edge(EF);
768 E2 = TopoDS::Edge(EL);
769
770 TopExp::Vertices(E1, Vf, Vl);
771 Vf.Orientation(TopAbs_FORWARD);
772 Vl.Orientation(TopAbs_FORWARD);
773
774 TopExp::Vertices(E2, V1, V2);
775 V1.Orientation(TopAbs_REVERSED);
776 V2.Orientation(TopAbs_REVERSED);
777
778 B.MakeEdge(E3);
779 B.MakeEdge(E4);
780
781 WithE3 = WithE4 = Standard_False;
782
783 if ((!Aux1.IsNull()) && (!Vf.IsSame(V1))) {
784 E3 = Aux1;
785// E3 = TopoDS::Edge(Aux1);
786 WithE3 = Standard_True;
787 }
788
789 if (Vf.IsSame(Vl)) {
790 E4 = E3;
791 E4.Reverse();
792 WithE4 = WithE3;
793 }
794 else if (!Aux2.IsNull() && (!Vl.IsSame(V2))) {
795 E4 = Aux2;
796// E4 = TopoDS::Edge(Aux2);
797 WithE4 = Standard_True;
798 }
799
800#if DRAW
801 if (Affich) {
802 DBRep::Set("Fill_Edge1", E1);
803 DBRep::Set("Fill_Edge2", E2);
804 if (!E3.IsNull())
805 DBRep::Set("Fill_Edge3", E3);
806 if (!E4.IsNull())
807 DBRep::Set("Fill_Edge4", E4);
808 }
809#endif
810
0d969553 811// Construction of a surface of revolution
7fd59977 812 Handle(Geom_Curve) Prof1, Prof2;
813 //Standard_Integer ii, jj;//, Nb;
814 Standard_Real f1, f2, l1, l2,/*d1, d2,*/ Angle;//, Eps = 1.e-9;
815// Prof1 = BT.Curve(E1, f1, l1);
816 Prof1 = BRep_Tool::Curve(E1, f1, l1);
817// Prof2 = BT.Curve(E2, f2, l2);
818 Prof2 = BRep_Tool::Curve(E2, f2, l2);
819 gp_Pnt P1, P2, P;
820 gp_Pnt2d p1, p2;
821 gp_Trsf Tf;
822 Tf.SetTransformation(Axe);
823
0d969553 824// Choose the angle of opening
7fd59977 825 P1 = Prof1->Value((f1+l1)/2);
826 P2 = Prof2->Value((f2+l2)/2);
827 P1.Transform(Tf);
828 P2.Transform(Tf);
829 p1.SetCoord(P1.Z(), P1.X());
830 p2.SetCoord(P2.Z(), P2.X());
831 gp_Vec2d v1(gp::Origin2d(), p1);
832 gp_Vec2d v2(gp::Origin2d(), p2);
833 if (v1.Magnitude() <= gp::Resolution() ||
834 v2.Magnitude() <= gp::Resolution())
835 return Standard_False;
836 Angle = v1.Angle(v2);
837
838 gp_Ax1 axe(Axe.Location(), Axe.YDirection());
839
840 if (Angle < 0) {
841 Angle = -Angle;
842 axe.Reverse();
843 }
844
845 Handle(Geom_SurfaceOfRevolution) Rev =
846 new (Geom_SurfaceOfRevolution) (Prof1, axe);
847
848 Handle(Geom_Surface) Surf =
849 new (Geom_RectangularTrimmedSurface) (Rev, 0, Angle, f1, l1);
850
0d969553 851 // Control the direction of the rotation
7fd59977 852 Standard_Boolean ToReverseResult = Standard_False;
853 gp_Vec d1u;
854 d1u = Surf->DN(0, (f1+l1)/2, 1, 0);
c6541a0c 855 if (d1u.Angle(TangentOnPart1) > M_PI/2) { //Invert everything
7fd59977 856 ToReverseResult = Standard_True;
857 /*
858 axe.Reverse();
c6541a0c 859 Angle = 2*M_PI - Angle;
7fd59977 860 Rev = new (Geom_SurfaceOfRevolution) (Prof1, axe);
861 Surf = new (Geom_RectangularTrimmedSurface)
862 (Rev, 0, Angle, f1, l1);
863 */
864 }
865
866#if DRAW
867 if (Affich) {
868 char* Temp = "Surf_Init" ;
869 DrawTrSurf::Set(Temp, Surf);
870 }
871#endif
872
873 Handle(Geom2d_Curve) C1, C2, C3, C4;
874/*
0d969553 875// Deform the surface of revolution.
7fd59977 876 GeomPlate_BuildPlateSurface BPS;
877
878 Handle(BRepAdaptor_HSurface) AS;
879 Handle(BRepAdaptor_HCurve2d) AC2d;
880 Handle(Adaptor3d_HCurveOnSurface) HConS;
881*/
882 Handle(Geom2d_Line) L;
883 gp_Pnt2d P2d(0.,0.);
884
885 L = new (Geom2d_Line) (P2d, gp::DY2d());
886 C1 = new (Geom2d_TrimmedCurve) (L, f1, l1);
887
888 P2d.SetCoord(Angle,0.);
889 L = new (Geom2d_Line) (P2d, gp::DY2d());
890 C2 = new (Geom2d_TrimmedCurve) (L, f1, l1);
891
0d969553 892 // It is required to control the direction and the range.
7fd59977 893 C2->D0(f1, P2d);
894 Surf->D0(P2d.X(), P2d.Y(), P1);
895 C2->D0(l1, P2d);
896 Surf->D0(P2d.X(), P2d.Y(), P2);
897// P = BT.Pnt(V1);
898 P = BRep_Tool::Pnt(V1);
899 if (P.Distance(P2)+Tol < P.Distance(P1)) {
0d969553 900 // E2 is parsed in the direction opposite to E1
7fd59977 901 C2->Reverse();
902 TopoDS_Vertex aux;
903 aux = V2;
904 V2 = V1;
905 V1 = aux;
906 }
907 GeomLib::SameRange(Precision::PConfusion(), C2,
908 C2->FirstParameter(),
909 C2->LastParameter(),
910 f2, l2, C3);
911 C2 = C3;
912
7fd59977 913// P1 = BT.Pnt(Vf);
914 P1 = BRep_Tool::Pnt(Vf);
915// P2 = BT.Pnt(V1);
916 P2 = BRep_Tool::Pnt(V1);
917// pointu_f = Vf.IsSame(V1) || (P1.Distance(P2) < BT.Tolerance(Vf));
7fd59977 918// P1 = BT.Pnt(Vl);
919 P1 = BRep_Tool::Pnt(Vl);
920// P2 = BT.Pnt(V2);
921 P2 = BRep_Tool::Pnt(V2);
922// pointu_l = Vl.IsSame(V2) || (P1.Distance(P2) < BT.Tolerance(Vl));
7fd59977 923
924 P2d.SetCoord(0.,f1);
925 L = new (Geom2d_Line) (P2d, gp::DX2d());
926 C3 = new (Geom2d_TrimmedCurve) (L, 0, Angle);
927
928
929 P2d.SetCoord(0.,l1);
930 L = new (Geom2d_Line) (P2d, gp::DX2d());
931 C4 = new (Geom2d_TrimmedCurve) (L, 0, Angle);
932/*
0d969553
Y
933 // Determine the constraints and
934 // their parametric localisation.
7fd59977 935 if (!E1.IsNull()) {
936 AS = new BRepAdaptor_HSurface(TopoDS::Face(F1));
937 AC2d = new BRepAdaptor_HCurve2d();
938 AC2d->ChangeCurve2d().Initialize(E1,TopoDS::Face(F1));
939 HConS = new (Adaptor3d_HCurveOnSurface)();
940 HConS->ChangeCurve().Load(AC2d);
941 HConS->ChangeCurve().Load(AS);
942
943 Handle(BRepFill_CurveConstraint) Cont
944 = new BRepFill_CurveConstraint(HConS, 1, 15);
945 Cont->SetCurve2dOnSurf(C1);
946
947 BPS.Add(Cont);
948 NbInt = HConS->NbIntervals(GeomAbs_CN);
949 }
950
951 if (!E2.IsNull()) {
952 AS = new BRepAdaptor_HSurface(TopoDS::Face(F2));
953 AC2d = new BRepAdaptor_HCurve2d();
954 AC2d->ChangeCurve2d().Initialize(E2,TopoDS::Face(F2));
955 HConS = new (Adaptor3d_HCurveOnSurface);
956
957 HConS->ChangeCurve().Load(AC2d);
958 HConS->ChangeCurve().Load(AS);
959
960 Handle(BRepFill_CurveConstraint) Cont
961 = new BRepFill_CurveConstraint(HConS, 1, 15);
962 Cont->SetCurve2dOnSurf(C2);
963 BPS.Add(Cont);
964 }
965
966 if (WithE3) {
967 Handle(BRepAdaptor_HCurve) AC = new (BRepAdaptor_HCurve) (E3);
968 Handle(BRepFill_CurveConstraint) Cont
969 = new BRepFill_CurveConstraint(AC, 0);
970 Cont->SetCurve2dOnSurf(C3);
971 BPS.Add(Cont);
972 }
973 else if (pointu_f) {
974 Standard_Real delta = Angle / 11;
975// P = BT.Pnt(Vf);
976 P = BRep_Tool::Pnt(Vf);
977 Handle(GeomPlate_PointConstraint) PC;
978 for (ii=1; ii<=10; ii++) {
979 C3->D0(ii*delta, P2d);
980 PC = new (GeomPlate_PointConstraint) (P, 0);
981 PC->SetPnt2dOnSurf(P2d);
982 BPS.Add(PC);
983 }
984 }
985
986
987 if (WithE4) {
988 Handle(BRepAdaptor_HCurve) AC = new (BRepAdaptor_HCurve) (E4);
989 Handle(BRepFill_CurveConstraint) Cont
990 = new BRepFill_CurveConstraint(AC, 0);
991 Cont->SetCurve2dOnSurf(C4);
992 BPS.Add(Cont);
993 }
994 else if (pointu_l) {
995 Standard_Real delta = Angle / 11;
996// P = BT.Pnt(Vl);
997 P = BRep_Tool::Pnt(Vl);
998 Handle(GeomPlate_PointConstraint) PC;
999 for (ii=1; ii<=10; ii++) {
1000 C4->D0(ii*delta, P2d);
1001 PC = new (GeomPlate_PointConstraint) (P, 0);
1002 PC->SetPnt2dOnSurf(P2d);
1003 BPS.Add(PC);
1004 }
1005 }
1006
1007 BPS.LoadInitSurface(Surf);
1008 BPS.Perform();
1009
1010 // Controle s'il y a une deformation effective
1011 Handle(GeomPlate_Surface) plate;
1012 plate = BPS.Surface();
1013 plate->SetBounds(0, Angle, f1, l1);
1014 Standard_Boolean Ok=Standard_True;
1015 Standard_Real u, v;
1016 d1 = (l1-f1)/5;
1017 d2 = Angle/5;
1018 for (ii=0; ii<=5 && Ok; ii++) {
1019 u = f1 + ii*d1;
1020 for (jj=0; jj<=5 && Ok; jj++) {
1021 v = jj*d2;
1022 plate->D0(u, v, P1);
1023 Surf->D0(u, v, P2);
1024 Ok = (P2.IsEqual(P1, Tol));
1025 }
1026 }
1027
1028
1029 if (!Ok) {
1030 // Approx de la plate surface
1031 // Bords naturelles => pas besoin de criteres.
1032 GeomConvert_ApproxSurface App(BPS.Surface(),
1033 Tol3d,
1034 GeomAbs_C1, GeomAbs_C1,
1035 8, 8, 2*NbInt, 0);
1036 if (!App.HasResult()) {
0797d9d3 1037#ifdef OCCT_DEBUG
7fd59977 1038 cout << "Filling_Approx : Pas de resultat" << endl;
1039#endif
1040 return Standard_False;
1041 }
0797d9d3 1042#ifdef OCCT_DEBUG
7fd59977 1043 cout << "Filling_Approx Error 3d = " <<
1044 App.MaxError() << endl;
1045#endif
1046 Surf = App.Surface();
1047 Tol3d = App.MaxError();
1048 }
1049*/
1050
1051// Update des Edges
1052 TopLoc_Location Loc;
1053 Handle(Geom_Curve) C3d;
1054 B.UpdateEdge(E1, C1, Surf, Loc, /*Tol3d*/Precision::Confusion());
1055 B.UpdateEdge(E2, C2, Surf, Loc, /*Tol3d*/Precision::Confusion());
1056
1057 if (E3.IsSame(E4)) {
1058 if (!WithE3)
1059 {
1060 C3d = Surf->VIso(f1);
1061 E3 = BuildEdge(C3d, C3, Surf, Vf, V1, 0, Angle, /*Tol3d*/Precision::Confusion());
1062 }
1063 else
1064 {
1065 BRepAdaptor_Curve aCurve(E3);
1066 Standard_Real AngleOld = aCurve.LastParameter();
1067 if (Angle > AngleOld)
1068 {
1069 B.Range( E3, 0, Angle );
1070 TopoDS_Vertex V (TopExp::LastVertex(E3));
1071 Handle(BRep_TVertex)& TVlast = *((Handle(BRep_TVertex)*) &V.TShape());
1072 TVlast->Tolerance( Precision::Confusion() );
1073 }
1074 }
1075
1076 B.UpdateEdge(E3, C3, C4, Surf, Loc, /*Tol3d*/Precision::Confusion());
1077 E4 = E3;
1078 E4.Reverse();
1079 }
1080 else {
1081 if (!WithE3)
1082 {
1083 C3d = Surf->VIso(f1);
1084 E3 = BuildEdge(C3d, C3, Surf, Vf, V1, 0, Angle, /*Tol3d*/Precision::Confusion());
1085 }
1086 else
1087 {
1088 BRepAdaptor_Curve aCurve(E3);
1089 Standard_Real AngleOld = aCurve.LastParameter();
1090 if (Angle > AngleOld)
1091 {
1092 B.Range( E3, 0, Angle );
1093 TopoDS_Vertex V(TopExp::LastVertex(E3));
1094 Handle(BRep_TVertex)& TVlast = *((Handle(BRep_TVertex)*) &V.TShape());
1095 TVlast->Tolerance( Precision::Confusion() );
1096 }
1097
1098 B.UpdateEdge(E3, C3, Surf, Loc, /*Tol3d*/Precision::Confusion());
1099 }
1100
1101 if (!WithE4)
1102 {
1103 C3d = Surf->VIso(l1);
1104 E4 = BuildEdge(C3d, C4, Surf, Vl, V2, 0, Angle, /*Tol3d*/Precision::Confusion());
1105 }
1106 else
1107 {
1108 BRepAdaptor_Curve aCurve(E4);
1109 Standard_Real AngleOld = aCurve.LastParameter();
1110 if (Angle > AngleOld)
1111 {
1112 B.Range( E4, 0, Angle );
1113 TopoDS_Vertex V (TopExp::LastVertex(E4));
1114 Handle(BRep_TVertex)& TVlast = *((Handle(BRep_TVertex)*)&V.TShape());
1115 TVlast->Tolerance( Precision::Confusion() );
1116 }
1117
1118 B.UpdateEdge(E4, C4, Surf, Loc, /*Tol3d*/Precision::Confusion());
1119 }
1120 }
1121
0d969553 1122//Construct face
7fd59977 1123 BuildFace(Surf,E1, E3, E2, E4, EEmap,
1124 Standard_False, Standard_False,
1125 Result);
1126
0d969553 1127// Set the continuities.
7fd59977 1128 B.Continuity(E1, TopoDS::Face(F1), Result, GeomAbs_G1);
1129 B.Continuity(E2, TopoDS::Face(F2), Result, GeomAbs_G1);
1130
0d969553 1131// Render the calculated borders.
7fd59977 1132// if (!BT.Degenerated(E3))
1133 if (!BRep_Tool::Degenerated(E3))
1134 Aux1 = E3;
1135 else
1136 B.MakeEdge(Aux1); //Nullify
1137
1138// if (!BT.Degenerated(E4))
1139 if (!BRep_Tool::Degenerated(E4))
1140 Aux2 = E4;
1141 else
1142 B.MakeEdge(Aux2);
1143
0d969553 1144 // Set the orientation
7fd59977 1145 gp_Vec D1U, D1V, N1, N2;
1146 C1->D0( (f1+l1)/2, P2d);
1147 Surf->D1(P2d.X(), P2d.Y(), P, D1U, D1V);
1148 N1 = D1U^D1V;
1149
1150// C1 = BT.CurveOnSurface(E1, TopoDS::Face(F1), f2, l2);
1151 C1 = BRep_Tool::CurveOnSurface(E1, TopoDS::Face(F1), f2, l2);
1152 C1->D0( (f1+l1)/2, P2d);
1153 Handle(BRepAdaptor_HSurface) AS = new BRepAdaptor_HSurface(TopoDS::Face(F1));
1154 AS->D1(P2d.X(), P2d.Y(), P, D1U, D1V);
1155 N2 = D1U^D1V;
1156
c6541a0c 1157 if ( (F1.Orientation() == TopAbs_REVERSED) ^ (N1.Angle(N2)>M_PI/2) )
7fd59977 1158 Result.Orientation(TopAbs_REVERSED);
1159 else Result.Orientation(TopAbs_FORWARD);
1160
1161 if (ToReverseResult)
1162 Result.Reverse();
1163
1164#if DRAW
1165 if (Affich) DBRep::Set("BoucheTrou", Result);
1166#endif
1167
1168 return Standard_True;
1169}
1170
1171//=======================================================================
1172//function : Substitute
1173//purpose :
1174//=======================================================================
1175static void Substitute(BRepTools_Substitution& aSubstitute,
1176 const TopoDS_Edge& Old,
1177 const TopoDS_Edge& New)
1178{
1179 TopTools_ListOfShape listShape;
1180
1181 TopoDS_Vertex OldV1, OldV2, NewV1, NewV2;
1182 TopExp::Vertices( Old, OldV1, OldV2 );
1183 TopExp::Vertices( New, NewV1, NewV2 );
1184
1185 if (!aSubstitute.IsCopied( OldV1 ))
1186 {
1187 listShape.Append( NewV1.Oriented(TopAbs_FORWARD) );
1188 aSubstitute.Substitute( OldV1, listShape );
1189 listShape.Clear();
1190 }
1191 if (!aSubstitute.IsCopied( OldV2 ))
1192 {
1193 listShape.Append( NewV2.Oriented(TopAbs_FORWARD) );
1194 aSubstitute.Substitute( OldV2, listShape );
1195 listShape.Clear();
1196 }
1197 if (!aSubstitute.IsCopied( Old ))
1198 {
1199 listShape.Append( New.Oriented(TopAbs_FORWARD) );
1200 aSubstitute.Substitute( Old, listShape );
1201 }
1202}
1203
1204//=======================================================================
1205//Function : SetCommonEdgeInFace
0d969553 1206//Purpose : Replace an edge of the face by the corresponding edge from
7fd59977 1207// myUEdges
1208//=======================================================================
1209/*
1210static void SetCommonEdgeInFace(BRepTools_Substitution& aSubstitute,
1211 const TopoDS_Shape& Face,
1212 const TopoDS_Shape& Edge)
1213{
1214 if (Edge.IsNull())
1215 return;
1216
1217 Standard_Boolean done = Standard_False;
1218// Class BRep_Tool without fields and without Constructor :
1219// BRep_Tool BT;
1220 Standard_Real f, l;
1221 TopExp_Explorer Exp(Face, TopAbs_EDGE);
1222 Handle(Geom_Curve) Cref, C;
1223 TopLoc_Location Lref, L;
1224// Cref = BT.Curve(TopoDS::Edge(Edge), Lref, f, l);
1225 const TopoDS_Edge& NewEdge = TopoDS::Edge(Edge);
1226 Cref = BRep_Tool::Curve( NewEdge, Lref, f, l );
1227
1228 for ( ; Exp.More() && !done; Exp.Next()) {
1229// C = BT.Curve(TopoDS::Edge(Exp.Current()), L, f, l);
1230 const TopoDS_Edge& OldEdge = TopoDS::Edge(Exp.Current());
1231 C = BRep_Tool::Curve(OldEdge, L, f, l);
1232 if ((Cref==C) && (Lref == L)) {
1233 done = Standard_True;
1234 Substitute( aSubstitute, OldEdge, NewEdge );
1235 }
1236 }
0797d9d3 1237#ifdef OCCT_DEBUG
7fd59977 1238 if (!done) cout << "Substitution of Edge failed" << endl;
1239#endif
1240}
1241*/
1242
1243//=======================================================================
1244//Fonction : KeepEdge
0d969553 1245//Objet : Find edges of the face supported by the same Curve.
7fd59977 1246//=======================================================================
1247static void KeepEdge(const TopoDS_Shape& Face,
1248 const TopoDS_Shape& Edge,
1249 TopTools_ListOfShape& List)
1250{
1251 List.Clear();
1252// Class BRep_Tool without fields and without Constructor :
1253// BRep_Tool BT;
1254 Standard_Real f, l;
1255 TopExp_Explorer Exp(Face, TopAbs_EDGE);
1256 Handle(Geom_Curve) Cref, C;
1257 TopLoc_Location Lref, L;
1258// Cref = BT.Curve(TopoDS::Edge(Edge), Lref, f, l);
1259 Cref = BRep_Tool::Curve(TopoDS::Edge(Edge), Lref, f, l);
1260
1261 for ( ; Exp.More(); Exp.Next()) {
1262// C = BT.Curve(TopoDS::Edge(Exp.Current()), L, f, l);
1263 C = BRep_Tool::Curve(TopoDS::Edge(Exp.Current()), L, f, l);
1264 if ((Cref==C) && (Lref == L)) {
1265 List.Append(Exp.Current());
1266 }
1267 }
1268}
1269
1270//=======================================================================
1271//Function :
0d969553 1272//Objet : Construct a vertex via an iso
7fd59977 1273//=======================================================================
1274static void BuildVertex(const Handle(Geom_Curve)& Iso,
1275 const Standard_Boolean isfirst,
1276 const Standard_Real First,
1277 const Standard_Real Last,
1278 TopoDS_Shape& Vertex)
1279{
1280 BRep_Builder B;
1281 Standard_Real val;
1282
1283 if (isfirst) val = First;
1284 else val = Last;
1285 B.MakeVertex(TopoDS::Vertex(Vertex),
1286 Iso->Value(val),
1287 Precision::Confusion());
1288}
1289
1290//=======================================================================
1291//Function :
0d969553 1292//Objet : Construct an empty edge
7fd59977 1293//=======================================================================
1294static TopoDS_Edge NullEdge(TopoDS_Shape& Vertex)
1295{
1296 TopoDS_Edge E;
1297 BRep_Builder B;
1298 B.MakeEdge(E);
1299 Vertex.Orientation(TopAbs_FORWARD);
1300 B.Add(E, Vertex);
1301 B.Add(E, Vertex.Reversed());
1302 B.Degenerated(E, Standard_True);
1303 return E;
1304
1305}
1306
1307//=======================================================================
1308//Function :
0d969553 1309//Objet : Construct an edge via an iso
7fd59977 1310//=======================================================================
1311static TopoDS_Edge BuildEdge(const Handle(Geom_Surface)& S,
1312 const Standard_Boolean isUiso,
1313 const Standard_Real ValIso,
1314 const TopoDS_Shape& VFirst,
1315 const TopoDS_Shape& VLast,
1316 const Standard_Real Tol)
1317{
1318 TopoDS_Edge E;
1319 BRep_Builder B;
1320 Handle(Geom_Curve) Iso;
1321 Standard_Boolean sing = Standard_False;
1322 if (isUiso) {
1323 Iso = S->UIso(ValIso);
1324 }
1325 else {
1326 Iso = S->VIso(ValIso);
1327 }
1328
0d969553 1329 if (VFirst.IsSame(VLast)) { // Singular case ?
7fd59977 1330 gp_Pnt P;
1331// Class BRep_Tool without fields and without Constructor :
1332// BRep_Tool BT;
1333 const TopoDS_Vertex& V = TopoDS::Vertex(VFirst);
1334// Standard_Real tol = BT.Tolerance(V);
1335 Standard_Real tol = BRep_Tool::Tolerance(V);
1336 if (Tol > tol) tol = Tol;
1337 Iso->D0((Iso->FirstParameter()+Iso->LastParameter())/2, P);
1338// if (P.Distance(BT.Pnt(V)) < tol) {
1339 if (P.Distance(BRep_Tool::Pnt(V)) < tol) {
1340 GeomAdaptor_Curve AC(Iso);
1341 sing = GCPnts_AbscissaPoint::Length(AC, tol/4) < tol;
1342 }
1343 }
1344
1345
0d969553 1346 if (sing) { // Singular case
7fd59977 1347 TopoDS_Shape V;
1348 V = VFirst;
1349 E = NullEdge(V);
1350// Iso.Nullify();
1351// B.UpdateEdge(E, Iso, Precision::Confusion());
1352 B.Degenerated(E, Standard_True);
1353 }
1354
1355 else {
0d969553 1356 // Construction Via 3d
7fd59977 1357// if (isUiso) {
1358// Iso = S->UIso(ValIso);
1359 gp_Pnt P1,P2;
1360 Standard_Real p1, p2, p11, p12, p21, p22;
1361 Standard_Boolean fwd = Standard_False;
1362 p1 = Iso->FirstParameter();
1363 p2 = Iso->LastParameter();
1364 P1 = Iso->Value(p1);
1365 P2 = Iso->Value(p2);
1366
1367 Standard_Real t1 = BRep_Tool::Tolerance(TopoDS::Vertex(VFirst));
1368 Standard_Real t2 = BRep_Tool::Tolerance(TopoDS::Vertex(VLast));
1369
1370 BRep_Builder BB;
1371
1372 p11 = P1.Distance(BRep_Tool::Pnt(TopoDS::Vertex(VFirst)));
1373 p22 = P2.Distance(BRep_Tool::Pnt(TopoDS::Vertex(VLast)));
1374 p12 = P1.Distance(BRep_Tool::Pnt(TopoDS::Vertex(VLast)));
1375 p21 = P2.Distance(BRep_Tool::Pnt(TopoDS::Vertex(VFirst)));
1376
1377 if(p11 < p12 && p22 < p21) fwd = Standard_True;
1378
1379 if(fwd) { //OCC500(apo)
1380 if (p11 >= t1) BB.UpdateVertex(TopoDS::Vertex(VFirst), 1.01*p11);
1381 if (p22 >= t2) BB.UpdateVertex(TopoDS::Vertex(VLast), 1.01*p22);
1382 }
1383 else {
1384// Iso = S->VIso(ValIso);
1385 if (p12 >= t2) BB.UpdateVertex(TopoDS::Vertex(VLast), 1.01*p12);
1386 if (p21 >= t1) BB.UpdateVertex(TopoDS::Vertex(VFirst), 1.01*p21);
1387 }
1388
1389 BRepLib_MakeEdge MkE;
1390
1391// MkE.Init(Iso,
1392// TopoDS::Vertex(VFirst),
1393// TopoDS::Vertex(VLast),
1394// Iso->FirstParameter(),
1395// Iso->LastParameter());
1396 if(fwd)
1397 MkE.Init(Iso,
1398 TopoDS::Vertex(VFirst),
1399 TopoDS::Vertex(VLast),
1400 Iso->FirstParameter(),
1401 Iso->LastParameter());
1402 else
1403 MkE.Init(Iso,
1404 TopoDS::Vertex(VLast),
1405 TopoDS::Vertex(VFirst),
1406 Iso->FirstParameter(),
1407 Iso->LastParameter());
1408
1409// if (!MkE.IsDone()) { // Il faut peut etre permuter les Vertex
1410// MkE.Init(Iso,
1411// TopoDS::Vertex(VLast),
1412// TopoDS::Vertex(VFirst),
1413// Iso->FirstParameter(),
1414// Iso->LastParameter());
1415// }
1416
1417 if (!MkE.IsDone()) { // Erreur de construction !!
1418#ifdef DRAW
1419 char name[100];
1420 sprintf(name,"firstvertex_error");
1421 DBRep::Set(name, VFirst);
1422 sprintf(name,"lastvertex_error");
1423 DBRep::Set(name, VLast);
1424 sprintf(name,"curve3d_error");
1425 char* Temp = name ;
1426 DrawTrSurf::Set(Temp,Iso);
1427// DrawTrSurf::Set(name,Iso);
1428#endif
1429 Standard_ConstructionError::Raise("BRepFill_Sweep::BuildEdge");
1430 }
1431
1432 E = MkE.Edge();
1433 }
1434
0d969553 1435 // Associate 2d
7fd59977 1436 Handle(Geom2d_Line) L;
1437 TopLoc_Location Loc;
9ba2c30f 1438 Standard_Real Umin, Umax, Vmin, Vmax;
1439 S->Bounds(Umin, Umax, Vmin, Vmax);
7fd59977 1440 if (isUiso) {
9ba2c30f 1441 //gp_Pnt2d P(ValIso, 0);
1442 gp_Pnt2d P( ValIso, Vmin - Iso->FirstParameter() );
7fd59977 1443 gp_Vec2d V(0., 1.);
1444 L = new (Geom2d_Line) (P, V);
1445 }
1446 else {
9ba2c30f 1447 //gp_Pnt2d P(0., ValIso);
1448 gp_Pnt2d P( Umin -Iso->FirstParameter() , ValIso );
7fd59977 1449 gp_Vec2d V(1., 0.);
1450 L = new (Geom2d_Line) (P, V);
1451 }
1452
1453 B.UpdateEdge(E, L, S, Loc, Precision::Confusion());
1454 if (sing) B.Range(E, S, Loc,
1455 Iso->FirstParameter(),
1456 Iso->LastParameter());
1457
471ce736 1458 Standard_Real MaxTol = 1.e-4;
1459 Standard_Real theTol;
1460 GeomAdaptor_Curve GAiso(Iso);
1461 Handle(GeomAdaptor_HCurve) GAHiso = new GeomAdaptor_HCurve(GAiso);
1462 GeomAdaptor_Surface GAsurf(S);
1463 Handle(GeomAdaptor_HSurface) GAHsurf = new GeomAdaptor_HSurface(GAsurf);
1464 CheckSameParameter( GAHiso, L, GAHsurf, MaxTol, theTol);
1465 B.UpdateEdge(E, theTol);
1466
7fd59977 1467 return E;
1468}
1469
1470//=======================================================================
1471//Function :
0d969553 1472//Objet : Complete an edge via an iso
7fd59977 1473//=======================================================================
1474static void UpdateEdge(TopoDS_Edge& E,
1475 const Handle(Geom_Surface)& S,
1476 const Standard_Boolean isUiso,
1477 const Standard_Real ValIso)
1478{
1479 BRep_Builder B;
1480 Handle(Geom2d_Line) L;
1481 Handle(Geom2d_Curve) PCurve, CL;
1482 TopLoc_Location Loc;
1483 Standard_Real UFirst, ULast, VFirst, VLast, F2d, L2d;
1484 S->Bounds( UFirst, ULast, VFirst, VLast);
1485
1486 Standard_Boolean sing = Standard_False;
1487 Handle(Geom_Curve) Iso;
1488 if (isUiso) {
1489 Iso = S->UIso(ValIso);
1490 }
1491 else {
1492 Iso = S->VIso(ValIso);
1493 }
1494
1495 TopoDS_Vertex Vf, Vl;
1496 TopExp::Vertices(E, Vf, Vl);
0d969553 1497 if (Vf.IsSame(Vl)) { // Singular case ?
7fd59977 1498 gp_Pnt Pmid;
1499 Standard_Real tol = BRep_Tool::Tolerance(Vf);
1500 Iso->D0((Iso->FirstParameter()+Iso->LastParameter())/2, Pmid);
1501 if (Pmid.Distance(BRep_Tool::Pnt(Vf)) < tol) {
1502 GeomAdaptor_Curve AC(Iso);
1503 sing = GCPnts_AbscissaPoint::Length(AC, tol/4) < tol;
1504 }
1505 }
1506
1507 if (isUiso) {
1508 gp_Pnt2d P(ValIso, 0);
1509 gp_Vec2d V(0., 1.);
1510 L = new (Geom2d_Line) (P, V);
1511 F2d = VFirst;
1512 L2d = VLast;
1513 }
1514 else {
1515 gp_Pnt2d P(0., ValIso);
1516 gp_Vec2d V(1., 0.);
1517 L = new (Geom2d_Line) (P, V);
1518 F2d = UFirst;
1519 L2d = ULast;
1520 }
1521 CL = new (Geom2d_TrimmedCurve) (L, F2d, L2d);
1522
0d969553 1523 // Control direction & Range
7fd59977 1524 Standard_Real R, First, Last, Tol=1.e-4;
1525 Standard_Boolean reverse = Standard_False;;
1526
1527
1528// Class BRep_Tool without fields and without Constructor :
1529// BRep_Tool BT;
1530 gp_Pnt POnS;
1531 gp_Pnt2d P2d;
1532// BT.Range(E, First, Last);
1533 BRep_Tool::Range(E, First, Last);
1534
1535 if (!Vf.IsSame(Vl)) {
0d969553 1536 // Test distances between "FirstPoint" and "Vertex"
7fd59977 1537 P2d = CL->Value(F2d);
1538 POnS = S->Value(P2d.X(), P2d.Y());
1539// reverse = POnS.Distance(BT.Pnt(Vl)) < POnS.Distance(BT.Pnt(Vf));
1540 reverse = POnS.Distance(BRep_Tool::Pnt(Vl)) < POnS.Distance(BRep_Tool::Pnt(Vf));
1541 }
1542 else if (!sing) {
0d969553 1543 // Test angle between "First Tangente"
7fd59977 1544 gp_Vec2d V2d;
1545 gp_Vec V3d, du, dv, dC3d;
1546 BRepAdaptor_Curve C3d(E);
1547
1548 C3d.D1(First, POnS, dC3d);
1549 CL->D1(F2d, P2d, V2d);
1550 S->D1(P2d.X(), P2d.Y(), POnS, du, dv);
1551 V3d.SetLinearForm(V2d.X(), du, V2d.Y(), dv);
1552 reverse = ( dC3d.Angle(V3d) > Tol);
1553 }
0d969553 1554 if (reverse ) { // Return curve 2d
7fd59977 1555 CL = new (Geom2d_TrimmedCurve)(L, F2d, L2d);
1556 CL->Reverse();
1557 F2d = CL->FirstParameter();
1558 L2d = CL->LastParameter();
1559 }
1560
1561 if (sing)
1562 {
1563 Handle(Geom_Curve) NullCurve;
1564 B.UpdateEdge(E, NullCurve, 0.);
1565 B.Degenerated(E, Standard_True);
1566 B.Range(E, F2d, L2d);
1567 First = F2d;
1568 Last = L2d;
1569 }
1570
1571 if (First != F2d || Last != L2d) {
1572 Handle(Geom2d_Curve) C2d;
1573 GeomLib::SameRange(Precision::PConfusion(), CL,
1574 F2d, L2d, First, Last,
1575 C2d);
1576 CL = new (Geom2d_TrimmedCurve)(C2d, First, Last);
1577 }
1578
1579 // Update des Vertex
1580
1581 TopoDS_Vertex V;
1582
1583 P2d = CL->Value(First);
1584 POnS = S->Value(P2d.X(), P2d.Y());
1585 V = TopExp::FirstVertex(E);
1586// R = POnS.Distance(BT.Pnt(V));
1587 R = POnS.Distance(BRep_Tool::Pnt(V));
1588 B.UpdateVertex(V, R);
1589
1590 P2d = CL->Value(Last);
1591 POnS = S->Value(P2d.X(), P2d.Y());
1592 V = TopExp::LastVertex(E);
1593// R = POnS.Distance(BT.Pnt(V));
1594 R = POnS.Distance(BRep_Tool::Pnt(V));
1595 B.UpdateVertex(V, R);
1596
0d969553 1597 // Update Edge
7fd59977 1598 if (!sing && SameParameter(E, CL, S, Tol, R)) {
1599 B.UpdateEdge(E, R);
1600 }
1601
1602 PCurve = Couture(E, S, Loc);
1603 if (PCurve.IsNull())
1604 B.UpdateEdge(E, CL, S, Loc, Precision::Confusion());
0d969553 1605 else { // Sewing edge
7fd59977 1606 TopoDS_Edge e = E;
1607 Oriente(S, e);
1608 if (e.Orientation() == TopAbs_REVERSED)
1609 B.UpdateEdge(E, CL, PCurve, S, Loc, Precision::Confusion());
1610 else
1611 B.UpdateEdge(E, PCurve, CL, S, Loc, Precision::Confusion());
1612 }
1613
0d969553 1614 // Attention to case not SameRange on its shapes (PRO13551)
7fd59977 1615// if (!BT.SameRange(E)) B.Range(E, S, Loc, First, Last);
1616 if (!BRep_Tool::SameRange(E)) B.Range(E, S, Loc, First, Last);
1617}
1618
1619//=======================================================================
0d969553 1620// Object : Check if a surface is degenerated
7fd59977 1621//=======================================================================
1622static Standard_Boolean IsDegen(const Handle(Geom_Surface)& S,
1623 const Standard_Real Tol)
1624{
1625 Standard_Integer Nb = 5;
1626 Standard_Boolean B = Standard_True;
1627 Standard_Real Umax, Umin, Vmax, Vmin, t, dt, l;
1628 Standard_Integer ii;
1629 Handle(Geom_Curve) Iso;
1630 gp_Pnt P1,P2,P3;
1631 GCPnts_AbscissaPoint GC;
1632
1633 S->Bounds(Umin, Umax, Vmin, Vmax);
1634
0d969553 1635 // Check the length of Iso-U
7fd59977 1636 t = (Umin + Umax)/2;
1637 S->D0(t, Vmin, P1);
1638 S->D0(t, (Vmin+Vmax)/2, P2);
1639 S->D0(t, Vmax, P3);
1640 B = ((P1.Distance(P2) + P2.Distance(P3)) < Tol);
1641
1642 for (ii=1, dt = (Umax-Umin)/(Nb+1); B && (ii<=Nb); ii++) {
1643 t = Umin + ii*dt;
1644 Iso = S->UIso(t);
1645 GeomAdaptor_Curve AC(Iso);
1646 l = GC.Length(AC, Tol/4);
1647 B = (l <= Tol);
1648 }
1649
1650 if (B) return Standard_True;
1651
0d969553 1652 // Check the length of Iso-V
7fd59977 1653 t = (Vmin + Vmax)/2;
1654 S->D0(Umin, t, P1);
1655 S->D0((Umin+Umax)/2, t, P2);
1656 S->D0(Umax, t, P3);
1657 B = ((P1.Distance(P2) + P2.Distance(P3)) < Tol);
1658
1659
1660 for (ii=1, dt = (Vmax-Vmin)/(Nb+1); B && (ii<=Nb); ii++) {
1661 t = Vmin + ii*dt;
1662 Iso = S->VIso(t);
1663 GeomAdaptor_Curve AC(Iso);
1664 l = GC.Length(AC, Tol/4);
1665 B = (l <= Tol);
1666 }
1667
1668 return B;
1669}
1670
1671//=======================================================================
1672//function : Constructeur
1673//purpose :
1674//======================================================================
1675BRepFill_Sweep::BRepFill_Sweep(const Handle(BRepFill_SectionLaw)& Section,
1676 const Handle(BRepFill_LocationLaw)& Location,
1677 const Standard_Boolean WithKPart) :
1678 isDone(Standard_False),
1679 KPart(WithKPart)
1680
1681
1682{
1683 mySec = Section;
1684 myLoc = Location;
1685
1686 SetTolerance(1.e-4);
1687 SetAngularControl();
1688 myAuxShape.Clear();
1689
1690 myApproxStyle = GeomFill_Location;
1691 myContinuity = GeomAbs_C2;
1692 myDegmax = 11;
1693 mySegmax = 30;
a31abc03 1694 myForceApproxC1 = Standard_False;
7fd59977 1695}
1696
1697//=======================================================================
1698//function : SetBounds
0d969553 1699//purpose : Define start and end shapes
7fd59977 1700//======================================================================
1701 void BRepFill_Sweep::SetBounds(const TopoDS_Wire& First,
1702 const TopoDS_Wire& Last)
1703{
1704 FirstShape = First;
1705 LastShape = Last;
1706
0d969553 1707 // It is necessary to check the SameRange on its (PRO13551)
0797d9d3 1708#ifdef OCCT_DEBUG
7fd59977 1709 Standard_Boolean issame = Standard_True;
96a95605 1710#endif
7fd59977 1711 BRep_Builder B;
1712 BRepTools_WireExplorer wexp;
1713 if (!FirstShape.IsNull()) {
1714 for (wexp.Init(FirstShape); wexp.More(); wexp.Next()) {
1715 if (!BRepLib::CheckSameRange(wexp.Current())) {
1716 B.SameRange(wexp.Current(), Standard_False);
1717 B.SameParameter(wexp.Current(), Standard_False);
0797d9d3 1718#ifdef OCCT_DEBUG
7fd59977 1719 issame = Standard_False;
96a95605 1720#endif
7fd59977 1721 }
1722 }
1723 }
1724
1725 if (!LastShape.IsNull()) {
1726 for (wexp.Init(LastShape); wexp.More(); wexp.Next()) {
1727 if (!BRepLib::CheckSameRange(wexp.Current())) {
1728 B.SameRange(wexp.Current(), Standard_False);
1729 B.SameParameter(wexp.Current(), Standard_False);
0797d9d3 1730#ifdef OCCT_DEBUG
7fd59977 1731 issame = Standard_False;
96a95605 1732#endif
7fd59977 1733 }
1734 }
1735 }
1736
0797d9d3 1737#ifdef OCCT_DEBUG
7fd59977 1738 if (!issame)
0d969553 1739 cout<<"Sweep Warning : Edge not SameRange in the limits"<<endl;
7fd59977 1740#endif
1741}
1742
1743//=======================================================================
1744//function : SetTolerance
1745//purpose :
1746//======================================================================
1747 void BRepFill_Sweep::SetTolerance(const Standard_Real Tol3d,
1748 const Standard_Real BoundTol,
1749 const Standard_Real Tol2d,
1750 const Standard_Real TolAngular)
1751{
1752 myTol3d = Tol3d;
1753 myBoundTol = BoundTol;
1754 myTol2d =Tol2d;
1755 myTolAngular = TolAngular;
1756}
1757//=======================================================================
1758//function : SetAngularControl
1759//purpose :
1760//======================================================================
1761 void BRepFill_Sweep::SetAngularControl(const Standard_Real MinAngle,
1762 const Standard_Real MaxAngle)
1763{
1764 myAngMin = Max (MinAngle, Precision::Angular());
1765 myAngMax = Min (MaxAngle, 6.28);
1766}
1767
a31abc03 1768//=======================================================================
1769//function : SetForceApproxC1
1770//purpose : Set the flag that indicates attempt to approximate
1771// a C1-continuous surface if a swept surface proved
1772// to be C0.
1773//=======================================================================
1774 void BRepFill_Sweep::SetForceApproxC1(const Standard_Boolean ForceApproxC1)
1775{
1776 myForceApproxC1 = ForceApproxC1;
1777}
1778
7fd59977 1779///=======================================================================
1780//function : CorrectApproxParameters
1781//purpose :
1782//=======================================================================
1783 Standard_Boolean BRepFill_Sweep::CorrectApproxParameters()
1784{
1785 TopoDS_Wire thePath = myLoc->Wire();
1786 GeomAbs_Shape NewCont = myContinuity;
1787 Standard_Integer NewSegmax = mySegmax;
1788
1789 TopoDS_Iterator iter(thePath);
1790 for (; iter.More(); iter.Next())
1791 {
1792 TopoDS_Edge anEdge = TopoDS::Edge(iter.Value());
1793 BRepAdaptor_Curve aBAcurve(anEdge);
1794 GeomAbs_Shape aContinuity = aBAcurve.Continuity();
1795 Standard_Integer aNbInterv = aBAcurve.NbIntervals(GeomAbs_CN);
1796 if (aContinuity < NewCont)
1797 NewCont = aContinuity;
1798 if (aNbInterv > NewSegmax)
1799 NewSegmax = aNbInterv;
1800 }
1801
1802 Standard_Boolean Corrected = Standard_False;
1803 if (NewCont != myContinuity || NewSegmax != mySegmax)
1804 Corrected = Standard_True;
1805 myContinuity = NewCont;
1806 mySegmax = NewSegmax;
1807 return Corrected;
1808}
1809
1810//=======================================================================
1811//function : BuildWire
0d969553 1812//purpose : Construit a wire by sweeping
7fd59977 1813//======================================================================
1814 Standard_Boolean BRepFill_Sweep::
1815 BuildWire(const BRepFill_TransitionStyle /*Transition*/)
1816{
1817 Standard_Integer ipath, isec = 1;
1818 gp_Pnt P1;//, P2;
1819
1820 BRep_Builder B;
1821// Class BRep_Tool without fields and without Constructor :
1822// BRep_Tool BT;
1823 Standard_Integer NbPath = myLoc->NbLaw();
1824 Standard_Boolean vclose;
1825 vclose = (myLoc->IsClosed() && (myLoc->IsG1(0, myTol3d)>= 0));
1826 Error = 0.;
1827 Handle(Geom_Surface) S;
1828 Handle(Geom_Curve) Iso;
1829 Standard_Real val, bid, First, Last, Tol;
1830
1831 TopoDS_Wire wire;
1832 TopoDS_Edge E;
1833 B.MakeWire(wire);
1834
0d969553 1835 // (1) Construction of all curves
7fd59977 1836
0d969553 1837 // (1.1) Construction of Tables
7fd59977 1838 myFaces = new (TopTools_HArray2OfShape) (1, 1, 1, NbPath);
1839 myUEdges = new (TopTools_HArray2OfShape) (1, 2, 1, NbPath);
1840 myVEdges = new (TopTools_HArray2OfShape) (1, 1, 1, NbPath+1);
1841
0d969553 1842 // (1.2) Calculate curves / vertex / edge
7fd59977 1843 for (ipath=1; ipath <=NbPath; ipath++) {
0d969553 1844 // Curve by iso value
7fd59977 1845 GeomFill_Sweep Sweep(myLoc->Law(ipath), KPart);
1846 Sweep.SetTolerance(myTol3d, myBoundTol, myTol2d, myTolAngular);
a31abc03 1847 Sweep.SetForceApproxC1(myForceApproxC1);
7fd59977 1848 Sweep.Build(mySec->Law(isec), myApproxStyle, myContinuity, myDegmax, mySegmax);
1849 if (!Sweep.IsDone())
1850 return Standard_False;
1851 S = Sweep.Surface();
1852 if (Sweep.ExchangeUV()) {
1853 if (Sweep.UReversed()) S->Bounds(First, Last, bid, val);
1854 else S->Bounds(First, Last, val, bid);
1855 Iso = S->VIso(val);
1856 }
1857 else {
1858 if (Sweep.UReversed()) S->Bounds(bid, val, First, Last);
1859 else S->Bounds(val, bid, First, Last);
1860 Iso = S->UIso(val);
1861 }
0d969553 1862 // Vertex by position
7fd59977 1863 if (ipath < NbPath)
1864 BuildVertex(Iso, Standard_False, First, Last,
1865 myVEdges->ChangeValue(1, ipath+1));
1866 else {
1867 if (vclose) {
1868 TopoDS_Vertex& V = TopoDS::Vertex(myVEdges->ChangeValue(1, 1));
1869 myVEdges->SetValue(1, ipath+1, V);
1870 Iso->D0(Last, P1);
1871// Tol = P1.Distance(BT.Pnt(V));
1872 Tol = P1.Distance(BRep_Tool::Pnt(V));
1873 B.UpdateVertex(V, Tol);
1874 }
1875 else {
1876 if (!LastShape.IsNull()) myVEdges->SetValue(1, NbPath, FirstShape);
1877 else BuildVertex(Iso, Standard_False, First, Last,
1878 myVEdges->ChangeValue(1, NbPath+1));
1879 }
1880 }
1881
1882 if (ipath > 1) {
1883 Iso->D0(First, P1);
1884 TopoDS_Vertex& V = TopoDS::Vertex(myVEdges->ChangeValue(1, ipath));
1885// Tol = P1.Distance(BT.Pnt(V));
1886 Tol = P1.Distance(BRep_Tool::Pnt(V));
1887 B.UpdateVertex(V, Tol);
1888 }
1889 if (ipath == 1) {
1890 if (!FirstShape.IsNull()) myVEdges->SetValue(1,1, FirstShape);
1891 else BuildVertex(Iso, Standard_True, First, Last,
1892 myVEdges->ChangeValue(1, 1));
1893 }
1894
0d969553 1895 // Construction of the edge
7fd59977 1896 BRepLib_MakeEdge MkE;
1897 MkE.Init(Iso,
1898 TopoDS::Vertex(myVEdges->Value(1, ipath)),
1899 TopoDS::Vertex(myVEdges->Value(1, ipath+1)),
1900 Iso->FirstParameter(),
1901 Iso->LastParameter());
0d969553 1902 if (!MkE.IsDone()) { // Error of construction !!
7fd59977 1903#ifdef DRAW
1904 char name[100];
1905 sprintf(name,"firstvertex_error");
1906 DBRep::Set(name, myVEdges->Value(1, ipath));
1907 sprintf(name,"lastvertex_error");
1908 DBRep::Set(name, myVEdges->Value(1, ipath+1));
1909 sprintf(name,"curve3d_error");
1910 char* Temp = name ;
1911 DrawTrSurf::Set(Temp,Iso);
1912// DrawTrSurf::Set(name,Iso);
1913 Standard_ConstructionError::Raise("BRepFill_Sweep::BuildEdge");
1914#endif
1915 return Standard_False;
1916 }
1917 E = MkE.Edge();
1918#if DRAW
1919 if (Affich) {
1920 sprintf(name,"Surf_%d", ipath);
1921 char* Temp = name;
1922 DrawTrSurf::Set(Temp, S);
1923// DrawTrSurf::Set(name, S);
1924 sprintf(name,"Edge_%d", ipath);
1925 DBRep::Set(name, E);
1926 }
1927#endif
1928 B.UpdateEdge(E, Sweep.ErrorOnSurface());
1929 B.Add(wire, E);
1930 myFaces->SetValue(1, ipath, E);
1931 }
1932 myShape = wire;
1933 return Standard_True;
1934}
1935
1936//=======================================================================
1937//function : BuildShell
0d969553 1938//purpose : Construct a Shell by sweeping
7fd59977 1939//======================================================================
1940 Standard_Boolean BRepFill_Sweep::
1941 BuildShell(const BRepFill_TransitionStyle /*Transition*/,
1942 const Standard_Integer IFirst,
1943 const Standard_Integer ILast,
c8ea5b8e 1944 TopTools_MapOfShape& ReversedEdges,
1945 BRepFill_DataMapOfShapeHArray2OfShape& Tapes,
8e817497 1946 BRepFill_DataMapOfShapeHArray2OfShape& Rails,
7fd59977 1947 const Standard_Real ExtendFirst,
1948 const Standard_Real ExtendLast)
1949{
1950 Standard_Integer ipath, isec, IPath;
1951#ifdef DRAW
1952 char name[100];
1953#endif
1954 BRep_Builder B;
1955 Standard_Integer NbPath = ILast - IFirst;
1956 Standard_Integer NbLaw = mySec->NbLaw();
1957 Standard_Boolean uclose, vclose, constSection, hasdegen = Standard_False;
1958 constSection = mySec->IsConstant();
1959 uclose = mySec->IsUClosed();
1960 vclose = (mySec->IsVClosed() && myLoc->IsClosed()) &&
1961 (NbPath == myLoc->NbLaw()) && (myLoc->IsG1(0, myTol3d)>= 0);
1962 Error = 0.;
1963
0d969553 1964 // (1) Construction of all surfaces
7fd59977 1965
0d969553 1966 // (1.1) Construction of Tables
7fd59977 1967
1968 TColStd_Array2OfInteger ExchUV(1, NbLaw, 1, NbPath);
1969 TColStd_Array2OfInteger UReverse(1, NbLaw, 1, NbPath);
1970 TColStd_Array2OfInteger Degenerated(1, NbLaw, 1, NbPath);
1971 Degenerated.Init(0);
0d969553 1972 // No VReverse for the moment...
7fd59977 1973 TColStd_Array2OfReal TabErr(1, NbLaw , 1, NbPath);
1974 TColGeom_Array2OfSurface TabS(1, NbLaw , 1, NbPath);
1975
1976 TopTools_Array2OfShape UEdge(1, NbLaw+1, 1, NbPath);
1977 TopTools_Array2OfShape VEdge(1, NbLaw , 1, NbPath+1);
1978 TopTools_Array2OfShape Vertex(1,NbLaw+1, 1, NbPath+1);
1979
1980 TopoDS_Vertex VNULL;
1981 VNULL.Nullify();
1982 Vertex.Init(VNULL);
1983
1984 TopTools_Array1OfShape SecVertex(1, NbLaw+1);
1985 TColStd_Array1OfReal VError(1, NbLaw+1);
1986 TColStd_Array1OfReal Vi(1, NbPath+1);
1987
0d969553
Y
1988//Initialization of management of parametric intervals
1989//(Case of evolutionary sections)
7fd59977 1990 Standard_Real Length, SecDom, SecDeb;
1991 myLoc->CurvilinearBounds(myLoc->NbLaw(), SecDom, Length);
1992 mySec->Law(1)->GetDomain(SecDeb, SecDom);
1993 SecDom -= SecDeb;
1994 if (IFirst > 1) {
1995 Standard_Real Lf, Ll;
1996 myLoc->CurvilinearBounds(IFirst-1, Lf, Ll);
1997 Vi(1) = SecDeb + (Ll/Length)*SecDom;
1998 }
1999 else
2000 Vi(1) = SecDeb;
2001
0d969553 2002 // Error a priori on vertices
7fd59977 2003 if (constSection) {
2004 for (isec=1; isec<=NbLaw+1; isec++) {
2005 VError(isec) = mySec->VertexTol(isec-1, 0.);
2006 SecVertex(isec) = mySec->Vertex(isec, 0.);
2007 }
2008 }
2009
2010
0d969553 2011 // (1.2) Calculate surfaces
7fd59977 2012 for (ipath=1, IPath=IFirst; ipath <=NbPath; ipath++, IPath++) {
2013
2014 GeomFill_Sweep Sweep(myLoc->Law(IPath), KPart);
2015 Sweep.SetTolerance(myTol3d, myBoundTol, myTol2d, myTolAngular);
a31abc03 2016 Sweep.SetForceApproxC1(myForceApproxC1);
7fd59977 2017
0d969553 2018 // Case of evolutionary section, definition of parametric correspondence
7fd59977 2019 if (!constSection) {
2020 Standard_Real lf, ll, Lf, Ll;
2021 myLoc->Law(IPath)->GetDomain(lf, ll);
2022 myLoc->CurvilinearBounds(IPath, Lf, Ll);
2023 Vi(ipath+1) = SecDeb + (Ll/Length)*SecDom;
2024 Sweep.SetDomain(lf, ll, Vi(ipath), Vi(ipath+1));
2025 }
2026 else //section is constant
2027 {
2028 Standard_Real lf, ll, Lf, Ll;
2029 myLoc->Law(IPath)->GetDomain(lf, ll);
2030 myLoc->CurvilinearBounds(IPath, Lf, Ll);
2031 Vi(ipath+1) = SecDeb + (Ll/Length)*SecDom;
2032 }
2033
2034 for(isec=1; isec<=NbLaw; isec++) {
2035 Sweep.Build(mySec->Law(isec), myApproxStyle, myContinuity, myDegmax, mySegmax);
2036 if (!Sweep.IsDone())
2037 return Standard_False;
2038 TabS(isec,ipath) = Sweep.Surface();
2039 TabErr(isec,ipath) = Sweep.ErrorOnSurface();
2040 ExchUV(isec, ipath) = Sweep.ExchangeUV();
2041 UReverse(isec, ipath) = Sweep.UReversed();
2042 if (Sweep.ErrorOnSurface()>Error) Error = Sweep.ErrorOnSurface();
2043
2044 if ((ipath==1)&&(ExtendFirst>0)) {
2045 Handle(Geom_BoundedSurface) BndS;
2046 BndS = Handle(Geom_BoundedSurface)::DownCast(TabS(isec,ipath));
2047 GeomLib::ExtendSurfByLength(BndS, ExtendFirst, 1,
2048 Sweep.ExchangeUV(), Standard_False);
2049 TabS(isec,ipath) = BndS;
2050 }
2051 if ((ipath==NbPath)&&(ExtendLast>0)){
2052 Handle(Geom_BoundedSurface) BndS;
2053 BndS = Handle(Geom_BoundedSurface)::DownCast(TabS(isec,ipath));
2054 GeomLib::ExtendSurfByLength(BndS, ExtendLast, 1,
2055 Sweep.ExchangeUV(), Standard_True);
2056 TabS(isec,ipath) = BndS;
2057 }
2058
2059#ifdef DRAW
2060 if (Affich) {
2061 sprintf(name,"Surf_%d_%d", isec, IPath);
2062 char* Temp = name ;
2063 DrawTrSurf::Set(Temp, TabS(isec,ipath));
2064 }
2065#endif
2066 }
2067 }
2068
0d969553 2069 // (2) Construction of Edges
7fd59977 2070 Standard_Real UFirst, ULast, VFirst, VLast;
2071 Standard_Boolean exuv, singu, singv;
2072 Handle(Geom_Surface) S;
2073
cf3327f4 2074 // (2.0) return preexisting Edges and vertices
2075 TopoDS_Edge E;
c8ea5b8e 2076 TColStd_Array1OfBoolean IsBuilt(1, NbLaw);
2077 IsBuilt.Init(Standard_False);
2078 TopTools_Array1OfShape StartEdges(1, NbLaw);
cf3327f4 2079 if (! FirstShape.IsNull() && (IFirst==1)) {
2080 mySec->Init(FirstShape);
2081 for (isec=1; isec<=NbLaw; isec++) {
2082 E = mySec->CurrentEdge();
8e817497 2083 TopoDS_Vertex Vfirst, Vlast;
2084 TopExp::Vertices(E, Vfirst, Vlast);
cf3327f4 2085 VEdge(isec, 1) = E;
2086 if (E.Orientation() == TopAbs_REVERSED)
8e817497 2087 Vertex(isec+1, 1) = Vfirst; //TopExp::FirstVertex(E);
cf3327f4 2088 else
8e817497 2089 Vertex(isec+1, 1) = Vlast; //TopExp::LastVertex(E);
cf3327f4 2090 UpdateVertex(IFirst-1, isec+1,
2091 TabErr(isec, 1), Vi(1), Vertex(isec+1, 1));
c8ea5b8e 2092
2093 StartEdges(isec) = E;
2094 if (Tapes.IsBound(E))
2095 {
2096 IsBuilt(isec) = Standard_True;
2097
2098 //Initialize VEdge, UEdge, Vertex and myFaces
2099 Standard_Integer j;
2100 for (j = 1; j <= NbPath+1; j++)
2101 {
2102 VEdge(isec, j) = Tapes(E)->Value(1, j);
2103 VEdge(isec, j).Reverse(); //direction of round is reversed
2104 }
2105 Standard_Integer ifirst = isec+1, ilast = isec; //direction of round is reversed
2106 for (j = 1; j <= NbPath; j++)
2107 UEdge(ifirst, j) = Tapes(E)->Value(2, j);
2108 for (j = 1; j <= NbPath; j++)
2109 UEdge(ilast, j) = Tapes(E)->Value(3, j);
2110 for (j = 1; j <= NbPath+1; j++)
2111 Vertex(ifirst, j) = Tapes(E)->Value(4, j);
2112 for (j = 1; j <= NbPath+1; j++)
2113 Vertex(ilast, j) = Tapes(E)->Value(5, j);
2114 for (j = 1; j <= NbPath; j++)
2115 myFaces->SetValue(isec, j, Tapes(E)->Value(6, j));
2116
2117 if (uclose && isec == 1)
2118 {
2119 for (j = 1; j <= NbPath; j++)
2120 UEdge(NbLaw+1, j) = UEdge(1, j);
2121 for (j = 1; j <= NbPath+1; j++)
2122 Vertex(NbLaw+1, j) = Vertex(1, j);
2123 }
2124 if (uclose && isec == NbLaw)
2125 {
2126 for (j = 1; j <= NbPath; j++)
2127 UEdge(1, j) = UEdge(NbLaw+1, j);
2128 for (j = 1; j <= NbPath+1; j++)
2129 Vertex(1, j) = Vertex(NbLaw+1, j);
2130 }
2131 }
2132 else
2133 {
2134 Handle(TopTools_HArray2OfShape) EmptyArray = new TopTools_HArray2OfShape(1, 6, 1, NbPath+1);
2135 Tapes.Bind(E, EmptyArray);
8e817497 2136 Standard_Integer j;
2137 if (Rails.IsBound(Vfirst))
2138 {
2139 Standard_Integer ind = (E.Orientation() == TopAbs_REVERSED)? isec+1 : isec;
2140 for (j = 1; j <= NbPath; j++)
2141 UEdge(ind, j) = Rails(Vfirst)->Value(1, j);
2142 for (j = 1; j <= NbPath+1; j++)
2143 Vertex(ind, j) = Rails(Vfirst)->Value(2, j);
2144 }
2145 if (Rails.IsBound(Vlast))
2146 {
2147 Standard_Integer ind = (E.Orientation() == TopAbs_FORWARD)? isec+1 : isec;
2148 for (j = 1; j <= NbPath; j++)
2149 UEdge(ind, j) = Rails(Vlast)->Value(1, j);
2150 for (j = 1; j <= NbPath+1; j++)
2151 Vertex(ind, j) = Rails(Vlast)->Value(2, j);
2152 }
c8ea5b8e 2153 }
7fd59977 2154 }
c8ea5b8e 2155
cf3327f4 2156 if (VEdge(1, 1).Orientation() == TopAbs_REVERSED)
2157 Vertex(1, 1) = TopExp::LastVertex(TopoDS::Edge(VEdge(1, 1)));
2158 else
2159 Vertex(1, 1) = TopExp::FirstVertex(TopoDS::Edge(VEdge(1, 1)));
2160 UpdateVertex(IFirst-1, 1,
2161 TabErr(1, 1), Vi(1), Vertex(1, 1));
2162 }
c8ea5b8e 2163
2164 Standard_Real u, v, aux;
2165 Standard_Boolean ureverse;
2166 for (isec=1; isec<=NbLaw+1; isec++) {
2167 // Return data
2168 if (isec >NbLaw) {
2169 S = TabS(NbLaw, 1);
2170 ureverse = UReverse(NbLaw, 1);
2171 exuv = ExchUV(NbLaw, 1);
2172 }
2173 else {
2174 S = TabS(isec, 1);
2175 ureverse = UReverse(isec, 1);
2176 exuv = ExchUV(isec, 1);
2177 }
2178 S->Bounds(UFirst, ULast, VFirst, VLast);
2179
2180 // Choice of parameters
2181 if (ureverse) {
2182 if (exuv) {
2183 aux = VFirst; VFirst = VLast; VLast = aux;
7fd59977 2184 }
cf3327f4 2185 else {
c8ea5b8e 2186 aux = UFirst; UFirst = ULast; ULast = aux;
cf3327f4 2187 }
c8ea5b8e 2188 }
2189 if (isec!= NbLaw+1) {
2190 u = UFirst;
2191 v = VFirst;
2192 }
2193 else {
2194 if (exuv) {
cf3327f4 2195 u = UFirst;
8e817497 2196 v = VLast;
cf3327f4 2197 }
2198 else {
c8ea5b8e 2199 u = ULast;
2200 v = VFirst;
7fd59977 2201 }
c8ea5b8e 2202 }
2203
2204 // construction of vertices
2205 if (Vertex(isec, 1).IsNull())
cf3327f4 2206 B.MakeVertex(TopoDS::Vertex(Vertex(isec, 1)),
2207 S->Value(u,v),
2208 mySec->VertexTol(isec-1,Vi(1)));
c8ea5b8e 2209 else
2210 {
2211 TopLoc_Location Identity;
2212 Vertex(isec, 1).Location(Identity);
2213 B.UpdateVertex(TopoDS::Vertex(Vertex(isec, 1)),
2214 S->Value(u,v),
2215 mySec->VertexTol(isec-1,Vi(1)));
cf3327f4 2216 }
c8ea5b8e 2217 } //end of for (isec=1; isec<=NbLaw+1; isec++)
2218
cf3327f4 2219 if (! LastShape.IsNull() && (ILast==myLoc->NbLaw()+1) ) {
2220 mySec->Init(LastShape);
2221 for (isec=1; isec<=NbLaw; isec++) {
2222 E = mySec->CurrentEdge();
c8ea5b8e 2223 if (VEdge(isec, NbPath+1).IsNull())
2224 VEdge(isec, NbPath+1) = E;
2225
2226 if (Vertex(isec+1, NbPath+1).IsNull())
2227 {
2228 if (VEdge(isec, NbPath+1).Orientation() == TopAbs_REVERSED)
2229 Vertex(isec+1, NbPath+1) = TopExp::FirstVertex(TopoDS::Edge(VEdge(isec, NbPath+1)));
2230 else
2231 Vertex(isec+1, NbPath+1) = TopExp::LastVertex(TopoDS::Edge(VEdge(isec, NbPath+1)));
2232 }
cf3327f4 2233 UpdateVertex(ILast-1, isec+1, TabErr(isec, NbPath),
2234 Vi(NbPath+1), Vertex(isec+1, NbPath+1));
2235 }
c8ea5b8e 2236
2237 if (Vertex(1, NbPath+1).IsNull())
2238 {
2239 if (VEdge(1, NbPath+1).Orientation() == TopAbs_REVERSED)
2240 Vertex(1, NbPath+1) = TopExp::LastVertex(TopoDS::Edge(VEdge(1, NbPath+1)));
2241 else
2242 Vertex(1, NbPath+1) = TopExp::FirstVertex(TopoDS::Edge(VEdge(1, NbPath+1)));
2243 }
cf3327f4 2244 UpdateVertex(ILast-1, 1,
2245 TabErr(1, NbPath), Vi(NbPath+1), Vertex(1, NbPath+1 ));
c8ea5b8e 2246 }
2247
2248 for (isec=1; isec<=NbLaw+1; isec++) {
2249 // Return data
2250 if (isec >NbLaw) {
cf3327f4 2251 S = TabS(NbLaw, NbPath);
2252 ureverse = UReverse(NbLaw, NbPath);
2253 exuv = ExchUV(NbLaw, NbPath);
c8ea5b8e 2254 }
2255 else {
2256 S = TabS(isec, NbPath);
2257 ureverse = UReverse(isec, NbPath);
2258 exuv = ExchUV(isec, NbPath);
2259 }
2260 S->Bounds(UFirst, ULast, VFirst, VLast);
2261
2262 // Choice of parametres
2263 if (ureverse) {
2264 if (exuv) {
2265 aux = VFirst; VFirst = VLast; VLast = aux;
cf3327f4 2266 }
2267 else {
c8ea5b8e 2268 aux = UFirst; UFirst = ULast; ULast = aux;
cf3327f4 2269 }
c8ea5b8e 2270 }
2271 if (isec == NbLaw+1) {
2272 u = ULast;
2273 v = VLast;
2274 }
2275 else {
2276 if (exuv) {
cf3327f4 2277 u = ULast;
c8ea5b8e 2278 v = VFirst;
7fd59977 2279 }
cf3327f4 2280 else {
c8ea5b8e 2281 u = UFirst;
2282 v = VLast;
cf3327f4 2283 }
c8ea5b8e 2284 }
2285
2286 // construction of vertex
2287 if (Vertex(isec, NbPath+1).IsNull())
cf3327f4 2288 B.MakeVertex(TopoDS::Vertex(Vertex(isec, NbPath+1)),
2289 S->Value(u,v),
2290 mySec->VertexTol(isec-1, Vi(NbPath+1)));
c8ea5b8e 2291 else
2292 {
2293 TopLoc_Location Identity;
2294 Vertex(isec, NbPath+1).Location(Identity);
2295 B.UpdateVertex(TopoDS::Vertex(Vertex(isec, NbPath+1)),
2296 S->Value(u,v),
2297 mySec->VertexTol(isec-1, Vi(NbPath+1)));
2298 }
2299 } //end of for (isec=1; isec<=NbLaw+1; isec++)
7fd59977 2300
2301
0d969553 2302 // ---------- Creation of Vertex and edge ------------
f52d1b53 2303 ReversedEdges.Clear();
7fd59977 2304 for (ipath=1, IPath=IFirst; ipath<=NbPath;
2305 ipath++, IPath++) {
2306 for (isec=1; isec <=NbLaw; isec++) {
c8ea5b8e 2307 if (IsBuilt(isec))
2308 continue;
2309
7fd59977 2310 S = TabS(isec, ipath);
2311 exuv = ExchUV(isec, ipath);
2312 S->Bounds(UFirst, ULast, VFirst, VLast);
2313 if (UReverse(isec, ipath)) {
2314 Standard_Real aux;
2315 if (exuv) {
2316 aux = VFirst; VFirst = VLast; VLast = aux;
2317 }
2318 else {
2319 aux = UFirst; UFirst = ULast; ULast = aux;
2320 }
2321 }
2322
0d969553 2323 // (2.1) Construction of new vertices
7fd59977 2324 if (isec == 1) {
2325 if (ipath == 1 && Vertex(1, 1).IsNull()) {
0d969553 2326 // All first
7fd59977 2327 if (constSection)
2328 myLoc->PerformVertex(IPath-1,
2329 TopoDS::Vertex(SecVertex(1)),
2330 VError(1),
2331 TopoDS::Vertex(Vertex(1, 1)));
2332 else
2333 myLoc->PerformVertex(IPath-1,
2334 mySec->Vertex(1,Vi(1)),
2335 mySec->VertexTol(0,Vi(1)),
2336 TopoDS::Vertex(Vertex(1, 1)));
2337 }
0d969553 2338 // the first and the next column
7fd59977 2339 if (vclose &&(ipath == NbPath) ) {
2340 Vertex(1, ipath+1) = Vertex(1, 1);
2341 }
2342 else if (Vertex(1, ipath+1).IsNull()) {
2343 if (constSection)
2344 myLoc->PerformVertex(IPath,
2345 TopoDS::Vertex(SecVertex(1)),
2346 TabErr(1,ipath)+VError(1),
2347 TopoDS::Vertex(Vertex(1, ipath+1)) );
2348 else
2349 myLoc->PerformVertex(IPath,
2350 mySec->Vertex(1,Vi(ipath+1)),
2351 TabErr(1,ipath) +
2352 mySec->VertexTol(0,Vi(ipath+1)),
2353 TopoDS::Vertex(Vertex(1, ipath+1)));
2354
2355 if (MergeVertex(Vertex(1,ipath), Vertex(1,ipath+1))) {
2356 UEdge(1, ipath) = NullEdge(Vertex(1,ipath));
2357 }
2358 }
2359 }
2360
eafb234b 2361 if (ipath == 1) {
2362 if (uclose && (isec == NbLaw)) {
2363 Vertex(isec+1, 1) = Vertex(1, 1);
2364 }
2365 else if (Vertex(isec+1, 1).IsNull()) {
2366 if (constSection)
2367 myLoc->PerformVertex(IPath-1,
2368 TopoDS::Vertex(SecVertex(isec+1)),
2369 TabErr(isec,1)+VError(isec+1),
2370 TopoDS::Vertex(Vertex(isec+1, 1)) );
2371 else
2372 myLoc->PerformVertex(IPath-1,
2373 mySec->Vertex(isec+1,Vi(1)),
2374 TabErr(isec,1) +
2375 mySec->VertexTol(isec,Vi(1)),
2376 TopoDS::Vertex(Vertex(isec+1, 1)) );
c8ea5b8e 2377
eafb234b 2378 if (MergeVertex(Vertex(isec,1), Vertex(isec+1,1))) {
2379 VEdge(isec, 1) = NullEdge(Vertex(isec, 1));
2380 }
2381 }
2382 }
7fd59977 2383
2384 if (uclose && (isec == NbLaw)) {
2385 Vertex(isec+1, ipath+1) = Vertex(1, ipath+1);
2386 }
2387 else if (vclose && (ipath == NbPath)) {
2388 Vertex(isec+1, ipath+1) = Vertex(isec+1, 1);
2389 }
2390 else if (Vertex(isec+1, ipath+1).IsNull()) {
2391 if (constSection)
2392 myLoc->PerformVertex(IPath,
2393 TopoDS::Vertex(SecVertex(isec+1)),
2394 TabErr(isec, ipath)+ VError(isec+1),
2395 TopoDS::Vertex(Vertex(isec+1, ipath+1)) );
2396 else
2397 myLoc->PerformVertex(IPath,
2398 mySec->Vertex(isec+1,Vi(ipath+1)),
2399 TabErr(isec, ipath) +
2400 mySec->VertexTol(isec, Vi(ipath+1)),
2401 TopoDS::Vertex(Vertex(isec+1, ipath+1)) );
2402 }
2403
0d969553 2404 // Singular cases
7fd59977 2405 singv = MergeVertex(Vertex(isec,ipath+1), Vertex(isec+1,ipath+1));
2406 singu = MergeVertex(Vertex(isec+1,ipath), Vertex(isec+1,ipath+1));
2407
2408
2409
2410 if (singu || singv) {
2411 Degenerated(isec, ipath) = IsDegen(TabS(isec,ipath),
2412 Max(myTol3d, TabErr(isec,ipath)));
2413 }
2414 if (Degenerated(isec, ipath)) {
0797d9d3 2415#ifdef OCCT_DEBUG
0d969553 2416 cout << "Sweep : Degenerated case" << endl;
7fd59977 2417#endif
2418 hasdegen = Standard_True;
0d969553 2419 // Particular construction of edges
7fd59977 2420 if (UEdge(isec+1, ipath).IsNull()) {
2421 if (singu) {
0d969553 2422 // Degenerated edge
7fd59977 2423 UEdge(isec+1, ipath) = NullEdge(Vertex(isec+1,ipath));
2424 }
0d969553 2425 else { // Copy the previous edge
7fd59977 2426 UEdge(isec+1, ipath) = UEdge(isec, ipath);
2427 }
2428 }
2429 if (VEdge(isec, ipath+1).IsNull()) {
2430 if (singv) {
0d969553 2431 // Degenerated Edge
7fd59977 2432 VEdge(isec, ipath+1) = NullEdge(Vertex(isec,ipath+1));
2433 }
0d969553 2434 else { // Copy the previous edge
7fd59977 2435 VEdge(isec, ipath+1) = VEdge(isec, ipath);
2436 }
2437 }
2438 }
0d969553 2439 else { // Construction of edges by isos
7fd59977 2440 if (exuv) {
2441 Standard_Real UV;
2442 UV = UFirst; UFirst = VFirst; VFirst = UV;
2443 UV = ULast ; ULast = VLast ; VLast = UV;
2444 }
2445
2446 // (2.2) Iso-u
c8ea5b8e 2447 if (isec == 1 && UEdge(1, ipath).IsNull()) {
7fd59977 2448 if (!Vertex(1,ipath).IsSame(Vertex(1,ipath+1))) {
2449 gp_Pnt P1 = BRep_Tool::Pnt(TopoDS::Vertex(Vertex(1,ipath)));
2450 gp_Pnt P2 = BRep_Tool::Pnt(TopoDS::Vertex(Vertex(1,ipath+1)));
2451 if (P1.Distance(P2) <= myTol3d)
2452 Vertex(1,ipath+1) = Vertex(1,ipath);
2453 }
2454 UEdge(1, ipath) = BuildEdge(S, !exuv, UFirst,
2455 Vertex(1,ipath),
2456 Vertex(1,ipath+1),
2457 myTol3d);
2458 }
73920cd4 2459 else
2460 {
2461 if (UEdge(isec, ipath).IsNull()) //sweep failed
2462 return Standard_False;
2463 UpdateEdge(TopoDS::Edge(UEdge(isec, ipath)),
2464 S, !exuv, UFirst);
2465 }
7fd59977 2466
2467 if (uclose && (isec==NbLaw)) {
21b7d8be 2468 if (UEdge(1, ipath).IsNull()) //degenerated case
2469 {
2470 UEdge(isec+1, ipath) = BuildEdge(S, !exuv, ULast,
2471 Vertex(isec+1, ipath),
2472 Vertex(isec+1, ipath+1),
2473 myTol3d);
2474 }
2475 else {
2476 UpdateEdge(TopoDS::Edge(UEdge(1, ipath)),
2477 S, !exuv, ULast);
2478 UEdge(isec+1, ipath) = UEdge(1, ipath);
2479 }
7fd59977 2480 }
2481 else {
c8ea5b8e 2482 if (UEdge(isec+1, ipath).IsNull())
2483 UEdge(isec+1, ipath) = BuildEdge(S, !exuv, ULast,
2484 Vertex(isec+1, ipath),
2485 Vertex(isec+1, ipath+1),
2486 myTol3d);
2487 else
2488 UpdateEdge(TopoDS::Edge(UEdge(isec+1, ipath)), S, !exuv, ULast);
7fd59977 2489 }
2490
2491 // (2.3) Iso-v
c8ea5b8e 2492 if (ipath == 1)
2493 {
2494 TopoDS_Edge aNewFirstEdge = BuildEdge(S, exuv, VFirst,
2495 Vertex(isec , 1),
2496 Vertex(isec+1, 1),
2497 myTol3d);
2498 if (VEdge(isec, ipath).IsNull())
2499 VEdge(isec, ipath) = aNewFirstEdge;
2500 else //rebuild first edge
d3dfddae 2501 {
c8ea5b8e 2502 RebuildTopOrBottomEdge(aNewFirstEdge,
2503 TopoDS::Edge(VEdge(isec, ipath)),
2504 ReversedEdges);
d3dfddae 2505 if (ReversedEdges.Contains(VEdge(isec, ipath)))
2506 StartEdges(isec).Reverse();
2507 }
c8ea5b8e 2508 }
7fd59977 2509
2510 else UpdateEdge(TopoDS::Edge(VEdge(isec, ipath)),
2511 S, exuv, VFirst);
2512
2513 if (vclose && (ipath == NbPath)) {
21b7d8be 2514 if (VEdge(isec, 1).IsNull()) //degenerated case
2515 {
2516 VEdge(isec, ipath+1) = BuildEdge(S, exuv, VLast,
2517 Vertex(isec , ipath+1),
2518 Vertex(isec+1, ipath+1),
2519 myTol3d);
2520 }
2521 else {
2522 UpdateEdge(TopoDS::Edge(VEdge(isec, 1)),
2523 S, exuv, VLast);
2524 VEdge(isec, ipath+1) = VEdge(isec, 1);
2525 }
7fd59977 2526 }
2527 else if (VEdge(isec, ipath+1).IsNull())
2528 VEdge(isec, ipath+1) = BuildEdge(S, exuv, VLast,
2529 Vertex(isec , ipath+1),
2530 Vertex(isec+1, ipath+1),
2531 myTol3d);
c8ea5b8e 2532 else
2533 {
2534 if (ipath != NbPath || vclose)
2535 UpdateEdge(TopoDS::Edge(VEdge(isec, ipath+1)),
2536 S, exuv, VLast);
2537 else //ipath == NbPath && !vclose => rebuild last edge
2538 {
2539 TopoDS_Edge aNewLastEdge = BuildEdge(S, exuv, VLast,
2540 Vertex(isec , ipath+1),
2541 Vertex(isec+1, ipath+1),
2542 myTol3d);
2543 RebuildTopOrBottomEdge(aNewLastEdge,
2544 TopoDS::Edge(VEdge(isec, ipath+1)),
2545 ReversedEdges);
2546 }
2547 }
7fd59977 2548 }
0d969553 2549 }// End of construction of edges
7fd59977 2550 }
2551
0d969553 2552 // (3) Construction of Faces
7fd59977 2553 TopoDS_Face face;
2554
2555#ifdef DRAW
2556 if (Affich) {
2557 for (ipath=1, IPath=IFirst; ipath<=NbPath; ipath++, IPath++) {
2558 for (isec=1; isec <=NbLaw+1; isec++){
2559 sprintf(name,"uedge_%d_%d", isec, IPath);
2560 DBRep::Set(name,UEdge(isec, ipath));
2561 }
2562 }
2563
2564 for (ipath=1, IPath=IFirst; ipath<=NbPath+1; ipath++, IPath++) {
2565 for (isec=1; isec <=NbLaw; isec++){
2566 sprintf(name,"vedge_%d_%d", isec, IPath);
2567 DBRep::Set(name,VEdge(isec, ipath));
2568 }
2569
2570 for (isec=1; isec <=NbLaw+1; isec++){
2571 sprintf(name,"vertex_%d_%d", isec, IPath);
2572 DBRep::Set(name,Vertex(isec, ipath));
2573 }
2574 }
2575 }
2576#endif
2577
2578 for (ipath=1, IPath=IFirst; ipath<=NbPath; ipath++, IPath++) {
2579 for (isec=1; isec <=NbLaw; isec++) {
2580 if (Degenerated(isec, ipath)) {
2581 if (UEdge(isec, ipath).IsSame(UEdge(isec+1, ipath)))
2582 myFaces->SetValue(isec, IPath, UEdge(isec, ipath));
2583 else
2584 myFaces->SetValue(isec, IPath, VEdge(isec, ipath));
2585 }
c8ea5b8e 2586 else if (myFaces->Value(isec, IPath).IsNull()) {
7fd59977 2587 BuildFace(TabS(isec,ipath),
2588 TopoDS::Edge(UEdge(isec, ipath)),
2589 TopoDS::Edge(VEdge(isec, ipath)),
2590 TopoDS::Edge(UEdge(isec+1, ipath)),
2591 TopoDS::Edge(VEdge(isec, ipath+1)),
2592 myVEdgesModified,
2593 ExchUV(isec, ipath),
2594 UReverse(isec, ipath),
2595 face);
2596 myFaces->SetValue(isec, IPath, face);
2597 }
2598 }
2599 }
2600
c8ea5b8e 2601 // (3.1) Reverse the faces that have been built ealier
2602 for (ipath = 1; ipath <= NbPath; ipath++)
2603 for (isec = 1; isec <= NbLaw; isec++)
2604 if (IsBuilt(isec))
2605 myFaces->ChangeValue(isec, ipath).Reverse();
2606
7fd59977 2607
0d969553 2608 // (4) History and Continuity
7fd59977 2609
2610 if (hasdegen) {
0d969553 2611 //(4.1) // Degenerated case => Sledgehammer
7fd59977 2612 TopoDS_Compound Comp;
2613 B.MakeCompound(Comp);
2614 for (isec=1; isec <= NbLaw+1; isec++)
2615 for (ipath=1, IPath=IFirst; ipath<= NbPath+1; ipath++, IPath++) {
2616 if (ipath <= NbPath) myUEdges->SetValue(isec, IPath, UEdge(isec, ipath));
2617 if (isec <= NbLaw) myVEdges->SetValue(isec, IPath, VEdge(isec, ipath));
2618 if ((ipath <= NbPath) && (isec <= NbLaw) &&
2619 (myFaces->Value(isec, IPath).ShapeType() == TopAbs_FACE))
2620 B.Add(Comp, myFaces->Value(isec, IPath));
2621 }
2622 BRepLib::EncodeRegularity(Comp, myTolAngular);
2623 }
2624 else {
0d969553 2625 //(4.2) // General case => Tweezers
7fd59977 2626 Standard_Boolean isG1;
2627 TopoDS_Face FF;
2628 TopoDS_Edge E;
2629
2630 for (isec=1; isec <= NbLaw+1; isec++) {
2631 if (isec>1) isG1 =
2632 (mySec->Continuity(isec-1, myTolAngular) >= GeomAbs_G1);
2633 else isG1 = Standard_False;
2634 for (ipath=1, IPath=IFirst; ipath<= NbPath; ipath++, IPath++) {
2635 myUEdges->SetValue(isec, IPath, UEdge(isec, ipath));
2636 if (isG1) {
2637 if (isec == NbLaw+1) FF = TopoDS::Face(myFaces->Value(1, IPath));
2638 else FF = TopoDS::Face(myFaces->Value(isec, IPath));
2639 B.Continuity(TopoDS::Edge(myUEdges->Value(isec, IPath)),
2640 TopoDS::Face(myFaces->Value(isec-1, IPath)),
2641 FF, GeomAbs_G1);
2642 }
2643 }
2644 }
2645
2646 Standard_Integer nbpath = NbPath;
0d969553 2647 if (vclose) nbpath++; //Another test G1
7fd59977 2648 for (ipath=1, IPath=IFirst; ipath<= NbPath+1; ipath++, IPath++) {
2649 if ((ipath > 1) && (ipath <=nbpath))
2650 isG1 = (myLoc->IsG1(IPath-1, myTol3d, myTolAngular) >= 0);
2651 else isG1 = Standard_False;
2652 for (isec=1; isec <= NbLaw; isec++) {
2653 myVEdges->SetValue(isec, IPath, VEdge(isec, ipath));
2654 if (isG1) {
2655 if (ipath==NbPath+1) FF = TopoDS::Face(myFaces->Value(isec, 1));
2656 else FF = TopoDS::Face(myFaces->Value(isec, IPath));
2657 E = TopoDS::Edge(myVEdges->Value(isec, IPath));
2658 BRepLib::EncodeRegularity(E, FF,
2659 TopoDS::Face(myFaces->Value(isec, IPath-1)),
2660 myTolAngular);
2661 }
2662 }
2663 }
2664 }
c8ea5b8e 2665
8e817497 2666 // (5) Update Tapes and Rails
c8ea5b8e 2667 Standard_Integer j;
2668 if (IFirst == 1 && !Tapes.IsEmpty()) //works only in case of single shell
2669 {
2670 for (isec = 1; isec <= NbLaw; isec++)
2671 {
2672 for (j = 1; j <= NbPath+1; j++)
2673 Tapes(StartEdges(isec))->SetValue(1, j, myVEdges->Value(isec, j));
2674 for (j = 1; j <= NbPath; j++)
2675 Tapes(StartEdges(isec))->SetValue(2, j, myUEdges->Value(isec, j));
2676 for (j = 1; j <= NbPath; j++)
2677 Tapes(StartEdges(isec))->SetValue(3, j, myUEdges->Value(isec+1, j));
2678 for (j = 1; j <= NbPath+1; j++)
2679 Tapes(StartEdges(isec))->SetValue(4, j, Vertex(isec, j));
2680 for (j = 1; j <= NbPath+1; j++)
2681 Tapes(StartEdges(isec))->SetValue(5, j, Vertex(isec+1, j));
2682 for (j = 1; j <= NbPath; j++)
2683 Tapes(StartEdges(isec))->SetValue(6, j, myFaces->Value(isec, j));
8e817497 2684 TopoDS_Vertex Vfirst, Vlast;
d3dfddae 2685 TopExp::Vertices(TopoDS::Edge(StartEdges(isec)), Vfirst, Vlast, Standard_True); //with orientation
8e817497 2686 if (!Rails.IsBound(Vfirst))
2687 {
2688 Handle(TopTools_HArray2OfShape) anArray = new TopTools_HArray2OfShape(1, 2, 1, NbPath+1);
2689 for (j = 1; j <= NbPath; j++)
2690 anArray->SetValue(1, j, myUEdges->Value(isec, j));
2691 for (j = 1; j <= NbPath+1; j++)
2692 anArray->SetValue(2, j, Vertex(isec, j));
2693 Rails.Bind(Vfirst, anArray);
2694 }
2695 if (!Rails.IsBound(Vlast))
2696 {
2697 Handle(TopTools_HArray2OfShape) anArray = new TopTools_HArray2OfShape(1, 2, 1, NbPath+1);
2698 for (j = 1; j <= NbPath; j++)
2699 anArray->SetValue(1, j, myUEdges->Value(isec+1, j));
2700 for (j = 1; j <= NbPath+1; j++)
2701 anArray->SetValue(2, j, Vertex(isec+1, j));
2702 Rails.Bind(Vlast, anArray);
2703 }
c8ea5b8e 2704 }
2705 }
2706
7fd59977 2707 return Standard_True;
2708}
2709
2710//=======================================================================
2711//function : Build
0d969553 2712//purpose : Construt the result of sweeping
7fd59977 2713//======================================================================
c8ea5b8e 2714void BRepFill_Sweep::Build(TopTools_MapOfShape& ReversedEdges,
2715 BRepFill_DataMapOfShapeHArray2OfShape& Tapes,
8e817497 2716 BRepFill_DataMapOfShapeHArray2OfShape& Rails,
c8ea5b8e 2717 const BRepFill_TransitionStyle Transition,
2718 const GeomAbs_Shape Continuity,
2719 const GeomFill_ApproxStyle Approx,
2720 const Standard_Integer Degmax,
2721 const Standard_Integer Segmax)
7fd59977 2722{
7fd59977 2723 myContinuity = Continuity;
a31abc03 2724 myApproxStyle = Approx;
7fd59977 2725 myDegmax = Degmax;
2726 mySegmax = Segmax;
2727
2728 CorrectApproxParameters();
2729
2730 // Wire
2731 if (mySec->IsVertex()) isDone = BuildWire(Transition);
2732
2733 else { // Shell
2734 Standard_Integer NbTrous = myLoc->NbHoles(myTol3d),
2735 NbPath = myLoc->NbLaw(),
2736 NbLaw = mySec->NbLaw(), ii, jj, NbPart=1;
2737 Standard_Integer ipath, isec;
2738 BRep_Builder B;
2739 myUEdges = new (TopTools_HArray2OfShape) (1, NbLaw+1, 1, NbPath);
2740 myVEdges = new (TopTools_HArray2OfShape) (1, NbLaw, 1, NbPath+1);
2741 myFaces = new (TopTools_HArray2OfShape) (1, NbLaw, 1, NbPath);
2742 Handle (TopTools_HArray2OfShape) Bounds =
2743 new (TopTools_HArray2OfShape) (1, NbLaw, 1, 2);
2744
2745 Handle(TColStd_HArray1OfInteger) Trous;
2746
0d969553 2747 if (NbTrous>0) { // How many sub-parts ?
7fd59977 2748 Trous = new (TColStd_HArray1OfInteger) (1, NbTrous);
2749 myLoc->Holes(Trous->ChangeArray1());
2750 NbPart += NbTrous;
2751 if (Trous->Value(NbTrous) == NbPath+1) NbPart--;
2752 }
0d969553 2753 if (NbPart == 1) { // This is done at once
7fd59977 2754 Standard_Real Extend = 0.0;
2755 if (NbTrous==1) Extend = EvalExtrapol(1, Transition);
2756 isDone = BuildShell(Transition,
2757 1, NbPath+1,
c8ea5b8e 2758 ReversedEdges,
8e817497 2759 Tapes, Rails,
7fd59977 2760 Extend, Extend);
2761 }
0d969553 2762 else { // This is done piece by piece
7fd59977 2763 Standard_Integer IFirst = 1, ILast;
2764 for (ii=1, isDone=Standard_True;
2765 ii<=NbPart && isDone; ii++) {
2766 if (ii > NbTrous) ILast = NbPath+1;
2767 else ILast = Trous->Value(ii);
2768 isDone = BuildShell(Transition,
2769 IFirst, ILast,
c8ea5b8e 2770 ReversedEdges,
8e817497 2771 Tapes, Rails,
7fd59977 2772 EvalExtrapol(IFirst, Transition),
2773 EvalExtrapol(ILast, Transition));
2774 if (IFirst>1) {
2775 Translate(myVEdges, IFirst, Bounds, 2);
2776 PerformCorner(IFirst,
2777 Transition, Bounds);
2778 }
2779 IFirst = ILast;
2780 Translate(myVEdges, IFirst, Bounds, 1);
2781 }
2782 }
0d969553 2783 // Management of looping ends
7fd59977 2784 if ( (NbTrous>0) && (myLoc->IsClosed()) &&
2785 (Trous->Value(NbTrous) == NbPath+1) ) {
2786 Translate(myVEdges, NbPath+1, Bounds, 1);
2787 Translate(myVEdges, 1, Bounds, 2);
2788 PerformCorner(1, Transition, Bounds);
2789 }
2790
0d969553 2791 // Construction of the shell
7fd59977 2792 TopoDS_Shell shell;
2793 B.MakeShell(shell);
2794 for (ipath=1; ipath<=NbPath; ipath++)
2795 for (isec=1; isec <=NbLaw; isec++) {
2796 const TopoDS_Shape& face = myFaces->Value(isec, ipath);
2797 if (!face.IsNull() &&
2798 (face.ShapeType() == TopAbs_FACE) ) B.Add(shell, face);
2799 }
2800
2801 TopTools_ListIteratorOfListOfShape It(myAuxShape);
2802 for (; It.More(); It.Next()) {
2803 const TopoDS_Shape& face = It.Value();
2804 if (!face.IsNull() &&
2805 (face.ShapeType() == TopAbs_FACE) ) B.Add(shell, face);
2806 }
2807 //Set common Uedges to faces
2808 BRepTools_Substitution aSubstitute;
2809 /*
2810 for (ii = 1; ii <= NbLaw; ii++)
2811 for (jj = 1; jj <= NbPath; jj++)
2812 {
2813 SetCommonEdgeInFace(aSubstitute,
2814 myFaces->Value(ii, jj),
2815 myUEdges->Value(ii, jj));
2816 SetCommonEdgeInFace(aSubstitute,
2817 myFaces->Value(ii, jj),
2818 myUEdges->Value(ii+1, jj));
2819 }
2820 if (mySec->IsUClosed())
2821 for (jj = 1; jj <= NbPath; jj++)
2822 SetCommonEdgeInFace(aSubstitute,
2823 myFaces->Value( 1, jj ),
2824 myUEdges->Value( NbLaw+1, jj));
2825 */
2826 TopTools_DataMapIteratorOfDataMapOfShapeShape mapit( myVEdgesModified );
2827 for (; mapit.More(); mapit.Next())
2828 {
2829 const TopoDS_Edge& OldEdge = TopoDS::Edge(mapit.Key());
2830 const TopoDS_Edge& NewEdge = TopoDS::Edge(mapit.Value());
2831 Substitute( aSubstitute, OldEdge, NewEdge );
2832 }
2833 aSubstitute.Build( shell );
2834 if (aSubstitute.IsCopied( shell )) {
2835 const TopTools_ListOfShape& listSh = aSubstitute.Copy( shell );
2836 shell = TopoDS::Shell( listSh.First() );
2837 }
2838
2839 for (ii = myFaces->LowerRow(); ii <= myFaces->UpperRow(); ii++) {
2840 for (jj = myFaces->LowerCol(); jj <= myFaces->UpperCol(); jj++) {
2841 const TopoDS_Shape& aLocalShape = myFaces->Value(ii, jj);
2842
2843 if(!aLocalShape.IsNull() && aSubstitute.IsCopied(aLocalShape)) {
2844 const TopTools_ListOfShape& aList = aSubstitute.Copy(aLocalShape);
2845
2846 if(!aList.IsEmpty())
2847 myFaces->ChangeValue(ii, jj) = aList.First();
2848 }
2849 }
2850 }
2851
2852 for (ii = myVEdges->LowerRow(); ii <= myVEdges->UpperRow(); ii++) {
2853 for (jj = myVEdges->LowerCol(); jj <= myVEdges->UpperCol(); jj++) {
2854 const TopoDS_Shape& aLocalShape = myVEdges->Value(ii, jj);
2855
2856 if(!aLocalShape.IsNull() && aSubstitute.IsCopied(aLocalShape)) {
2857 const TopTools_ListOfShape& aList = aSubstitute.Copy(aLocalShape);
2858
2859 if(!aList.IsEmpty())
2860 myVEdges->ChangeValue(ii, jj) = aList.First();
2861 }
2862 }
2863 }
2864
2865 for (ii = myUEdges->LowerRow(); ii <= myUEdges->UpperRow(); ii++) {
2866 for (jj = myUEdges->LowerCol(); jj <= myUEdges->UpperCol(); jj++) {
2867 const TopoDS_Shape& aLocalShape = myUEdges->Value(ii, jj);
2868
2869 if(!aLocalShape.IsNull() && aSubstitute.IsCopied(aLocalShape)) {
2870 const TopTools_ListOfShape& aList = aSubstitute.Copy(aLocalShape);
2871
2872 if(!aList.IsEmpty())
2873 myUEdges->ChangeValue(ii, jj) = aList.First();
2874 }
2875 }
2876 }
2877
0d969553 2878 // Is it Closed ?
7fd59977 2879 if (myLoc->IsClosed() && mySec->IsUClosed()) {
0d969553 2880 //Check
7fd59977 2881 Standard_Boolean closed = Standard_True;
2882 Standard_Integer iedge;
2883 TopTools_IndexedDataMapOfShapeListOfShape EFmap;
2884 TopExp::MapShapesAndAncestors(shell, TopAbs_EDGE,
2885 TopAbs_FACE, EFmap);
2886
2887 for (iedge = 1; iedge <=EFmap.Extent() && closed; iedge++) {
2888 const TopoDS_Edge& theEdge = TopoDS::Edge(EFmap.FindKey(iedge));
2889 if (BRep_Tool::Degenerated(theEdge)) continue;
2890 closed = ( EFmap(iedge).Extent() > 1);
2891 }
2892 shell.Closed(closed);
2893 }
2894 myShape = shell;
2895 }
2896}
2897
2898
2899//=======================================================================
2900//function : IsDone
2901//purpose :
2902//=======================================================================
2903 Standard_Boolean BRepFill_Sweep::IsDone() const
2904{
2905 return isDone;
2906}
2907
2908//=======================================================================
2909//function : Shape
2910//purpose :
2911//=======================================================================
2912 TopoDS_Shape BRepFill_Sweep::Shape() const
2913{
2914 return myShape;
2915}
2916
2917//=======================================================================
2918//function : ErrorOnSurface
2919//purpose :
2920//=======================================================================
2921 Standard_Real BRepFill_Sweep::ErrorOnSurface() const
2922{
2923 return Error;
2924}
2925
2926//=======================================================================
2927//function : SubShape
0d969553 2928//purpose : Faces obtained by sweeping
7fd59977 2929//=======================================================================
2930 Handle(TopTools_HArray2OfShape) BRepFill_Sweep::SubShape() const
2931{
2932 return myFaces;
2933}
2934
2935//=======================================================================
2936//function : InterFaces
0d969553 2937//purpose : Edges obtained by sweeping
7fd59977 2938//=======================================================================
2939 Handle(TopTools_HArray2OfShape) BRepFill_Sweep::InterFaces() const
2940{
2941 return myUEdges;
2942}
2943
2944//=======================================================================
2945//function : Sections
0d969553 2946//purpose : Edges or Face (or compound of 2) Transition between 2 sweepings
7fd59977 2947//=======================================================================
2948 Handle(TopTools_HArray2OfShape) BRepFill_Sweep::Sections() const
2949{
2950 return myVEdges;
2951}
2952
2953//=======================================================================
2954//function : PerformCorner
0d969553 2955//purpose : Trim and/or loop a corner
7fd59977 2956//======================================================================
2957 void BRepFill_Sweep::PerformCorner(const Standard_Integer Index,
2958 const BRepFill_TransitionStyle Transition,
2959 const Handle(TopTools_HArray2OfShape)& Bounds)
2960{
2961
0d969553 2962 if (Transition == BRepFill_Modified) return; // Do nothing.
7fd59977 2963
2964 BRepFill_TransitionStyle TheTransition = Transition;
2965 Standard_Boolean isTangent=Standard_False;
2966 Standard_Real F, L;
2967 Standard_Integer I1, I2, ii; //, jj;
2968 gp_Pnt P1,P2;
2969 gp_Vec T1, T2, Tang, Sortant;
2970// gp_Mat M;
2971 //Handle(TopTools_HArray1OfShape) TheShape =
2972 //new TopTools_HArray1OfShape( 1, mySec->NbLaw() );
2973// TopTools_ListIteratorOfListOfShape Iterator;
2974
2975 if (Index > 1) {
2976 I1 = Index-1;
2977 I2 = Index;
2978 }
2979 else {
2980 I1 = myLoc->NbLaw();
2981 I2 = 1;
2982 }
2983
0d969553 2984 // Construct an axis supported by the bissectrice
7fd59977 2985 myLoc->Law(I1)->GetDomain(F, L);
2986 myLoc->Law(I1)->GetCurve()->D1(L, P1, T1);
2987 T1.Normalize();
2988
2989 myLoc->Law(I2)->GetDomain(F, L);
2990 myLoc->Law(I2)->GetCurve()->D1(F, P2, T2);
2991 T2.Normalize();
2992
2993 if (T1.Angle(T2) < myAngMin) {
2994 isTangent = Standard_True;
2995 gp_Vec t1, t2, V;
2996 gp_Mat M;
2997 myLoc->Law(I1)->GetDomain(F, L);
2998 myLoc->Law(I1)->D0(L, M, V);
2999 t1 = M.Column(3);
3000 myLoc->Law(I2)->GetDomain(F, L);
3001 myLoc->Law(I2)->D0(L, M, V);
3002 t2 = M.Column(3);
3003
3004 if (t1.Angle(t2) < myAngMin) {
0797d9d3 3005#ifdef OCCT_DEBUG
0d969553 3006 cout << "BRepFill_Sweep::PerformCorner : This is not a corner !" << endl;
7fd59977 3007#endif
3008 return;
3009 }
3010 Sortant = t2 - t1;
3011 }
3012
3013 if ((TheTransition == BRepFill_Right)
3014 && (T1.Angle(T2) > myAngMax) ) {
3015 TheTransition = BRepFill_Round;
3016 }
3017
0d969553 3018 Tang = T1 + T2; //Average direction
7fd59977 3019 gp_Dir NormalOfBisPlane = Tang;
3020
3021 if (isTangent) {
3022 Sortant -= Tang.Dot(Tang)*Tang;
3023 }
3024 else {
0d969553
Y
3025 Sortant = T2-T1; //Direction input
3026 Sortant *= -1; // " " output
7fd59977 3027 Tang -= (Tang.Dot(T2))*T2;
3028 }
3029
3030 P1.BaryCenter(0.5, P2, 0.5);
3031 gp_Dir N(Sortant);
3032 gp_Dir Dx(Tang);
3033
3034 gp_Ax2 Axe (P1, N, Dx);
3035 gp_Ax2 AxeOfBisPlane( P1, NormalOfBisPlane );
3036
0d969553 3037 // Construct 2 intersecting Shells
7fd59977 3038 Handle (TopTools_HArray2OfShape) UEdges =
3039 new TopTools_HArray2OfShape( 1, mySec->NbLaw()+1, 1, myLoc->NbLaw() );
3040 UEdges->ChangeArray2() = myUEdges->Array2();
3041
3042// modified by NIZHNY-MKK Wed Oct 29 18:31:47 2003.BEGIN
3043 Handle (TopTools_HArray2OfShape) aFaces =
3044 new TopTools_HArray2OfShape(myFaces->LowerRow(), myFaces->UpperRow(), 1, 2);
3045 Translate(myFaces, I1, aFaces, 1);
3046 Translate(myFaces, I2, aFaces, 2);
3047
3048 Handle (TopTools_HArray2OfShape) aUEdges =
3049 new TopTools_HArray2OfShape(myUEdges->LowerRow(), myUEdges->UpperRow(), 1, 2);
3050 Translate(myUEdges, I1, aUEdges, 1);
3051 Translate(myUEdges, I2, aUEdges, 2);
3052
3053 gp_Vec aNormal = T2 + T1;
3054 TopoDS_Face aPlaneF;
3055
3056 if(aNormal.Magnitude() > gp::Resolution()) {
3057 gp_Pln pl(P1, gp_Dir(aNormal));
3058 BRepLib_MakeFace aFMaker(pl);
3059
3060 if(aFMaker.Error() == BRepLib_FaceDone) {
3061 aPlaneF = aFMaker.Face();
3062 BRep_Builder aBB;
3063 aBB.UpdateFace(aPlaneF, Precision::Confusion() * 10.);
3064 }
3065 }
3066
3067 BRepFill_TrimShellCorner aTrim(aFaces, AxeOfBisPlane, aPlaneF);
3068 aTrim.AddBounds(Bounds);
3069 aTrim.AddUEdges(aUEdges);
3070 aTrim.Perform();
3071
3072 if (aTrim.IsDone()) {
3073 TopTools_ListOfShape listmodif;
3074 Standard_Integer iit = 0;
3075
3076 for(iit = 0; iit < 2; iit++) {
3077 Standard_Integer II = (iit == 0) ? I1 : I2;
3078
3079 for (ii = 1; ii <= mySec->NbLaw(); ii++) {
3080 aTrim.Modified(myFaces->Value(ii, II), listmodif);
3081
3082 if(!listmodif.IsEmpty()) {
3083 myFaces->SetValue(ii, II, listmodif.First());
3084 }
3085 }
3086
3087 for (ii = myUEdges->LowerRow(); ii <= myUEdges->UpperRow(); ii++) {
3088 aTrim.Modified(myUEdges->Value(ii, II), listmodif);
3089
3090 if(!listmodif.IsEmpty()) {
3091 myUEdges->SetValue(ii, II, listmodif.First());
3092 }
3093 }
3094 }
3095 }
3096 else if ((TheTransition == BRepFill_Right) ||
3097 aTrim.HasSection() ) {
0797d9d3 3098#ifdef OCCT_DEBUG
0d969553 3099 cout << "Fail of TrimCorner" << endl;
7fd59977 3100#endif
0d969553 3101 return; // Nothing is touched
7fd59977 3102 }
3103
3104 if (mySec->IsUClosed())
3105 {
3106 myUEdges->SetValue( 1, I1, myUEdges->Value(mySec->NbLaw()+1, I1) );
3107 myUEdges->SetValue( 1, I2, myUEdges->Value(mySec->NbLaw()+1, I2) );
3108 }
3109
3110 if (TheTransition == BRepFill_Round) {
0d969553 3111 // Filling
7fd59977 3112 TopTools_ListOfShape list1, list2;
3113 TopoDS_Edge Bord1, Bord2, BordFirst;
3114 BordFirst.Nullify();
3115 Bord1.Nullify();
3116 Bord2.Nullify();
3117 Standard_Boolean HasFilling = Standard_False;
3118 TopoDS_Face FF;
3119 for (ii=1; ii<=mySec->NbLaw(); ii++) {
3120 KeepEdge(myFaces->Value(ii, I1), Bounds->Value(ii, 1), list1);
3121 KeepEdge(myFaces->Value(ii, I2), Bounds->Value(ii, 2), list2);
3122 if (list1.Extent() == list2.Extent()) {
3123 TopTools_ListIteratorOfListOfShape It1(list1);
3124 TopTools_ListIteratorOfListOfShape It2(list2);
3125 Standard_Boolean B;
3126 for (; It1.More(); It1.Next(), It2.Next()) {
0d969553 3127 if (HasFilling) { // Transversal choice of constraints
7fd59977 3128 TopoDS_Vertex VF, VL, VC;
3129 TopoDS_Edge E = TopoDS::Edge(It1.Value());
3130 TopoDS_Edge E1, E2;
3131 E1.Nullify();
3132 E2.Nullify();
3133 TopExp::Vertices(E, VF, VL);
3134 if (!Bord1.IsNull() &&
3135 TopExp::CommonVertex(E, Bord1, VC)) {
3136 if (VC.IsSame(VF)) E1 = Bord1;
3137 else E2 = Bord1;
3138 }
3139 if (!Bord2.IsNull() &&
3140 TopExp::CommonVertex(E, Bord2, VC)) {
3141 if (VC.IsSame(VF)) E1 = Bord2;
3142 else E2 = Bord2;
3143 }
3144 if (!BordFirst.IsNull() &&
3145 TopExp::CommonVertex(E, BordFirst, VC)) {
3146 if (VC.IsSame(VF)) E1 = BordFirst;
3147 else E2 = BordFirst;
3148 }
3149 Bord1 = E1;
3150 Bord2 = E2;
3151 }
3152
0d969553 3153 // Filling
7fd59977 3154 B = Filling(It1.Value(), myFaces->Value(ii, I1),
3155 It2.Value(), myFaces->Value(ii, I2),
3156 myVEdgesModified, myTol3d, Axe, T1, Bord1, Bord2, FF);
3157
3158 if (B) {
3159 myAuxShape.Append(FF);
3160 myVEdges->ChangeValue(ii, I2) = FF;
3161 HasFilling = Standard_True;
3162 }
3163 if (ii==1) BordFirst = Bord1;
3164 }
3165 }
0797d9d3 3166#ifdef OCCT_DEBUG
0d969553 3167 else cout << "PerformCorner : Unsymmetry of free border" << endl;
7fd59977 3168#endif
3169 }
3170 }
3171
3172/*
3173#if DRAW
3174 if (Affich) {
3175 Standard_Integer jj;
3176 char name[100];
3177 DBRep::Set("TrimmedShell", TheShape);
3178 for (jj=1; jj <=myFaces->ColLength(); jj++){
3179 sprintf(name,"Tfaces_%d_%d", jj, I1);
3180 DBRep::Set(name, myFaces->Value(jj, I1));
3181 sprintf(name,"Tfaces_%d_%d", jj, I2);
3182 DBRep::Set(name, myFaces->Value(jj, I2));
3183 }
3184 }
3185#endif
3186*/
3187}
3188
3189//=======================================================================
3190//function : EvalExtrapol
3191//purpose :
3192//======================================================================
3193Standard_Real BRepFill_Sweep::
3194 EvalExtrapol(const Standard_Integer Index,
3195 const BRepFill_TransitionStyle Transition) const
3196{
3197 Standard_Real Extrap = 0.0;
3198 if (Transition == BRepFill_Right) {
3199 Standard_Integer I1, I2;
3200 if ((Index == 1) || (Index ==myLoc->NbLaw()+1) ) {
3201 if (!myLoc->IsClosed() || !mySec->IsVClosed()) return Extrap;
3202 I1 = myLoc->NbLaw();
3203 I2 = 1;
3204 }
3205 else {
3206 I1 = Index-1;
3207 I2 = Index;
3208 }
3209
3210 gp_Vec V1, V2, T1, T2;
3211 gp_Mat M1, M2;
3212 Standard_Real Xmin, Ymin, Zmin, Xmax, Ymax, Zmax, R, f, l;
3213
3214 myLoc->Law(I1)->GetDomain(f, l);
3215 myLoc->Law(I1)->D0(l, M1, V1);
3216 T1.SetXYZ(M1.Column(3));
3217 myLoc->Law(I2)->GetDomain(f, l);
3218 myLoc->Law(I2)->D0(f, M2, V2);
3219 T2.SetXYZ(M2.Column(3));
3220
3221 Standard_Real alpha = T1.Angle(T2);
3222 if ((alpha > myAngMax) || (alpha < myAngMin)) {
0d969553
Y
3223 //Angle too great => No "straight" connection
3224 //Angle too small => No connection
7fd59977 3225 return Extrap; // = 0.0
3226 }
3227
3228 Handle(GeomFill_SectionLaw) Sec;
3229 Sec = mySec->ConcatenedLaw();
3230
3231 //Calculating parameter U
3232 Standard_Real U, Length, SecFirst, SecLen, Lf, Ll;
3233 myLoc->CurvilinearBounds( myLoc->NbLaw(), Lf, Length );
3234 mySec->Law(1)->GetDomain( SecFirst, SecLen );
3235 SecLen -= SecFirst;
3236 myLoc->CurvilinearBounds( I1, Lf, Ll );
3237 U = SecFirst + (Ll/Length)*SecLen;
3238
3239 Bnd_Box box;
3240 //Box(Sec, 0., box);
3241 Box(Sec, U, box);
3242 box.Get(Xmin, Ymin, Zmin, Xmax, Ymax, Zmax);
3243
3244 R = Max(Max(Abs(Xmin), Abs(Xmax)),Max(Abs(Ymin), Abs(Ymax)));
3245 //R *= 1.1;
3246 // modified by NIZHNY-MKK Fri Oct 31 18:57:51 2003
3247 // Standard_Real coef = 1.2;
3248 Standard_Real coef = 2.;
3249 R *= coef;
3250 Extrap = Max(Abs(Zmin), Abs(Zmax)) + 100*myTol3d;
3251 Extrap += R*Tan(alpha/2);
3252 }
3253 return Extrap;
3254}
3255
3256//=======================================================================
3257//function : MergeVertex
0d969553 3258//purpose : Make V2 = V1 if V2 is too close to V1
7fd59977 3259//======================================================================
3260Standard_Boolean BRepFill_Sweep::MergeVertex(const TopoDS_Shape& V1,
3261 TopoDS_Shape& V2) const
3262{
3263// Class BRep_Tool without fields and without Constructor :
3264// BRep_Tool BT;
3265 const TopoDS_Vertex& v1 = TopoDS::Vertex(V1);
3266 const TopoDS_Vertex& v2 = TopoDS::Vertex(V2);
3267 Standard_Real tol;
3268// tol = Max(BT.Tolerance(v1), BT.Tolerance(v2));
3269 tol = Max(BRep_Tool::Tolerance(v1), BRep_Tool::Tolerance(v2));
3270 if (tol < myTol3d) tol = myTol3d;
3271// if (BT.Pnt(v1).Distance(BT.Pnt(v2)) <= tol ){
3272 if (BRep_Tool::Pnt(v1).Distance(BRep_Tool::Pnt(v2)) <= tol ){
3273 V2 = V1;
3274 return Standard_True;
3275 }
3276 return Standard_False;
3277}
3278
3279
3280//=======================================================================
3281//function : UpdateVertex
0d969553 3282//purpose : Update the Tolerance of Vertices depending on Laws.
7fd59977 3283//======================================================================
3284void BRepFill_Sweep::UpdateVertex(const Standard_Integer ipath,
3285 const Standard_Integer isec,
3286 const Standard_Real ErrApp,
3287 const Standard_Real Param,
3288 TopoDS_Shape& V) const
3289{
3290 TopoDS_Vertex vv, TheV;
3291 TheV = TopoDS::Vertex(V);
3292 myLoc->PerformVertex(ipath,
3293 mySec->Vertex(isec, Param),
3294 ErrApp+mySec->VertexTol(isec-1, Param),
3295 vv);
3296// Class BRep_Tool without fields and without Constructor :
3297// BRep_Tool BT;
3298 gp_Pnt P1, P2;
3299// P1 = BT.Pnt(vv);
3300 P1 = BRep_Tool::Pnt(vv);
3301// P2 = BT.Pnt(TheV);
3302 P2 = BRep_Tool::Pnt(TheV);
3303
3304// Standard_Real Tol = BT.Tolerance(vv);
3305 Standard_Real Tol = BRep_Tool::Tolerance(vv);
3306 Tol += P1.Distance(P2);
3307
3308// if (Tol > BT.Tolerance(TheV)) {
3309 if (Tol > BRep_Tool::Tolerance(TheV)) {
3310 BRep_Builder B;
3311 B.UpdateVertex(TheV, Tol);
3312 }
3313}
c8ea5b8e 3314
3315//=======================================================================
3316//function : RebuildTopOrBottomEdge
3317//purpose : Rebuild v-iso edge of top or bottom section
3318// inserting new 3d and 2d curves taken from swept surfaces
3319//======================================================================
3320void BRepFill_Sweep::RebuildTopOrBottomEdge(const TopoDS_Edge& aNewEdge,
3321 TopoDS_Edge& anEdge,
3322 TopTools_MapOfShape& ReversedEdges) const
3323{
3324 Standard_Real fpar, lpar;
3325 Handle(Geom_Curve) aNewCurve = BRep_Tool::Curve(aNewEdge, fpar, lpar);
3326 TopLoc_Location Identity;
3327
3328 Standard_Boolean ToReverse = Standard_False;
3329 Standard_Boolean IsDegen = BRep_Tool::Degenerated(aNewEdge);
3330 if (IsDegen)
3331 BRep_Tool::Range(aNewEdge, fpar, lpar);
3332 else
3333 {
3334 TopoDS_Vertex V1, V2, NewV1, NewV2;
3335 TopExp::Vertices(anEdge, V1, V2);
3336 if (!V1.IsSame(V2))
3337 {
3338 TopExp::Vertices(aNewEdge, NewV1, NewV2);
3339 V1.Location(Identity);
3340 if (!V1.IsSame(NewV1))
3341 {
3342 if (V1.IsSame(NewV2))
3343 ToReverse = Standard_True;
3344 else
3345 {
3346 gp_Pnt Pnt1 = BRep_Tool::Pnt(V1);
3347 gp_Pnt NewPnt1 = BRep_Tool::Pnt(NewV1);
3348 Standard_Real TolSum = BRep_Tool::Tolerance(V1) + BRep_Tool::Tolerance(NewV1);
3349 if (!Pnt1.IsEqual(NewPnt1, TolSum))
3350 ToReverse = Standard_True;
3351 }
3352 }
3353 }
3354 else
3355 {
3356 Standard_Real OldFirst, OldLast;
3357 Handle(Geom_Curve) OldCurve = BRep_Tool::Curve(anEdge, OldFirst, OldLast);
3358 gp_Vec OldD1, NewD1;
3359 gp_Pnt MidPnt;
3360 OldCurve->D1(0.5*(OldFirst + OldLast), MidPnt, OldD1);
3361 aNewCurve->D1(0.5*(fpar + lpar), MidPnt, NewD1);
3362 if (OldD1 * NewD1 < 0.)
3363 ToReverse = Standard_True;
3364 }
3365 }
3366
3367 anEdge.Location(Identity);
3368 const Handle(BRep_TEdge)& TEdge = *((Handle(BRep_TEdge)*) &anEdge.TShape());
3369 TEdge->Tolerance(BRep_Tool::Tolerance(aNewEdge));
3370 BRep_Builder BB;
3371 BB.Range(anEdge, fpar, lpar);
3372 BB.UpdateEdge(anEdge, aNewCurve, Precision::Confusion());
3373 const Handle(BRep_TEdge)& TE = *((Handle(BRep_TEdge)*) &aNewEdge.TShape());
3374 const BRep_ListOfCurveRepresentation& lcr = TE->Curves();
3375 BRep_ListIteratorOfListOfCurveRepresentation itrep(lcr);
3376 for (; itrep.More(); itrep.Next())
3377 {
3378 const Handle(BRep_CurveRepresentation)& CurveRep = itrep.Value();
3379 if (CurveRep->IsCurveOnSurface())
3380 {
3381 const Handle(BRep_GCurve)& GC = *((Handle(BRep_GCurve)*)&CurveRep);
3382 Handle(Geom2d_Curve) aPCurve = GC->PCurve();
3383 Handle(Geom_Surface) aSurf = GC->Surface();
3384 TopLoc_Location aLoc = aNewEdge.Location() * GC->Location();
3385 BB.UpdateEdge(anEdge, aPCurve, aSurf, aLoc, Precision::Confusion());
3386 }
3387 }
3388
3389 anEdge.Free(Standard_True);
3390 TopoDS_Vertex V1, V2;
3391 TopExp::Vertices(anEdge, V1, V2);
3392
3393 TopoDS_Shape anEdgeFORWARD = anEdge.Oriented(TopAbs_FORWARD);
3394
3395 BB.Remove(anEdgeFORWARD, V1);
3396 BB.Remove(anEdgeFORWARD, V2);
3397
3398 V1.Location(Identity);
3399 V2.Location(Identity);
3400 if (ToReverse)
3401 {
3402 V2.Orientation(TopAbs_FORWARD);
3403 V1.Orientation(TopAbs_REVERSED);
3404 }
3405 BB.Add(anEdgeFORWARD, V1);
3406 BB.Add(anEdgeFORWARD, V2);
3407
3408 if (ToReverse)
3409 {
3410 anEdge.Reverse();
3411 ReversedEdges.Add(anEdge);
3412 }
3413
3414 BB.Degenerated(anEdge, IsDegen);
3415}