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