6a3d8d52d6294f015849545ef489fc50e25da57a
[occt.git] / src / BRepLib / BRepLib_MakeEdge.cxx
1 // Created on: 1993-07-23
2 // Created by: Joelle CHAUVET
3 // Copyright (c) 1993-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 // Modified:    Wed Oct 23 09:17:47 1996
18 //              check ponctuallity (PRO4896)
19
20 #include <Adaptor3d_CurveOnSurface.hxx>
21 #include <BRep_Builder.hxx>
22 #include <BRep_Tool.hxx>
23 #include <BRepLib.hxx>
24 #include <BRepLib_MakeEdge.hxx>
25 #include <ElCLib.hxx>
26 #include <Extrema_ExtPC.hxx>
27 #include <Geom2d_Curve.hxx>
28 #include <Geom2d_TrimmedCurve.hxx>
29 #include <Geom2dAdaptor_HCurve.hxx>
30 #include <Geom_Circle.hxx>
31 #include <Geom_Curve.hxx>
32 #include <Geom_Ellipse.hxx>
33 #include <Geom_Hyperbola.hxx>
34 #include <Geom_Line.hxx>
35 #include <Geom_Parabola.hxx>
36 #include <Geom_Surface.hxx>
37 #include <Geom_TrimmedCurve.hxx>
38 #include <GeomAdaptor_Curve.hxx>
39 #include <GeomAdaptor_HSurface.hxx>
40 #include <gp.hxx>
41 #include <gp_Circ.hxx>
42 #include <gp_Elips.hxx>
43 #include <gp_Hypr.hxx>
44 #include <gp_Lin.hxx>
45 #include <gp_Parab.hxx>
46 #include <gp_Pnt.hxx>
47 #include <Precision.hxx>
48 #include <StdFail_NotDone.hxx>
49 #include <TopoDS.hxx>
50 #include <TopoDS_Edge.hxx>
51 #include <TopoDS_Vertex.hxx>
52
53 //=======================================================================
54 //function : Project
55 //purpose  : project a vertex on a curve
56 //=======================================================================
57 static Standard_Boolean Project(const Handle(Geom_Curve)& C,
58                                 const TopoDS_Vertex& V,
59                                 Standard_Real& p)
60 {
61   Standard_Real Eps2 = BRep_Tool::Tolerance(V);
62   Eps2 *= Eps2;
63   
64   gp_Pnt P = BRep_Tool::Pnt(V);
65   GeomAdaptor_Curve GAC(C);
66   
67   // Afin de faire les extremas, on verifie les distances en bout
68   Standard_Real D1,D2;
69   gp_Pnt P1,P2;
70   P1 = GAC.Value(GAC.FirstParameter());
71   P2 = GAC.Value(GAC.LastParameter());
72   D1 = P1.SquareDistance(P);
73   D2 = P2.SquareDistance(P);
74   if ( (D1 < D2) && (D1 <= Eps2) ) {
75     p = GAC.FirstParameter();
76     return Standard_True;
77   }
78   else if ( (D2 < D1) && (D2 <= Eps2) ) {
79     p = GAC.LastParameter();
80     return Standard_True;
81   }
82
83   // Sinon, on calcule les extremas.
84
85   Extrema_ExtPC extrema(P,GAC);
86   if (extrema.IsDone()) {
87     Standard_Integer i, index = 0, n = extrema.NbExt();
88     Standard_Real Dist2 = RealLast(), dist2min;
89
90     for (i = 1; i <= n; i++) {
91       dist2min = extrema.SquareDistance(i);
92       if (dist2min < Dist2) {
93         index = i;
94         Dist2 = dist2min;
95       }
96     }
97
98     if (index != 0) {
99       if (Dist2 <= Eps2) {
100         p = (extrema.Point(index)).Parameter();
101         return Standard_True;
102       }
103     }
104   }
105   return Standard_False;
106 }
107
108
109 //=======================================================================
110 //function : Project
111 //purpose  : project a vertex on a curve on surface
112 //=======================================================================
113
114 static Standard_Boolean Project(const Handle(Geom2d_Curve)& C,
115                                 const Handle(Geom_Surface)& S,
116                                 const TopoDS_Vertex& V,
117                                 Standard_Real& p)
118 {
119   gp_Pnt P = BRep_Tool::Pnt(V);
120   Standard_Real Eps2 = BRep_Tool::Tolerance(V);
121   Eps2 *= Eps2;
122   
123   Handle(Geom2dAdaptor_HCurve) HG2AHC = new Geom2dAdaptor_HCurve();
124   HG2AHC->Set(C);
125   Handle(GeomAdaptor_HSurface) HGAHS = new GeomAdaptor_HSurface();
126   HGAHS->Set(S);
127   Adaptor3d_CurveOnSurface ACOS(HG2AHC,HGAHS);
128
129   Standard_Real D1,D2;
130   gp_Pnt P1,P2;
131   P1 = ACOS.Value(ACOS.FirstParameter());
132   P2 = ACOS.Value(ACOS.LastParameter());
133   D1 = P1.SquareDistance(P);
134   D2 = P2.SquareDistance(P);
135   if ( (D1 < D2) && (D1 <= Eps2) ) {
136     p = ACOS.FirstParameter();
137     return Standard_True;
138   }
139   else if ( (D2 < D1) && (D2 <= Eps2) ) {
140     p = ACOS.LastParameter();
141     return Standard_True;
142   }
143   
144   
145   Extrema_ExtPC extrema(P,ACOS);
146   
147   if (extrema.IsDone()) {
148     Standard_Integer i, index = 0, n = extrema.NbExt();
149     Standard_Real Dist2 = RealLast(), dist2min;
150     
151     for (i = 1; i <= n; i++) {
152       dist2min = extrema.SquareDistance(i);
153       if (dist2min < Dist2) {
154         index = i;
155         Dist2 = dist2min;
156       }
157     }
158     
159     if (index != 0) {
160       Extrema_POnCurv POC = extrema.Point(index);
161       if (P.SquareDistance(POC.Value()) <= Precision::SquareConfusion()) {
162         p = POC.Parameter();
163         return Standard_True;
164       }
165     }
166   }
167   return Standard_False;
168 }
169
170 //=======================================================================
171 //function : BRepLib_MakeEdge
172 //purpose  : 
173 //=======================================================================
174
175 BRepLib_MakeEdge::BRepLib_MakeEdge()
176 {}
177
178 //=======================================================================
179 //function : BRepLib_MakeEdge
180 //purpose  : 
181 //=======================================================================
182
183 BRepLib_MakeEdge::BRepLib_MakeEdge(const TopoDS_Vertex& V1, 
184                                    const TopoDS_Vertex& V2)
185 {
186   gp_Pnt P1 = BRep_Tool::Pnt(V1);
187   gp_Pnt P2 = BRep_Tool::Pnt(V2);
188   Standard_Real l = P1.Distance(P2);
189   if (l <= gp::Resolution()) {
190     myError = BRepLib_LineThroughIdenticPoints;
191     return;
192   }
193   gp_Lin L(P1,gp_Vec(P1,P2));
194   Handle(Geom_Line) GL = new Geom_Line(L);
195   Init(GL,V1,V2,0,l);
196 }
197
198
199 //=======================================================================
200 //function : BRepLib_MakeEdge
201 //purpose  : 
202 //=======================================================================
203
204 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Pnt& P1, 
205                                    const gp_Pnt& P2)
206 {
207   Standard_Real l = P1.Distance(P2);
208   if (l <= gp::Resolution()) {
209     myError = BRepLib_LineThroughIdenticPoints;
210     return;
211   }
212   gp_Lin L(P1,gp_Vec(P1,P2));
213   Handle(Geom_Line) GL = new Geom_Line(L);
214   Init(GL,P1,P2,0,l);
215 }
216
217
218 //=======================================================================
219 //function : BRepLib_MakeEdge
220 //purpose  : 
221 //=======================================================================
222
223 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Lin& L)
224 {
225   Handle(Geom_Line) GL = new Geom_Line(L);
226   Init(GL);
227 }
228
229
230 //=======================================================================
231 //function : BRepLib_MakeEdge
232 //purpose  : 
233 //=======================================================================
234
235 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Lin& L, 
236                                    const Standard_Real p1, 
237                                    const Standard_Real p2)
238 {
239   Handle(Geom_Line) GL = new Geom_Line(L);
240   Init(GL,p1,p2);
241 }
242
243
244 //=======================================================================
245 //function : BRepLib_MakeEdge
246 //purpose  : 
247 //=======================================================================
248
249 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Lin& L, 
250                                    const gp_Pnt& P1, 
251                                    const gp_Pnt& P2)
252 {
253   Handle(Geom_Line) GL = new Geom_Line(L);
254   Init(GL,P1,P2);
255 }
256
257
258 //=======================================================================
259 //function : BRepLib_MakeEdge
260 //purpose  : 
261 //=======================================================================
262
263 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Lin& L, 
264                                    const TopoDS_Vertex& V1, 
265                                    const TopoDS_Vertex& V2)
266 {
267   Handle(Geom_Line) GL = new Geom_Line(L);
268   Init(GL,V1,V2);
269 }
270
271
272 //=======================================================================
273 //function : BRepLib_MakeEdge
274 //purpose  : 
275 //=======================================================================
276
277 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Circ& C) 
278 {
279   Handle(Geom_Circle) GC = new Geom_Circle(C);
280   Init(GC);
281 }
282
283
284 //=======================================================================
285 //function : BRepLib_MakeEdge
286 //purpose  : 
287 //=======================================================================
288
289 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Circ& C,
290                                    const Standard_Real p1,
291                                    const Standard_Real p2)
292 {
293   Handle(Geom_Circle) GC = new Geom_Circle(C);
294   Init(GC,p1,p2);
295 }
296
297
298 //=======================================================================
299 //function : BRepLib_MakeEdge
300 //purpose  : 
301 //=======================================================================
302
303 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Circ& C,
304                                    const gp_Pnt& P1,
305                                    const gp_Pnt& P2)
306 {
307   Handle(Geom_Circle) GC = new Geom_Circle(C);
308   Init(GC,P1,P2);
309 }
310
311
312 //=======================================================================
313 //function : BRepLib_MakeEdge
314 //purpose  : 
315 //=======================================================================
316
317 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Circ& C,
318                                    const TopoDS_Vertex& V1,
319                                    const TopoDS_Vertex& V2)
320 {
321   Handle(Geom_Circle) GC = new Geom_Circle(C);
322   Init(GC,V1,V2);
323 }
324
325
326 //=======================================================================
327 //function : BRepLib_MakeEdge
328 //purpose  : 
329 //=======================================================================
330
331 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Elips& E) 
332 {
333   Handle(Geom_Ellipse) GE = new Geom_Ellipse(E);
334   Init(GE);
335 }
336
337
338 //=======================================================================
339 //function : BRepLib_MakeEdge
340 //purpose  : 
341 //=======================================================================
342
343 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Elips& E,
344                                    const Standard_Real p1,
345                                    const Standard_Real p2)
346 {
347   Handle(Geom_Ellipse) GE = new Geom_Ellipse(E);
348   Init(GE,p1,p2);
349 }
350
351
352 //=======================================================================
353 //function : BRepLib_MakeEdge
354 //purpose  : 
355 //=======================================================================
356
357 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Elips& E,
358                                    const gp_Pnt& P1,
359                                    const gp_Pnt& P2)
360 {
361   Handle(Geom_Ellipse) GE = new Geom_Ellipse(E);
362   Init(GE,P1,P2);
363 }
364
365
366 //=======================================================================
367 //function : BRepLib_MakeEdge
368 //purpose  : 
369 //=======================================================================
370
371 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Elips& E,
372                                    const TopoDS_Vertex& V1,
373                                    const TopoDS_Vertex& V2)
374 {
375   Handle(Geom_Ellipse) GE = new Geom_Ellipse(E);
376   Init(GE,V1,V2);
377 }
378
379
380 //=======================================================================
381 //function : BRepLib_MakeEdge
382 //purpose  : 
383 //=======================================================================
384
385 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Hypr& H)
386 {
387   Handle(Geom_Hyperbola) GH = new Geom_Hyperbola(H);
388   Init(GH);
389 }
390
391
392 //=======================================================================
393 //function : BRepLib_MakeEdge
394 //purpose  : 
395 //=======================================================================
396
397 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Hypr& H,
398                                    const Standard_Real p1,
399                                    const Standard_Real p2)
400 {
401   Handle(Geom_Hyperbola) GH = new Geom_Hyperbola(H);
402   Init(GH,p1,p2);
403 }
404
405
406 //=======================================================================
407 //function : BRepLib_MakeEdge
408 //purpose  : 
409 //=======================================================================
410
411 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Hypr& H,
412                                    const gp_Pnt& P1,
413                                    const gp_Pnt& P2)
414 {
415   Handle(Geom_Hyperbola) GH = new Geom_Hyperbola(H);
416   Init(GH,P1,P2);
417 }
418
419
420 //=======================================================================
421 //function : BRepLib_MakeEdge
422 //purpose  : 
423 //=======================================================================
424
425 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Hypr& H,
426                                    const TopoDS_Vertex& V1,
427                                    const TopoDS_Vertex& V2)
428 {
429   Handle(Geom_Hyperbola) GH = new Geom_Hyperbola(H);
430   Init(GH,V1,V2);
431 }
432
433
434 //=======================================================================
435 //function : BRepLib_MakeEdge
436 //purpose  : 
437 //=======================================================================
438
439 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Parab& P)
440 {
441   Handle(Geom_Parabola) GP = new Geom_Parabola(P);
442   Init(GP);
443 }
444
445
446 //=======================================================================
447 //function : BRepLib_MakeEdge
448 //purpose  : 
449 //=======================================================================
450
451 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Parab& P,
452                                    const Standard_Real p1,
453                                    const Standard_Real p2)
454 {
455   Handle(Geom_Parabola) GP = new Geom_Parabola(P);
456   Init(GP,p1,p2);
457 }
458
459
460 //=======================================================================
461 //function : BRepLib_MakeEdge
462 //purpose  : 
463 //=======================================================================
464
465 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Parab& P,
466                                    const gp_Pnt& P1,
467                                    const gp_Pnt& P2)
468 {
469   Handle(Geom_Parabola) GP = new Geom_Parabola(P);
470   Init(GP,P1,P2);
471 }
472
473
474 //=======================================================================
475 //function : BRepLib_MakeEdge
476 //purpose  : 
477 //=======================================================================
478
479 BRepLib_MakeEdge::BRepLib_MakeEdge(const gp_Parab& P,
480                                    const TopoDS_Vertex& V1,
481                                    const TopoDS_Vertex& V2)
482 {
483   Handle(Geom_Parabola) GP = new Geom_Parabola(P);
484   Init(GP,V1,V2);
485 }
486
487
488 //=======================================================================
489 //function : BRepLib_MakeEdge
490 //purpose  : 
491 //=======================================================================
492
493 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L)
494 {
495   Init(L);
496 }
497
498
499 //=======================================================================
500 //function : BRepLib_MakeEdge
501 //purpose  : 
502 //=======================================================================
503
504 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L,
505                                    const Standard_Real p1,
506                                    const Standard_Real p2)
507 {
508   Init(L,p1,p2);
509 }
510
511
512 //=======================================================================
513 //function : BRepLib_MakeEdge
514 //purpose  : 
515 //=======================================================================
516
517 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L,
518                                    const gp_Pnt& P1,
519                                    const gp_Pnt& P2)
520 {
521   Init(L,P1,P2);
522 }
523
524 //=======================================================================
525 //function : BRepLib_MakeEdge
526 //purpose  : 
527 //=======================================================================
528
529 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L,
530                                    const TopoDS_Vertex& V1,
531                                    const TopoDS_Vertex& V2)
532 {
533   Init(L,V1,V2);
534 }
535
536
537 //=======================================================================
538 //function : BRepLib_MakeEdge
539 //purpose  : 
540 //=======================================================================
541
542 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L,
543                                    const gp_Pnt& P1,
544                                    const gp_Pnt& P2,
545                                    const Standard_Real p1,
546                                    const Standard_Real p2)
547 {
548   Init(L,P1,P2,p1,p2);
549 }
550
551
552 //=======================================================================
553 //function : BRepLib_MakeEdge
554 //purpose  : 
555 //=======================================================================
556
557 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom_Curve)& L,
558                                    const TopoDS_Vertex& V1,
559                                    const TopoDS_Vertex& V2,
560                                    const Standard_Real p1,
561                                    const Standard_Real p2)
562 {
563   Init(L,V1,V2,p1,p2);
564 }
565
566
567
568 //=======================================================================
569 //function : BRepLib_MakeEdge
570 //purpose  : 
571 //=======================================================================
572
573 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
574                                    const Handle(Geom_Surface)& S)
575 {
576   Init(L,S);
577 }
578
579
580 //=======================================================================
581 //function : BRepLib_MakeEdge
582 //purpose  : 
583 //=======================================================================
584
585 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
586                                    const Handle(Geom_Surface)& S,
587                                    const Standard_Real p1,
588                                    const Standard_Real p2)
589 {
590   Init(L,S,p1,p2);
591 }
592
593
594 //=======================================================================
595 //function : BRepLib_MakeEdge
596 //purpose  : 
597 //=======================================================================
598
599 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
600                                    const Handle(Geom_Surface)& S,
601                                    const gp_Pnt& P1,
602                                    const gp_Pnt& P2)
603 {
604   Init(L,S,P1,P2);
605 }
606
607 //=======================================================================
608 //function : BRepLib_MakeEdge
609 //purpose  : 
610 //=======================================================================
611
612 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
613                                    const Handle(Geom_Surface)& S,
614                                    const TopoDS_Vertex& V1,
615                                    const TopoDS_Vertex& V2)
616 {
617   Init(L,S,V1,V2);
618 }
619
620
621 //=======================================================================
622 //function : BRepLib_MakeEdge
623 //purpose  : 
624 //=======================================================================
625
626 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
627                                    const Handle(Geom_Surface)& S,
628                                    const gp_Pnt& P1,
629                                    const gp_Pnt& P2,
630                                    const Standard_Real p1,
631                                    const Standard_Real p2)
632 {
633   Init(L,S,P1,P2,p1,p2);
634 }
635
636
637 //=======================================================================
638 //function : BRepLib_MakeEdge
639 //purpose  : 
640 //=======================================================================
641
642 BRepLib_MakeEdge::BRepLib_MakeEdge(const Handle(Geom2d_Curve)& L,
643                                    const Handle(Geom_Surface)& S,
644                                    const TopoDS_Vertex& V1,
645                                    const TopoDS_Vertex& V2,
646                                    const Standard_Real p1,
647                                    const Standard_Real p2)
648 {
649   Init(L,S,V1,V2,p1,p2);
650 }
651
652
653 //=======================================================================
654 //function : Init
655 //purpose  : 
656 //=======================================================================
657
658 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& C)
659 {
660   Init(C,C->FirstParameter(),C->LastParameter());
661 }
662
663
664 //=======================================================================
665 //function : Init
666 //purpose  : 
667 //=======================================================================
668
669 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& C,
670                              const Standard_Real p1,
671                              const Standard_Real p2)
672 {
673 //  BRep_Builder B;
674
675   TopoDS_Vertex V1,V2;
676   Init(C,V1,V2,p1,p2);
677 }
678
679
680 //=======================================================================
681 //function : Init
682 //purpose  : 
683 //=======================================================================
684
685 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& C,
686                              const gp_Pnt& P1,
687                              const gp_Pnt& P2)
688 {
689   Standard_Real Tol = BRepLib::Precision();
690
691   BRep_Builder B;
692   TopoDS_Vertex V1,V2;
693   B.MakeVertex(V1,P1,Tol);
694   if (P1.Distance(P2) < Tol)
695     V2 = V1;
696   else
697     B.MakeVertex(V2,P2,Tol);
698   
699   Init(C,V1,V2);
700 }
701
702
703 //=======================================================================
704 //function : Init
705 //purpose  : 
706 //=======================================================================
707
708 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& C,
709                              const TopoDS_Vertex& V1,
710                              const TopoDS_Vertex& V2)
711 {
712   // try projecting the vertices on the curve
713
714   Standard_Real p1,p2;
715   
716   if (V1.IsNull())
717     p1 = C->FirstParameter();
718   else
719     if (!Project(C,V1,p1)) {
720       myError = BRepLib_PointProjectionFailed;
721       return;
722     }
723   if (V2.IsNull())
724     p2 = C->LastParameter();
725   else
726     if (!Project(C,V2,p2))  {
727       myError = BRepLib_PointProjectionFailed;
728       return;
729     }
730   
731   Init(C,V1,V2,p1,p2);
732 }
733
734
735 //=======================================================================
736 //function : Init
737 //purpose  : 
738 //=======================================================================
739
740 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& C,
741                              const gp_Pnt& P1,
742                              const gp_Pnt& P2,
743                              const Standard_Real p1,
744                              const Standard_Real p2)
745 {
746   Standard_Real Tol = BRepLib::Precision();
747   BRep_Builder B;
748
749   TopoDS_Vertex V1,V2;
750   B.MakeVertex(V1,P1,Tol);
751   if (P1.Distance(P2) < Tol)
752     V2 = V1;
753   else
754     B.MakeVertex(V2,P2,Tol);
755   
756   Init(C,V1,V2,p1,p2);
757 }
758
759
760 //=======================================================================
761 //function : Init
762 //purpose  : this one really makes the job ...
763 //=======================================================================
764
765 void  BRepLib_MakeEdge::Init(const Handle(Geom_Curve)& CC,
766                              const TopoDS_Vertex& VV1,
767                              const TopoDS_Vertex& VV2,
768                              const Standard_Real pp1,
769                              const Standard_Real pp2)
770 {
771   // kill trimmed curves
772   Handle(Geom_Curve) C = CC;
773   Handle(Geom_TrimmedCurve) CT = Handle(Geom_TrimmedCurve)::DownCast(C);
774   while (!CT.IsNull()) {
775     C = CT->BasisCurve();
776     CT = Handle(Geom_TrimmedCurve)::DownCast(C);
777   }
778
779   // check parameters
780   Standard_Real p1 = pp1;
781   Standard_Real p2 = pp2;
782   Standard_Real cf = C->FirstParameter();
783   Standard_Real cl = C->LastParameter();
784   Standard_Real epsilon = Precision::PConfusion();
785   Standard_Boolean periodic = C->IsPeriodic();
786   GeomAdaptor_Curve aCA(C);
787
788   TopoDS_Vertex V1,V2;
789   if (periodic) {
790     // adjust in period
791     ElCLib::AdjustPeriodic(cf,cl,epsilon,p1,p2);
792     V1 = VV1;
793     V2 = VV2;
794   }
795   else {
796     // reordonate
797     if (p1 < p2) {
798       V1 = VV1;
799       V2 = VV2;
800     }
801     else {
802       V2 = VV1;
803       V1 = VV2;
804       Standard_Real x = p1;
805       p1 = p2;
806       p2 = x;
807     }
808
809     // check range
810     if ((cf - p1 > epsilon) || (p2 - cl > epsilon)) {
811       myError = BRepLib_ParameterOutOfRange;
812       return;
813     }
814
815     // check ponctuallity
816     if ((p2-p1) <= gp::Resolution()) {
817       myError = BRepLib_LineThroughIdenticPoints;
818       return;
819     }
820   }
821   
822   // compute points on the curve
823   Standard_Boolean p1inf = Precision::IsNegativeInfinite(p1);
824   Standard_Boolean p2inf = Precision::IsPositiveInfinite(p2);
825   gp_Pnt P1,P2;
826   if (!p1inf) P1 = aCA.Value(p1);
827   if (!p2inf) P2 = aCA.Value(p2);
828
829   Standard_Real preci = BRepLib::Precision();
830   BRep_Builder B;
831
832   // check for closed curve
833   Standard_Boolean closed = Standard_False;
834   Standard_Boolean degenerated = Standard_False;
835   if (!p1inf && !p2inf)
836     closed = (P1.Distance(P2) <= preci);
837
838   // check if the vertices are on the curve
839   if (closed) {
840     if (V1.IsNull() && V2.IsNull()) {
841       B.MakeVertex(V1,P1,preci);
842       V2 = V1;
843     }
844     else if (V1.IsNull())
845       V1 = V2;
846     else if (V2.IsNull())
847       V2 = V1;
848     else {
849       if (!V1.IsSame(V2)) {
850         myError = BRepLib_DifferentPointsOnClosedCurve;
851         return;
852       }
853       else if (P1.Distance(BRep_Tool::Pnt(V1)) > 
854         Max(preci,BRep_Tool::Tolerance(V1))) {
855         myError = BRepLib_DifferentPointsOnClosedCurve;
856         return;
857       }
858       else
859       {
860         gp_Pnt PM = aCA.Value((p1+p2)/2);
861         if (P1.Distance(PM) < preci)
862           degenerated = Standard_True;
863       }
864     }
865   }
866
867   else {    // not closed
868
869     if (p1inf) {
870       if (!V1.IsNull()) {
871         myError = BRepLib_PointWithInfiniteParameter;
872         return;
873       }
874     }
875     else {
876       if (V1.IsNull()) {
877         B.MakeVertex(V1,P1,preci);
878       }
879       else if (P1.Distance(BRep_Tool::Pnt(V1)) >
880                Max(preci,BRep_Tool::Tolerance(V1))) {
881         myError = BRepLib_DifferentsPointAndParameter;
882         return;
883       }
884     }
885     
886     if (p2inf) {
887       if (!V2.IsNull()) {
888         myError = BRepLib_PointWithInfiniteParameter;
889         return;
890       }
891     }
892     else {
893       if (V2.IsNull()) {
894         B.MakeVertex(V2,P2,preci);
895       }
896       else if (P2.Distance(BRep_Tool::Pnt(V2)) >
897                Max(preci,BRep_Tool::Tolerance(V2))){
898         myError = BRepLib_DifferentsPointAndParameter;
899         return;
900       }
901     }
902   }
903
904   V1.Orientation(TopAbs_FORWARD);
905   V2.Orientation(TopAbs_REVERSED);
906   myVertex1 = V1;
907   myVertex2 = V2;
908
909   TopoDS_Edge& E = TopoDS::Edge(myShape);
910   B.MakeEdge(E,C,preci);
911   if (!V1.IsNull()) {
912     B.Add(E,V1);
913   }
914   if (!V2.IsNull()) {
915     B.Add(E,V2);
916   }
917   B.Range(E,p1,p2);
918   B.Degenerated(E, degenerated);
919
920   myError = BRepLib_EdgeDone;
921   Done();
922 }
923
924 //=======================================================================
925 //function : Init
926 //purpose  : 
927 //=======================================================================
928
929 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& C,
930                              const Handle(Geom_Surface)& S)
931 {
932   Init(C,S,C->FirstParameter(),C->LastParameter());
933 }
934
935
936 //=======================================================================
937 //function : Init
938 //purpose  : 
939 //=======================================================================
940
941 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& C,
942                              const Handle(Geom_Surface)& S,
943                              const Standard_Real p1,
944                              const Standard_Real p2)
945 {
946 //  BRep_Builder B;
947
948   TopoDS_Vertex V1,V2;
949   Init(C,S,V1,V2,p1,p2);
950 }
951
952
953 //=======================================================================
954 //function : Init
955 //purpose  : 
956 //=======================================================================
957
958 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& C,
959                              const Handle(Geom_Surface)& S,
960                              const gp_Pnt& P1,
961                              const gp_Pnt& P2)
962 {
963   Standard_Real Tol = BRepLib::Precision();
964   
965   BRep_Builder B;
966   TopoDS_Vertex V1,V2;
967   B.MakeVertex(V1,P1,Tol);
968   if (P1.Distance(P2) < Tol)
969     V2 = V1;
970   else
971     B.MakeVertex(V2,P2,Tol);
972   
973   Init(C,S,V1,V2);
974 }
975
976
977 //=======================================================================
978 //function : Init
979 //purpose  : 
980 //=======================================================================
981
982 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& C,
983                              const Handle(Geom_Surface)& S,
984                              const TopoDS_Vertex& V1,
985                              const TopoDS_Vertex& V2)
986 {
987   // try projecting the vertices on the curve
988
989   Standard_Real p1,p2;
990   
991   if (V1.IsNull())
992     p1 = C->FirstParameter();
993   else
994     if (!Project(C,S,V1,p1)) {
995       myError = BRepLib_PointProjectionFailed;
996       return;
997     }
998   if (V2.IsNull())
999     p2 = C->LastParameter();
1000   else
1001     if (!Project(C,S,V2,p2))  {
1002       myError = BRepLib_PointProjectionFailed;
1003       return;
1004     }
1005   
1006   Init(C,S,V1,V2,p1,p2);
1007 }
1008
1009
1010 //=======================================================================
1011 //function : Init
1012 //purpose  : 
1013 //=======================================================================
1014
1015 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& C,
1016                              const Handle(Geom_Surface)& S,
1017                              const gp_Pnt& P1,
1018                              const gp_Pnt& P2,
1019                              const Standard_Real p1,
1020                              const Standard_Real p2)
1021 {
1022   Standard_Real Tol = BRepLib::Precision();
1023   BRep_Builder B;
1024
1025   TopoDS_Vertex V1,V2;
1026   B.MakeVertex(V1,P1,Tol);
1027   if (P1.Distance(P2) < Tol)
1028     V2 = V1;
1029   else
1030     B.MakeVertex( V2, P2, Tol);
1031   
1032   Init(C,S,V1,V2,p1,p2);
1033 }
1034
1035
1036 //=======================================================================
1037 //function : Init
1038 //purpose  : this one really makes the job ...
1039 //=======================================================================
1040
1041 void  BRepLib_MakeEdge::Init(const Handle(Geom2d_Curve)& CC,
1042                              const Handle(Geom_Surface)& S,
1043                              const TopoDS_Vertex& VV1,
1044                              const TopoDS_Vertex& VV2,
1045                              const Standard_Real pp1,
1046                              const Standard_Real pp2)
1047 {
1048   // kill trimmed curves
1049   Handle(Geom2d_Curve) C = CC;
1050   Handle(Geom2d_TrimmedCurve) CT = Handle(Geom2d_TrimmedCurve)::DownCast(C);
1051   while (!CT.IsNull()) {
1052     C = CT->BasisCurve();
1053     CT = Handle(Geom2d_TrimmedCurve)::DownCast(C);
1054   }
1055
1056   // check parameters
1057   Standard_Real p1 = pp1;
1058   Standard_Real p2 = pp2;
1059   Standard_Real cf = C->FirstParameter();
1060   Standard_Real cl = C->LastParameter();
1061   Standard_Real epsilon = Precision::PConfusion();
1062   Standard_Boolean periodic = C->IsPeriodic();
1063
1064
1065   TopoDS_Vertex V1,V2;
1066   Standard_Boolean reverse = Standard_False;
1067
1068   if (periodic) {
1069     // adjust in period
1070     ElCLib::AdjustPeriodic(cf,cl,epsilon,p1,p2);
1071     V1 = VV1;
1072     V2 = VV2;
1073   }
1074   else {
1075     // reordonate
1076     if (p1 < p2) {
1077       V1 = VV1;
1078       V2 = VV2;
1079     }
1080     else {
1081       V2 = VV1;
1082       V1 = VV2;
1083       Standard_Real x = p1;
1084       p1 = p2;
1085       p2 = x;
1086       reverse = Standard_True;
1087     }
1088
1089     // check range
1090     if ((cf - p1 > epsilon) || (p2 - cl > epsilon)) {
1091       myError = BRepLib_ParameterOutOfRange;
1092       return;
1093     }
1094   }
1095   
1096   // compute points on the curve
1097   Standard_Boolean p1inf = Precision::IsNegativeInfinite(p1);
1098   Standard_Boolean p2inf = Precision::IsPositiveInfinite(p2);
1099   gp_Pnt P1,P2;
1100   gp_Pnt2d P2d1,P2d2;
1101   if (!p1inf) {
1102     P2d1 = C->Value(p1);
1103     P1   = S->Value(P2d1.X(),P2d1.Y());
1104   }
1105   if (!p2inf) {
1106     P2d2 = C->Value(p2);
1107     P2   = S->Value(P2d2.X(),P2d2.Y());
1108   }
1109
1110   Standard_Real preci = BRepLib::Precision();
1111   BRep_Builder B;
1112
1113   // check for closed curve
1114   Standard_Boolean closed = Standard_False;
1115   if (!p1inf && !p2inf)
1116     closed = (P1.Distance(P2) <= preci);
1117
1118   // check if the vertices are on the curve
1119   if (closed) {
1120     if (V1.IsNull() && V2.IsNull()) {
1121       B.MakeVertex(V1,P1,preci);
1122       V2 = V1;
1123     }
1124     else if (V1.IsNull())
1125       V1 = V2;
1126     else if (V2.IsNull())
1127       V2 = V1;
1128     else {
1129       if (!V1.IsSame(V2)) {
1130         myError = BRepLib_DifferentPointsOnClosedCurve;
1131         return;
1132       }
1133       else if (P1.Distance(BRep_Tool::Pnt(V1)) > 
1134                Max(preci,BRep_Tool::Tolerance(V1))) {
1135         myError = BRepLib_DifferentPointsOnClosedCurve;
1136         return;
1137       }
1138     }
1139   }
1140
1141   else {    // not closed
1142
1143     if (p1inf) {
1144       if (!V1.IsNull()) {
1145         myError = BRepLib_PointWithInfiniteParameter;
1146         return;
1147       }
1148     }
1149     else {
1150       if (V1.IsNull()) {
1151         B.MakeVertex(V1,P1,preci);
1152       }
1153       else if (P1.Distance(BRep_Tool::Pnt(V1)) >
1154                Max(preci,BRep_Tool::Tolerance(V1))) {
1155         myError = BRepLib_DifferentsPointAndParameter;
1156         return;
1157       }
1158     }
1159     
1160     if (p2inf) {
1161       if (!V2.IsNull()) {
1162         myError = BRepLib_PointWithInfiniteParameter;
1163         return;
1164       }
1165     }
1166     else {
1167       if (V2.IsNull()) {
1168         B.MakeVertex(V2,P2,preci);
1169       }
1170       else if (P2.Distance(BRep_Tool::Pnt(V2)) >
1171                Max(preci,BRep_Tool::Tolerance(V2))){
1172         myError = BRepLib_DifferentsPointAndParameter;
1173         return;
1174       }
1175     }
1176   }
1177
1178   V1.Orientation(TopAbs_FORWARD);
1179   V2.Orientation(TopAbs_REVERSED);
1180   myVertex1 = V1;
1181   myVertex2 = V2;
1182
1183   TopoDS_Edge& E = TopoDS::Edge(myShape);
1184   B.MakeEdge(E);
1185   B.UpdateEdge(E,C,S,TopLoc_Location(),preci);
1186
1187   if (!V1.IsNull()) {
1188     B.Add(E,V1);
1189   }
1190   if (!V2.IsNull()) {
1191     B.Add(E,V2);
1192   }
1193   B.Range(E,p1,p2);
1194
1195   if (reverse)
1196     E.Orientation(TopAbs_REVERSED);
1197
1198   myError = BRepLib_EdgeDone;
1199   Done();
1200 }
1201
1202 //=======================================================================
1203 //function : Error
1204 //purpose  : 
1205 //=======================================================================
1206
1207 BRepLib_EdgeError BRepLib_MakeEdge::Error() const
1208 {
1209   return myError;
1210 }
1211
1212 //=======================================================================
1213 //function : Edge
1214 //purpose  : 
1215 //=======================================================================
1216
1217 const TopoDS_Edge&  BRepLib_MakeEdge::Edge()
1218 {
1219   return TopoDS::Edge(Shape());
1220 }
1221
1222
1223 //=======================================================================
1224 //function : Vertex1
1225 //purpose  : 
1226 //=======================================================================
1227
1228 const TopoDS_Vertex&  BRepLib_MakeEdge::Vertex1()const 
1229 {
1230   Check();
1231   return myVertex1;
1232 }
1233
1234
1235 //=======================================================================
1236 //function : Vertex2
1237 //purpose  : 
1238 //=======================================================================
1239
1240 const TopoDS_Vertex&  BRepLib_MakeEdge::Vertex2()const 
1241 {
1242   Check();
1243   return myVertex2;
1244 }
1245
1246
1247
1248 //=======================================================================
1249 //function : operator
1250 //purpose  : 
1251 //=======================================================================
1252
1253 BRepLib_MakeEdge::operator TopoDS_Edge()
1254 {
1255   return Edge();
1256 }