0024624: Lost word in license statement in source files
[occt.git] / src / BRepAlgo / BRepAlgo.cxx
1 // Created on: 1997-03-10
2 // Created by: Stagiaire Francois DUMONT
3 // Copyright (c) 1997-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
8 // This library is free software; you can redistribute it and/or modify it under
9 // the terms of the GNU Lesser General Public License version 2.1 as published
10 // by the Free Software Foundation, with special exception defined in the file
11 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12 // distribution for complete text of the license and disclaimer of any warranty.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 #include <BRepAlgo.ixx>
18 #include <BRepTools_WireExplorer.hxx>
19 #include <BRep_Tool.hxx>
20 #include <BRepLib_MakeEdge.hxx>
21 #include <BRepLib_MakeWire.hxx>
22 #include <gp_Pnt.hxx>
23 #include <GeomConvert.hxx>
24 #include <GeomLProp.hxx>
25 #include <Geom_TrimmedCurve.hxx>
26 #include <Precision.hxx>
27 #include <Standard_ConstructionError.hxx>
28 #include <TColGeom_Array1OfBSplineCurve.hxx>
29 #include <TColGeom_HArray1OfBSplineCurve.hxx>
30 #include <TColStd_Array1OfReal.hxx>
31 #include <TColStd_Array1OfBoolean.hxx>
32 #include <TopoDS_Edge.hxx>
33 #include <TopoDS_Vertex.hxx>
34 #include <TopLoc_Location.hxx>
35 #include <TopExp.hxx>
36
37 #include <TColGeom_SequenceOfCurve.hxx>
38 #include <TopTools_SequenceOfShape.hxx>
39 #include <TColStd_SequenceOfReal.hxx>
40 #include <TColStd_SequenceOfBoolean.hxx>
41 #include <GeomAbs_CurveType.hxx>
42 #include <BRepAdaptor_Curve.hxx>
43 #include <ElCLib.hxx>
44 #include <BRepLib.hxx>
45 #include <TopoDS.hxx>
46 #include <ShapeFix_Shape.hxx>
47 #include <GeomConvert_CompCurveToBSplineCurve.hxx>
48
49 //Temporary
50 #//include <DrawTrSurf.hxx>
51
52
53 //=======================================================================
54 //function : ConcatenateWire
55 //purpose  : 
56 //=======================================================================
57
58 TopoDS_Wire  BRepAlgo::ConcatenateWire(const TopoDS_Wire& W,
59                                        const GeomAbs_Shape Option,
60                                        const Standard_Real TolAngular) 
61 {
62
63
64   Standard_Integer        nb_curve,                         //number of curves in the Wire
65                           index;
66   BRepTools_WireExplorer  WExp(W) ;
67   TopoDS_Edge             edge;
68   TopLoc_Location         L ;
69   Standard_Real           First=0.,Last=0.,                       //extremal values for the curve
70                           First0 =0.,
71                           toler =0.,
72                           tolleft,tolright;                 //Vertex tolerances
73   TopoDS_Vertex           Vfirst,Vlast;                     //Vertex of the Wire
74   gp_Pnt                  Pfirst,Plast;            //, Pint;  corresponding points
75
76   BRepLib_MakeWire        MakeResult;                       
77   Standard_Real           closed_tolerance =0.0;
78   Standard_Boolean        closed_flag = Standard_False ;
79   
80   nb_curve = 0;
81   
82   while ( WExp.More()){                                     //computation of the curve number
83     nb_curve++ ;
84     WExp.Next();
85   }
86   
87   if (nb_curve > 1) {
88     TColGeom_Array1OfBSplineCurve tab(0,nb_curve-1);          //array of the wire's curve
89     TColStd_Array1OfReal tabtolvertex(0,nb_curve-2);          //array of the tolerance's vertex
90     
91     WExp.Init(W);
92     
93     for (index=0 ;index<nb_curve; index++){                   //main loop
94       edge = WExp.Current() ;
95       Handle(Geom_Curve) aCurve = BRep_Tool::Curve(edge, L, First, Last);
96       Handle(Geom_TrimmedCurve) aTrCurve = new Geom_TrimmedCurve(aCurve, First, Last);
97       tab(index) = GeomConvert::CurveToBSplineCurve(aTrCurve); //storage in a array 
98       tab(index)->Transform(L.Transformation());
99       GeomConvert::C0BSplineToC1BSplineCurve(tab(index),Precision::Confusion());
100       
101       if (index >= 1){                                         //continuity test loop
102         if (edge.Orientation()==TopAbs_REVERSED)
103           tab(index)->Reverse();
104         tolleft=BRep_Tool::Tolerance(TopExp::LastVertex(edge));
105         tolright=BRep_Tool::Tolerance(TopExp::FirstVertex(edge));
106         tabtolvertex(index-1)=Max(tolleft,tolright);
107       }
108       
109       if(index==0){                                           //storage of the first edge features
110         First0=First;
111         if(edge.Orientation()==TopAbs_REVERSED){             //(usefull for the closed wire) 
112           Vfirst=TopExp::LastVertex(edge);
113           tab(index)->Reverse();
114         }
115         else
116           Vfirst=TopExp::FirstVertex(edge);
117       }
118       
119       if(index==nb_curve-1){                                  //storage of the last edge features
120         if(edge.Orientation()==TopAbs_REVERSED)
121           Vlast=TopExp::FirstVertex(edge);
122         else
123           Vlast=TopExp::LastVertex(edge);
124       }
125       WExp.Next() ; 
126     }
127   
128     if (BRep_Tool::Tolerance(Vfirst)>BRep_Tool::Tolerance(Vlast)) //computation of the closing tolerance
129       toler=BRep_Tool::Tolerance(Vfirst);
130     else
131       toler=BRep_Tool::Tolerance(Vlast);
132     
133     Pfirst=BRep_Tool::Pnt(Vfirst);
134     Plast=BRep_Tool::Pnt(Vlast); 
135     
136     if ((Pfirst.Distance(Plast)<=toler)&&                   //C0 continuity test at the closing point
137         (GeomLProp::Continuity(tab(nb_curve-1),tab(0),Last,First0,
138                                Standard_True,Standard_True, 
139                                toler, TolAngular)>=GeomAbs_G1)) 
140       {
141         closed_tolerance =toler;                                        //if ClosedG1!=0 it will be True and
142         closed_flag = Standard_True ;
143       }                                                        //with the toler value
144     Handle(TColGeom_HArray1OfBSplineCurve)  concatcurve;     //array of the concatenated curves
145     Handle(TColStd_HArray1OfInteger)        ArrayOfIndices;  //array of the remining Vertex
146     if (Option==GeomAbs_G1)
147       GeomConvert::ConcatG1(tab,
148                             tabtolvertex,
149                             concatcurve,
150                             closed_flag,
151                             closed_tolerance) ;    //G1 concatenation
152     else
153       GeomConvert::ConcatC1(tab,
154                             tabtolvertex,
155                             ArrayOfIndices,
156                             concatcurve,
157                             closed_flag,
158                             closed_tolerance);   //C1 concatenation
159     
160     for (index=0;index<=(concatcurve->Length()-1);index++){    //building of the resulting Wire
161       BRepLib_MakeEdge EdgeBuilder(concatcurve->Value(index));
162       edge = EdgeBuilder.Edge();
163       MakeResult.Add(edge);
164     } 
165
166   }
167   else {
168     TColGeom_Array1OfBSplineCurve tab(0,0);          //array of the wire's curve
169     TColStd_Array1OfReal tabtolvertex(0,0);          //array of the tolerance's vertex 
170     WExp.Init(W);
171     
172     edge = WExp.Current() ;
173     tab(0)  = GeomConvert::CurveToBSplineCurve(new      //storage in a array 
174                                                      Geom_TrimmedCurve(BRep_Tool::Curve(edge,L,First,Last),First,Last));
175     tab(0)->Transform(L.Transformation());
176     GeomConvert::C0BSplineToC1BSplineCurve(tab(0),Precision::Confusion());
177     if (edge.Orientation()==TopAbs_REVERSED)
178           tab(0)->Reverse();
179     tolleft=BRep_Tool::Tolerance(TopExp::LastVertex(edge));
180     tolright=BRep_Tool::Tolerance(TopExp::FirstVertex(edge));
181     tabtolvertex(0)=Max(tolleft,tolright);
182     if(edge.Orientation()==TopAbs_REVERSED){             //(usefull for the closed wire) 
183           Vfirst=TopExp::LastVertex(edge);
184           Vlast=TopExp::FirstVertex(edge);
185     }
186     else {
187       
188       Vfirst=TopExp::FirstVertex(edge);
189       Vlast = TopExp::LastVertex(edge) ;
190     }
191     Pfirst=BRep_Tool::Pnt(Vfirst);
192     Plast=BRep_Tool::Pnt(Vlast); 
193     if ((Pfirst.Distance(Plast)<=toler)&&                   //C0 continuity test at the closing point
194         (GeomLProp::Continuity(tab(0),tab(0),Last,First,
195                                Standard_True,Standard_True,
196                                toler, TolAngular)>=GeomAbs_G1)) 
197       {
198         closed_tolerance =toler;                                        //if ClosedG1!=0 it will be True and
199         closed_flag = Standard_True ;
200       }                                                        //with the toler value
201     Handle(TColGeom_HArray1OfBSplineCurve)  concatcurve;     //array of the concatenated curves
202     Handle(TColStd_HArray1OfInteger)        ArrayOfIndices;  //array of the remining Vertex
203     if (Option==GeomAbs_G1)
204       GeomConvert::ConcatG1(tab,
205                             tabtolvertex,
206                             concatcurve,
207                             closed_flag,
208                             closed_tolerance) ;    //G1 concatenation
209     else
210       GeomConvert::ConcatC1(tab,
211                             tabtolvertex,
212                             ArrayOfIndices,
213                             concatcurve,
214                             closed_flag,
215                             closed_tolerance);   //C1 concatenation
216     
217     for (index=0;index<=(concatcurve->Length()-1);index++){    //building of the resulting Wire
218       BRepLib_MakeEdge EdgeBuilder(concatcurve->Value(index));
219       edge = EdgeBuilder.Edge();
220       MakeResult.Add(edge);
221     } 
222   }
223   return MakeResult.Wire() ;  
224   
225 }
226
227 //=======================================================================
228 //function : ConcatenateWireC0
229 //purpose  : 
230 //=======================================================================
231
232 TopoDS_Edge  BRepAlgo::ConcatenateWireC0(const TopoDS_Wire& aWire)
233 {
234   Standard_Real LinTol = Precision::Confusion();
235   Standard_Real AngTol = Precision::Angular();
236
237   TopoDS_Edge ResEdge;
238
239   TopoDS_Wire theWire = aWire;
240   BRepLib::BuildCurves3d(theWire);
241   Handle(ShapeFix_Shape) Fixer = new ShapeFix_Shape(theWire);
242   Fixer->SetPrecision(LinTol);
243   Fixer->SetMaxTolerance(LinTol);
244   Fixer->Perform();
245   theWire = TopoDS::Wire(Fixer->Shape());
246
247   TColGeom_SequenceOfCurve CurveSeq;
248   TColStd_SequenceOfReal FparSeq;
249   TColStd_SequenceOfReal LparSeq;
250   TColStd_SequenceOfReal TolSeq;
251   TColStd_SequenceOfBoolean IsFwdSeq;
252   GeomAbs_CurveType CurType = GeomAbs_OtherCurve;
253   TopoDS_Vertex FirstVertex, LastVertex;
254
255   BRepTools_WireExplorer wexp(theWire);
256
257   for (; wexp.More(); wexp.Next()) {
258     TopoDS_Edge anEdge = wexp.Current();
259     Standard_Real fpar, lpar;
260     Handle(Geom_Curve) aCurve = BRep_Tool::Curve(anEdge, fpar, lpar);
261
262     if (aCurve.IsNull())
263       continue;
264
265     GeomAdaptor_Curve  aGACurve(aCurve);
266     GeomAbs_CurveType  aType       = aGACurve.GetType();
267     Handle(Geom_Curve) aBasisCurve = aGACurve.Curve();
268     Standard_Boolean   isFwd       = (wexp.Orientation() != TopAbs_REVERSED);
269
270     if (aBasisCurve->IsPeriodic()) {
271       ElCLib::AdjustPeriodic
272         (aBasisCurve->FirstParameter(), aBasisCurve->LastParameter(),
273         Precision::PConfusion(), fpar, lpar);
274
275
276
277     }
278
279     if (CurveSeq.IsEmpty()) {
280       CurveSeq.Append(aCurve);
281       FparSeq.Append(fpar);
282       LparSeq.Append(lpar);
283       IsFwdSeq.Append(isFwd);
284       CurType     = aType;
285       FirstVertex = wexp.CurrentVertex();
286     } else {
287       Standard_Boolean isSameCurve = Standard_False;
288       Standard_Real NewFpar = RealFirst(), NewLpar = RealLast();
289       GeomAdaptor_Curve GAprevcurve(CurveSeq.Last());
290
291       if (aCurve == CurveSeq.Last()) {
292         NewFpar = fpar;
293         NewLpar = lpar;
294         isSameCurve = Standard_True;
295       } else if (aType == CurType &&
296                  aType != GeomAbs_BezierCurve &&
297                  aType != GeomAbs_BSplineCurve &&
298                  aType != GeomAbs_OtherCurve) {
299         switch (aType) {
300         case GeomAbs_Line:
301         {
302           gp_Lin aLine    = aGACurve.Line();
303           gp_Lin PrevLine = GAprevcurve.Line(); 
304
305           if (aLine.Contains(PrevLine.Location(), LinTol) &&
306               aLine.Direction().IsParallel(PrevLine.Direction(), AngTol)) {
307             gp_Pnt P1 = ElCLib::Value(fpar, aLine);
308             gp_Pnt P2 = ElCLib::Value(lpar, aLine);
309
310             NewFpar = ElCLib::Parameter(PrevLine, P1);
311             NewLpar = ElCLib::Parameter(PrevLine, P2);
312             isSameCurve = Standard_True;
313           }
314           break;
315         }
316         case GeomAbs_Circle:
317         {
318           gp_Circ aCircle    = aGACurve.Circle();
319           gp_Circ PrevCircle = GAprevcurve.Circle();
320
321           if (aCircle.Location().Distance(PrevCircle.Location()) <= LinTol &&
322               Abs(aCircle.Radius() - PrevCircle.Radius()) <= LinTol &&
323               aCircle.Axis().IsParallel(PrevCircle.Axis(), AngTol)) {
324             gp_Pnt P1 = ElCLib::Value(fpar, aCircle);
325             gp_Pnt P2 = ElCLib::Value(lpar, aCircle);
326
327             NewFpar = ElCLib::Parameter(PrevCircle, P1);
328             NewLpar = ElCLib::Parameter(PrevCircle, P2);
329             isSameCurve = Standard_True;
330           }
331           break;
332         }
333         case GeomAbs_Ellipse:
334         {
335           gp_Elips anEllipse   = aGACurve.Ellipse();
336           gp_Elips PrevEllipse = GAprevcurve.Ellipse();
337
338           if (anEllipse.Focus1().Distance(PrevEllipse.Focus1()) <= LinTol &&
339               anEllipse.Focus2().Distance(PrevEllipse.Focus2()) <= LinTol &&
340               Abs(anEllipse.MajorRadius() - PrevEllipse.MajorRadius()) <= LinTol &&
341               Abs(anEllipse.MinorRadius() - PrevEllipse.MinorRadius()) <= LinTol &&
342               anEllipse.Axis().IsParallel(PrevEllipse.Axis(), AngTol)) {
343             gp_Pnt P1 = ElCLib::Value(fpar, anEllipse);
344             gp_Pnt P2 = ElCLib::Value(lpar, anEllipse);
345
346             NewFpar = ElCLib::Parameter(PrevEllipse, P1);
347             NewLpar = ElCLib::Parameter(PrevEllipse, P2);
348             isSameCurve = Standard_True;
349           }
350           break;
351         }
352         case GeomAbs_Hyperbola:
353         {
354           gp_Hypr aHypr    = aGACurve.Hyperbola();
355           gp_Hypr PrevHypr = GAprevcurve.Hyperbola();
356
357           if (aHypr.Focus1().Distance(PrevHypr.Focus1()) <= LinTol &&
358               aHypr.Focus2().Distance(PrevHypr.Focus2()) <= LinTol &&
359               Abs(aHypr.MajorRadius() - PrevHypr.MajorRadius()) <= LinTol &&
360               Abs(aHypr.MinorRadius() - PrevHypr.MinorRadius()) <= LinTol &&
361               aHypr.Axis().IsParallel(PrevHypr.Axis(), AngTol)) {
362             gp_Pnt P1 = ElCLib::Value(fpar, aHypr);
363             gp_Pnt P2 = ElCLib::Value(lpar, aHypr);
364
365             NewFpar = ElCLib::Parameter(PrevHypr, P1);
366             NewLpar = ElCLib::Parameter(PrevHypr, P2);
367             isSameCurve = Standard_True;
368           }
369           break;
370         }
371         case GeomAbs_Parabola:
372         {
373           gp_Parab aParab    = aGACurve.Parabola();
374           gp_Parab PrevParab = GAprevcurve.Parabola();
375
376           if (aParab.Location().Distance(PrevParab.Location()) <= LinTol &&
377               aParab.Focus().Distance(PrevParab.Focus()) <= LinTol &&
378               Abs(aParab.Focal() - PrevParab.Focal()) <= LinTol &&
379               aParab.Axis().IsParallel(PrevParab.Axis(), AngTol)) {
380             gp_Pnt P1 = ElCLib::Value(fpar, aParab);
381             gp_Pnt P2 = ElCLib::Value(lpar, aParab);
382
383             NewFpar = ElCLib::Parameter(PrevParab, P1);
384             NewLpar = ElCLib::Parameter(PrevParab, P2);
385             isSameCurve = Standard_True;
386           }
387           break;
388         }
389         default:
390           break;
391         } //end of switch
392       } //end of else
393
394       if (isSameCurve) {
395         const Standard_Boolean isSameDir = (isFwd == IsFwdSeq.Last());
396
397         if (aBasisCurve->IsPeriodic()) {
398           // Treat periodic curves.
399           const Standard_Real aPeriod = aBasisCurve->Period();
400
401           if (isSameDir) {
402             // Check if first parameter is greater then the last one.
403             while (NewFpar > NewLpar) {
404               NewFpar -= aPeriod;
405             }
406           } else { // !isSameDir
407             // Check if last parameter is greater then the first one.
408             while (NewLpar > NewFpar) {
409               NewLpar -= aPeriod;
410             }
411
412             // Change parameters
413             const Standard_Real aTmpPar = NewLpar;
414
415             NewLpar = NewFpar;
416             NewFpar = aTmpPar;
417           }
418
419           // Udjust parameters on periodic curves.
420           if (IsFwdSeq.Last()) {
421             // The current curve should be after the previous one.
422             ElCLib::AdjustPeriodic(LparSeq.Last(), LparSeq.Last() + aPeriod,
423               Precision::PConfusion(), NewFpar, NewLpar);
424           } else {
425             // The current curve should be before the previous one.
426             ElCLib::AdjustPeriodic(FparSeq.Last() - aPeriod, FparSeq.Last(),
427               Precision::PConfusion(), NewFpar, NewLpar);
428           }
429         } else if (!isSameDir) {
430           // Not periodic curves. Opposite dirs.
431           const Standard_Real aTmpPar = NewLpar;
432
433           NewLpar = NewFpar;
434           NewFpar = aTmpPar;
435         }
436
437         if (IsFwdSeq.Last()) {
438           // Update last parameter 
439           LparSeq(LparSeq.Length()) = NewLpar;
440         } else {
441           // Update first parameter 
442           FparSeq(FparSeq.Length()) = NewFpar;
443         }
444       } else {
445         // Add new curve.
446         CurveSeq.Append(aCurve);
447         FparSeq.Append(fpar);
448         LparSeq.Append(lpar);
449         IsFwdSeq.Append(isFwd);
450         TolSeq.Append(BRep_Tool::Tolerance(wexp.CurrentVertex()));
451         CurType = aType;
452       }
453     }
454   }
455
456   LastVertex = wexp.CurrentVertex();
457   TolSeq.Append(BRep_Tool::Tolerance(LastVertex));
458
459   Standard_Boolean isReverse = Standard_False;
460
461   if (!IsFwdSeq.IsEmpty()) {
462     isReverse = !IsFwdSeq(1);
463   }
464
465   TopoDS_Vertex FirstVtx_final = (isReverse)? LastVertex : FirstVertex;
466   FirstVtx_final.Orientation(TopAbs_FORWARD);
467   TopoDS_Vertex LastVtx_final = (isReverse)? FirstVertex : LastVertex;
468   LastVtx_final.Orientation(TopAbs_REVERSED);
469   
470   if (CurveSeq.IsEmpty())
471     return ResEdge;
472
473   Standard_Integer nb_curve = CurveSeq.Length();   //number of curves
474   TColGeom_Array1OfBSplineCurve tab(0,nb_curve-1);                    //array of the curves
475   TColStd_Array1OfReal tabtolvertex(0,nb_curve-1); //(0,nb_curve-2);  //array of the tolerances
476
477   Standard_Integer i;
478
479   if (nb_curve > 1)
480     {
481       for (i = 1; i <= nb_curve; i++)
482         {
483           if (CurveSeq(i)->IsInstance(STANDARD_TYPE(Geom_TrimmedCurve)))
484             CurveSeq(i) = (*((Handle(Geom_TrimmedCurve)*)&(CurveSeq(i))))->BasisCurve();
485           
486           Handle(Geom_TrimmedCurve) aTrCurve = new Geom_TrimmedCurve(CurveSeq(i), FparSeq(i), LparSeq(i));
487           tab(i-1) = GeomConvert::CurveToBSplineCurve(aTrCurve);
488           GeomConvert::C0BSplineToC1BSplineCurve(tab(i-1), Precision::Confusion());
489
490           if (!IsFwdSeq(i)) {
491             tab(i-1)->Reverse();
492           }
493           
494           //Temporary
495           //char* name = new char[100];
496           //sprintf(name, "c%d", i);
497           //DrawTrSurf::Set(name, tab(i-1));
498           
499           if (i > 1)
500             tabtolvertex(i-2) = TolSeq(i-1) * 5.;
501         }
502       tabtolvertex(nb_curve-1) = TolSeq(TolSeq.Length()) * 5.;
503       
504       Standard_Boolean closed_flag = Standard_False;
505       Standard_Real closed_tolerance = 0.;
506       if (FirstVertex.IsSame(LastVertex) &&
507           GeomLProp::Continuity(tab(0), tab(nb_curve-1),
508                                 tab(0)->FirstParameter(),
509                                 tab(nb_curve-1)->LastParameter(),
510                                 Standard_False, Standard_False, LinTol, AngTol) >= GeomAbs_G1)
511         {
512           closed_flag = Standard_True ;
513           closed_tolerance = BRep_Tool::Tolerance(FirstVertex);
514         }
515       
516       Handle(TColGeom_HArray1OfBSplineCurve)  concatcurve;     //array of the concatenated curves
517       Handle(TColStd_HArray1OfInteger)        ArrayOfIndices;  //array of the remining Vertex
518       GeomConvert::ConcatC1(tab,
519                             tabtolvertex,
520                             ArrayOfIndices,
521                             concatcurve,
522                             closed_flag,
523                             closed_tolerance);   //C1 concatenation
524
525       if (concatcurve->Length() > 1)
526         {
527           Standard_Real MaxTolVer = LinTol;
528           for (i = 1; i <= TolSeq.Length(); i++)
529             if (TolSeq(i) > MaxTolVer)
530               MaxTolVer = TolSeq(i);
531           MaxTolVer *= 5.;
532           
533           GeomConvert_CompCurveToBSplineCurve Concat(concatcurve->Value(concatcurve->Lower()));
534           
535           for (i = concatcurve->Lower()+1; i <= concatcurve->Upper(); i++)
536             Concat.Add( concatcurve->Value(i), MaxTolVer, Standard_True );
537           
538           concatcurve->SetValue(concatcurve->Lower(), Concat.BSplineCurve());
539         }
540
541       ResEdge = BRepLib_MakeEdge(concatcurve->Value(concatcurve->Lower()),
542                                  FirstVtx_final, LastVtx_final,
543                                  concatcurve->Value(concatcurve->Lower())->FirstParameter(),
544                                  concatcurve->Value(concatcurve->Lower())->LastParameter());
545     }
546   else
547     {
548       if (CurveSeq(1)->IsInstance(STANDARD_TYPE(Geom_TrimmedCurve)))
549         CurveSeq(1) = (*((Handle(Geom_TrimmedCurve)*)&(CurveSeq(1))))->BasisCurve();
550
551       Handle(Geom_Curve) aCopyCurve =
552           Handle(Geom_Curve)::DownCast(CurveSeq(1)->Copy());
553
554       ResEdge = BRepLib_MakeEdge(aCopyCurve,
555                                  FirstVtx_final, LastVtx_final,
556                                  FparSeq(1), LparSeq(1));
557     }
558
559   if (isReverse)
560     ResEdge.Reverse();
561   
562   return ResEdge;
563 }