7a8d2e7263de74e8177c18ccb0a5554eb45226f9
[occt.git] / src / IntPatch / IntPatch_Intersection.cxx
1 // Created by: Modelization
2 // Copyright (c) 1999-2014 OPEN CASCADE SAS
3 //
4 // This file is part of Open CASCADE Technology software library.
5 //
6 // This library is free software; you can redistribute it and/or modify it under
7 // the terms of the GNU Lesser General Public License version 2.1 as published
8 // by the Free Software Foundation, with special exception defined in the file
9 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
10 // distribution for complete text of the license and disclaimer of any warranty.
11 //
12 // Alternatively, this file may be used under the terms of Open CASCADE
13 // commercial license or contractual agreement.
14
15 #include <stdio.h>
16 #include <IntPatch_Intersection.hxx>
17
18 #include <Adaptor3d_HSurface.hxx>
19 #include <Adaptor3d_TopolTool.hxx>
20 #include <IntPatch_ALine.hxx>
21 #include <IntPatch_ALineToWLine.hxx>
22 #include <IntPatch_GLine.hxx>
23 #include <IntPatch_ImpImpIntersection.hxx>
24 #include <IntPatch_ImpPrmIntersection.hxx>
25 #include <IntPatch_PrmPrmIntersection.hxx>
26 #include <IntPatch_WLine.hxx>
27 #include <IntPatch_WLineTool.hxx>
28
29 #include <ProjLib_ProjectOnPlane.hxx>
30 #include <Geom_Plane.hxx>
31 #include <GeomAdaptor_HSurface.hxx>
32 #include <GeomAdaptor_HCurve.hxx>
33 #include <ProjLib_ProjectedCurve.hxx>
34 #include <Geom2dInt_GInter.hxx>
35 #include <Geom2dAdaptor_Curve.hxx>
36 #include <ProjLib.hxx>
37
38 //======================================================================
39 // function: SequenceOfLine
40 //======================================================================
41 const IntPatch_SequenceOfLine& IntPatch_Intersection::SequenceOfLine() const { return(slin); }
42
43 //======================================================================
44 // function: IntPatch_Intersection
45 //======================================================================
46 IntPatch_Intersection::IntPatch_Intersection ()
47  : done(Standard_False),
48    //empt, tgte, oppo,
49    myTolArc(0.0), myTolTang(0.0),
50    myUVMaxStep(0.0), myFleche(0.0),
51    myIsStartPnt(Standard_False)
52    //myU1Start, myV1Start, myU2Start, myV2Start
53 {
54 }
55
56 //======================================================================
57 // function: IntPatch_Intersection
58 //======================================================================
59 IntPatch_Intersection::IntPatch_Intersection(const Handle(Adaptor3d_HSurface)&  S1,
60                                              const Handle(Adaptor3d_TopolTool)& D1,
61                                              const Handle(Adaptor3d_HSurface)&  S2,
62                                              const Handle(Adaptor3d_TopolTool)& D2,
63                                              const Standard_Real TolArc,
64                                              const Standard_Real TolTang)
65  : done(Standard_False),
66    //empt, tgte, oppo,
67    myTolArc(TolArc), myTolTang(TolTang),
68    myUVMaxStep(0.0), myFleche(0.0),
69    myIsStartPnt(Standard_False)
70    //myU1Start, myV1Start, myU2Start, myV2Start
71 {
72   if(myTolArc<1e-8) myTolArc=1e-8;
73   if(myTolTang<1e-8) myTolTang=1e-8;
74   if(myTolArc>0.5) myTolArc=0.5;
75   if(myTolTang>0.5) myTolTang=0.5;
76   Perform(S1,D1,S2,D2,TolArc,TolTang);
77 }
78
79 //======================================================================
80 // function: IntPatch_Intersection
81 //======================================================================
82 IntPatch_Intersection::IntPatch_Intersection(const Handle(Adaptor3d_HSurface)&  S1,
83                                              const Handle(Adaptor3d_TopolTool)& D1,
84                                              const Standard_Real TolArc,
85                                              const Standard_Real TolTang)
86  : done(Standard_False),
87    //empt, tgte, oppo,
88    myTolArc(TolArc), myTolTang(TolTang),
89    myUVMaxStep(0.0), myFleche(0.0),
90    myIsStartPnt(Standard_False)
91    //myU1Start, myV1Start, myU2Start, myV2Start
92 {
93   Perform(S1,D1,TolArc,TolTang);
94 }
95
96 //======================================================================
97 // function: SetTolerances
98 //======================================================================
99 void IntPatch_Intersection::SetTolerances(const Standard_Real TolArc,
100                                           const Standard_Real TolTang,
101                                           const Standard_Real UVMaxStep,
102                                           const Standard_Real Fleche)
103
104   myTolArc     = TolArc;
105   myTolTang    = TolTang;
106   myUVMaxStep  = UVMaxStep;
107   myFleche     = Fleche;
108   if(myTolArc<1e-8) myTolArc=1e-8;
109   if(myTolTang<1e-8) myTolTang=1e-8;
110   if(myTolArc>0.5) myTolArc=0.5;
111   if(myTolTang>0.5) myTolTang=0.5;  
112   if(myFleche<1.0e-3) myFleche=1e-3;
113   if(myUVMaxStep<1.0e-3) myUVMaxStep=1e-3;
114   if(myFleche>10) myFleche=10;
115   if(myUVMaxStep>0.5) myUVMaxStep=0.5;
116 }
117
118 //======================================================================
119 // function: Perform
120 //======================================================================
121 void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)&  S1,
122                                     const Handle(Adaptor3d_TopolTool)& D1,
123                                     const Standard_Real TolArc,
124                                     const Standard_Real TolTang)
125 {
126   myTolArc = TolArc;
127   myTolTang = TolTang;
128   if(myFleche == 0.0)  myFleche = 0.01;
129   if(myUVMaxStep==0.0) myUVMaxStep = 0.01;
130
131   done = Standard_True;
132   spnt.Clear();
133   slin.Clear();
134   
135   empt = Standard_True;
136   tgte = Standard_False;
137   oppo = Standard_False;
138
139   switch (S1->GetType())
140   { 
141   case GeomAbs_Plane:
142   case GeomAbs_Cylinder:
143   case GeomAbs_Sphere:
144   case GeomAbs_Cone:
145   case GeomAbs_Torus:
146     break;
147   case GeomAbs_SurfaceOfExtrusion:
148     {
149       gp_Dir aDirection = S1->Direction();
150       gp_Ax3 anAxis(gp::Origin(), aDirection);
151       Handle(Adaptor3d_HCurve) aBasisCurve = S1->BasisCurve();
152       ProjLib_ProjectOnPlane Projector(anAxis);
153       Projector.Load(aBasisCurve, Precision::Confusion());
154       Handle(GeomAdaptor_HCurve) aProjCurve = Projector.GetResult();
155       Handle(Geom_Plane) aPlane = new Geom_Plane(anAxis);
156       Handle(GeomAdaptor_HSurface) aGAHsurf = new GeomAdaptor_HSurface(aPlane);
157       ProjLib_ProjectedCurve aProjectedCurve(aGAHsurf, aProjCurve);
158       Handle(Geom2d_Curve) aPCurve;
159       ProjLib::MakePCurveOfType(aProjectedCurve, aPCurve);
160       Geom2dAdaptor_Curve AC(aPCurve,
161                              aProjectedCurve.FirstParameter(),
162                              aProjectedCurve.LastParameter());
163       Geom2dInt_GInter Intersector(AC,
164                                    Precision::Confusion(),
165                                    Precision::Confusion());
166       if (Intersector.IsDone() && Intersector.IsEmpty())
167         break;
168     }
169     Standard_FALLTHROUGH
170   default:
171     {
172       IntPatch_PrmPrmIntersection interpp;
173       interpp.Perform(S1,D1,TolTang,TolArc,myFleche,myUVMaxStep);
174       if (interpp.IsDone())
175       {
176         done = Standard_True;
177         tgte = Standard_False;
178         empt = interpp.IsEmpty();
179         const Standard_Integer nblm = interpp.NbLines();
180         for (Standard_Integer i=1; i<=nblm; i++) slin.Append(interpp.Line(i));
181       }
182     }
183     break;
184   }
185 }
186
187 /////////////////////////////////////////////////////////////////////////////
188 //  These several support functions provide methods which can help basic   //
189 //  algorithm to intersect infinite surfaces of the following types:       //
190 //                                                                         //
191 //  a.) SurfaceOfExtrusion;                                                //
192 //  b.) SurfaceOfRevolution;                                               //
193 //  c.) OffsetSurface.                                                     //
194 //                                                                         //
195 /////////////////////////////////////////////////////////////////////////////
196 #include <TColgp_Array1OfXYZ.hxx>
197 #include <TColgp_Array1OfPnt.hxx>
198 #include <TColgp_SequenceOfPnt.hxx>
199 #include <Extrema_ExtPS.hxx>
200 #include <Extrema_POnSurf.hxx>
201 #include <Geom2d_Curve.hxx>
202 #include <Geom2dAPI_InterCurveCurve.hxx>
203 #include <GeomAdaptor.hxx>
204 #include <GeomAdaptor_HCurve.hxx>
205 #include <GeomAdaptor_Curve.hxx>
206 #include <GeomAdaptor_Surface.hxx>
207 #include <GeomAdaptor_HSurface.hxx>
208 #include <Geom_Plane.hxx>
209 #include <ProjLib_ProjectOnPlane.hxx>
210 #include <GeomProjLib.hxx>
211 #include <ElCLib.hxx>
212 #include <Geom_TrimmedCurve.hxx>
213 #include <Geom_Surface.hxx>
214 #include <Geom_SurfaceOfLinearExtrusion.hxx>
215 #include <Geom_OffsetSurface.hxx>
216 #include <Geom_SurfaceOfRevolution.hxx>
217 #include <Geom_RectangularTrimmedSurface.hxx>
218
219 //===============================================================
220 //function: FUN_GetMinMaxXYZPnt
221 //===============================================================
222 static void FUN_GetMinMaxXYZPnt( const Handle(Adaptor3d_HSurface)& S,
223                                  gp_Pnt& pMin, gp_Pnt& pMax )
224 {
225   const Standard_Real DU = 0.25 * Abs(S->LastUParameter() - S->FirstUParameter());
226   const Standard_Real DV = 0.25 * Abs(S->LastVParameter() - S->FirstVParameter());
227   Standard_Real tMinXYZ = RealLast();
228   Standard_Real tMaxXYZ = -tMinXYZ;
229   gp_Pnt PUV, ptMax, ptMin;
230   for(Standard_Real U = S->FirstUParameter(); U <= S->LastUParameter(); U += DU)
231   {
232     for(Standard_Real V = S->FirstVParameter(); V <= S->LastVParameter(); V += DV)
233     {
234       S->D0(U,V,PUV);
235       const Standard_Real cXYZ = PUV.XYZ().Modulus();
236       if(cXYZ > tMaxXYZ) { tMaxXYZ = cXYZ; ptMax = PUV; }
237       if(cXYZ < tMinXYZ) { tMinXYZ = cXYZ; ptMin = PUV; }
238     }
239   }
240   pMin = ptMin;
241   pMax = ptMax;
242 }
243 //==========================================================================
244 //function: FUN_TrimInfSurf
245 //==========================================================================
246 static void FUN_TrimInfSurf(const gp_Pnt& Pmin,
247                             const gp_Pnt& Pmax,
248                             const Handle(Adaptor3d_HSurface)& InfSurf,
249                             const Standard_Real& AlternativeTrimPrm,
250                             Handle(Adaptor3d_HSurface)& TrimS)
251 {
252   Standard_Real TP = AlternativeTrimPrm;
253   Extrema_ExtPS ext1(Pmin, InfSurf->Surface(), 1.e-7, 1.e-7);
254   Extrema_ExtPS ext2(Pmax, InfSurf->Surface(), 1.e-7, 1.e-7);
255   if(ext1.IsDone() || ext2.IsDone())
256   {
257     Standard_Real Umax = -1.e+100, Umin = 1.e+100, Vmax = -1.e+100, Vmin = 1.e+100, cU, cV;
258     if(ext1.IsDone())
259     {
260       for(Standard_Integer i = 1; i <= ext1.NbExt(); i++)
261       {
262         const Extrema_POnSurf & pons = ext1.Point(i);
263         pons.Parameter(cU,cV);
264         if(cU > Umax) Umax = cU;
265         if(cU < Umin) Umin = cU;
266         if(cV > Vmax) Vmax = cV;
267         if(cV < Vmin) Vmin = cV;
268       }
269     }
270     if(ext2.IsDone())
271     {
272       for(Standard_Integer i = 1; i <= ext2.NbExt(); i++)
273       {
274         const Extrema_POnSurf & pons = ext2.Point(i);
275         pons.Parameter(cU,cV);
276         if(cU > Umax) Umax = cU;
277         if(cU < Umin) Umin = cU;
278         if(cV > Vmax) Vmax = cV;
279         if(cV < Vmin) Vmin = cV;
280       }
281     }
282     TP = Max(Abs(Umin),Max(Abs(Umax),Max(Abs(Vmin),Abs(Vmax))));
283   }
284   if(TP == 0.) { TrimS = InfSurf; return; }
285   else
286   {
287     const Standard_Boolean Uinf = Precision::IsNegativeInfinite(InfSurf->FirstUParameter()); 
288     const Standard_Boolean Usup = Precision::IsPositiveInfinite(InfSurf->LastUParameter());
289     const Standard_Boolean Vinf = Precision::IsNegativeInfinite(InfSurf->FirstVParameter()); 
290     const Standard_Boolean Vsup = Precision::IsPositiveInfinite(InfSurf->LastVParameter());
291     Handle(Adaptor3d_HSurface) TmpSS;
292     Standard_Integer IsTrimed = 0;
293     const Standard_Real tp = 1000.0 * TP;
294     if(Vinf && Vsup) { TrimS = InfSurf->VTrim(-tp, tp, 1.0e-7); IsTrimed = 1; }
295     if(Vinf && !Vsup){ TrimS = InfSurf->VTrim(-tp, InfSurf->LastVParameter(), 1.0e-7); IsTrimed = 1; }
296     if(!Vinf && Vsup){ TrimS = InfSurf->VTrim(InfSurf->FirstVParameter(), tp, 1.0e-7); IsTrimed = 1; }
297     if(IsTrimed)
298     {
299       TmpSS = TrimS;
300       if(Uinf && Usup)  TrimS = TmpSS->UTrim(-tp, tp, 1.0e-7);
301       if(Uinf && !Usup) TrimS = TmpSS->UTrim(-tp, InfSurf->LastUParameter(), 1.0e-7);
302       if(!Uinf && Usup) TrimS = TmpSS->UTrim(InfSurf->FirstUParameter(), tp, 1.0e-7);
303     }
304     else
305     {
306       if(Uinf && Usup)  TrimS = InfSurf->UTrim(-tp, tp, 1.0e-7);
307       if(Uinf && !Usup) TrimS = InfSurf->UTrim(-tp, InfSurf->LastUParameter(), 1.0e-7);
308       if(!Uinf && Usup) TrimS = InfSurf->UTrim(InfSurf->FirstUParameter(), tp, 1.0e-7);
309     }
310   }
311 }
312 //================================================================================
313 //function: FUN_GetUiso
314 //================================================================================
315 static void FUN_GetUiso(const Handle(Geom_Surface)& GS,
316                         const GeomAbs_SurfaceType&  T,
317                         const Standard_Real&        FirstV,
318                         const Standard_Real&        LastV,
319                         const Standard_Boolean&     IsVC,
320                         const Standard_Boolean&     IsVP,
321                         const Standard_Real&        U,
322                         Handle(Geom_Curve)&         I)
323 {
324   if(T !=  GeomAbs_OffsetSurface)
325   {
326     Handle(Geom_Curve) gc = GS->UIso(U);
327     if(IsVP && (FirstV == 0.0 && LastV == (2.*M_PI))) I = gc;
328     else
329     {
330       Handle(Geom_TrimmedCurve) gtc = new Geom_TrimmedCurve(gc,FirstV,LastV);
331       //szv:I = Handle(Geom_Curve)::DownCast(gtc);
332       I = gtc;
333     }
334   }
335   else//OffsetSurface
336   {
337     const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (GS);
338     const Handle(Geom_Surface) bs = gos->BasisSurface();
339     Handle(Geom_Curve) gcbs = bs->UIso(U);
340     GeomAdaptor_Curve gac(gcbs);
341     const GeomAbs_CurveType GACT = gac.GetType();
342     if(IsVP || IsVC || GACT == GeomAbs_BSplineCurve || GACT == GeomAbs_BezierCurve || Abs(LastV - FirstV) < 1.e+5)
343     {
344       Handle(Geom_Curve) gc = gos->UIso(U);
345       if(IsVP && (FirstV == 0.0 && LastV == (2*M_PI))) I = gc;
346       else
347       {
348         Handle(Geom_TrimmedCurve) gtc = new Geom_TrimmedCurve(gc,FirstV,LastV);
349         //szv:I = Handle(Geom_Curve)::DownCast(gtc);
350         I = gtc;
351       }
352     }
353     else//Offset Line, Parab, Hyperb
354     {
355       Standard_Real VmTr, VMTr;
356       if(GACT != GeomAbs_Hyperbola)
357       {
358         if(FirstV >= 0. && LastV >= 0.){ VmTr = FirstV; VMTr = ((LastV - FirstV) > 1.e+4) ? (FirstV + 1.e+4) : LastV; }
359         else if(FirstV < 0. && LastV < 0.){ VMTr = LastV; VmTr = ((FirstV - LastV) < -1.e+4) ? (LastV - 1.e+4) : FirstV; }
360         else { VmTr = (FirstV < -1.e+4) ? -1.e+4 : FirstV; VMTr = (LastV > 1.e+4) ? 1.e+4 : LastV; }
361       }
362       else//Hyperbola
363       {
364         if(FirstV >= 0. && LastV >= 0.)
365         {
366           if(FirstV > 4.) return;
367           VmTr = FirstV; VMTr = (LastV > 4.) ? 4. : LastV;
368         }
369         else if(FirstV < 0. && LastV < 0.)
370         {
371           if(LastV < -4.) return;
372           VMTr = LastV; VmTr = (FirstV < -4.) ? -4. : FirstV;
373         }
374         else { VmTr = (FirstV < -4.) ? -4. : FirstV; VMTr = (LastV > 4.) ? 4. : LastV; }
375       }
376       //Make trimmed surface
377       Handle(Geom_RectangularTrimmedSurface) rts = new Geom_RectangularTrimmedSurface(gos,VmTr,VMTr,Standard_True);
378       I = rts->UIso(U);
379     }
380   }
381 }
382 //================================================================================
383 //function: FUN_GetViso
384 //================================================================================
385 static void FUN_GetViso(const Handle(Geom_Surface)& GS,
386                         const GeomAbs_SurfaceType&  T,
387                         const Standard_Real&        FirstU,
388                         const Standard_Real&        LastU,
389                         const Standard_Boolean&     IsUC,
390                         const Standard_Boolean&     IsUP,
391                         const Standard_Real&        V,
392                         Handle(Geom_Curve)&         I)
393 {
394   if(T !=  GeomAbs_OffsetSurface)
395   {
396     Handle(Geom_Curve) gc = GS->VIso(V);
397     if(IsUP && (FirstU == 0.0 && LastU == (2*M_PI))) I = gc;
398     else
399     {
400       Handle(Geom_TrimmedCurve) gtc = new Geom_TrimmedCurve(gc,FirstU,LastU);
401       //szv:I = Handle(Geom_Curve)::DownCast(gtc);
402       I = gtc;
403     }
404   }
405   else//OffsetSurface
406   {
407     const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (GS);
408     const Handle(Geom_Surface) bs = gos->BasisSurface();
409     Handle(Geom_Curve) gcbs = bs->VIso(V);
410     GeomAdaptor_Curve gac(gcbs);
411     const GeomAbs_CurveType GACT = gac.GetType();
412     if(IsUP || IsUC || GACT == GeomAbs_BSplineCurve || GACT == GeomAbs_BezierCurve || Abs(LastU - FirstU) < 1.e+5)
413     {
414       Handle(Geom_Curve) gc = gos->VIso(V);
415       if(IsUP && (FirstU == 0.0 && LastU == (2*M_PI))) I = gc;
416       else
417       {
418         Handle(Geom_TrimmedCurve) gtc = new Geom_TrimmedCurve(gc,FirstU,LastU);
419         //szv:I = Handle(Geom_Curve)::DownCast(gtc);
420         I = gtc;
421       }
422     }
423     else//Offset Line, Parab, Hyperb
424     {
425       Standard_Real UmTr, UMTr;
426       if(GACT != GeomAbs_Hyperbola)
427       {
428         if(FirstU >= 0. && LastU >= 0.){ UmTr = FirstU; UMTr = ((LastU - FirstU) > 1.e+4) ? (FirstU + 1.e+4) : LastU; }
429         else if(FirstU < 0. && LastU < 0.){ UMTr = LastU; UmTr = ((FirstU - LastU) < -1.e+4) ? (LastU - 1.e+4) : FirstU; }
430         else { UmTr = (FirstU < -1.e+4) ? -1.e+4 : FirstU; UMTr = (LastU > 1.e+4) ? 1.e+4 : LastU; }
431       }
432       else//Hyperbola
433       {
434         if(FirstU >= 0. && LastU >= 0.)
435         {
436           if(FirstU > 4.) return;
437           UmTr = FirstU; UMTr = (LastU > 4.) ? 4. : LastU;
438         }
439         else if(FirstU < 0. && LastU < 0.)
440         {
441           if(LastU < -4.) return;
442           UMTr = LastU; UmTr = (FirstU < -4.) ? -4. : FirstU;
443         }
444         else { UmTr = (FirstU < -4.) ? -4. : FirstU; UMTr = (LastU > 4.) ? 4. : LastU; }
445       }
446       //Make trimmed surface
447       Handle(Geom_RectangularTrimmedSurface) rts = new Geom_RectangularTrimmedSurface(gos,UmTr,UMTr,Standard_True);
448       I = rts->VIso(V);
449     }
450   }
451 }
452 //================================================================================
453 //function: FUN_PL_Intersection
454 //================================================================================
455 static void FUN_PL_Intersection(const Handle(Adaptor3d_HSurface)& S1,
456                                 const GeomAbs_SurfaceType&        T1,
457                                 const Handle(Adaptor3d_HSurface)& S2,
458                                 const GeomAbs_SurfaceType&        T2,
459                                 Standard_Boolean&                 IsOk,
460                                 TColgp_SequenceOfPnt&             SP,
461                                 gp_Vec&                           DV)
462 {
463   IsOk = Standard_False;
464   // 1. Check: both surfaces have U(V)isos - lines.
465   DV = gp_Vec(0.,0.,1.);
466   Standard_Boolean isoS1isLine[2] = {0, 0};
467   Standard_Boolean isoS2isLine[2] = {0, 0};
468   Handle(Geom_Curve) C1, C2;
469   const GeomAdaptor_Surface & gas1 = *(GeomAdaptor_Surface*)(&(S1->Surface()));
470   const GeomAdaptor_Surface & gas2 = *(GeomAdaptor_Surface*)(&(S2->Surface()));
471   const Handle(Geom_Surface) gs1 = gas1.Surface();
472   const Handle(Geom_Surface) gs2 = gas2.Surface();
473   Standard_Real MS1[2], MS2[2];
474   MS1[0] = 0.5 * (S1->LastUParameter() + S1->FirstUParameter());
475   MS1[1] = 0.5 * (S1->LastVParameter() + S1->FirstVParameter());
476   MS2[0] = 0.5 * (S2->LastUParameter() + S2->FirstUParameter());
477   MS2[1] = 0.5 * (S2->LastVParameter() + S2->FirstVParameter());
478   if(T1 == GeomAbs_SurfaceOfExtrusion) isoS1isLine[0] = Standard_True;
479   else if(!S1->IsVPeriodic() && !S1->IsVClosed()) {
480     if(T1 != GeomAbs_OffsetSurface) C1 = gs1->UIso(MS1[0]);
481     else {
482       const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs1);
483       const Handle(Geom_Surface) bs = gos->BasisSurface();
484       C1 = bs->UIso(MS1[0]);
485     }
486     GeomAdaptor_Curve gac(C1);
487     if(gac.GetType() == GeomAbs_Line) isoS1isLine[0] = Standard_True;
488   }
489   if(!S1->IsUPeriodic() && !S1->IsUClosed()) {
490     if(T1 != GeomAbs_OffsetSurface) C1 = gs1->VIso(MS1[1]);
491     else {
492       const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs1);
493       const Handle(Geom_Surface) bs = gos->BasisSurface();
494       C1 = bs->VIso(MS1[1]);
495     }
496     GeomAdaptor_Curve gac(C1);
497     if(gac.GetType() == GeomAbs_Line) isoS1isLine[1] = Standard_True;
498   }
499   if(T2 == GeomAbs_SurfaceOfExtrusion) isoS2isLine[0] = Standard_True;
500   else if(!S2->IsVPeriodic() && !S2->IsVClosed()) {
501     if(T2 != GeomAbs_OffsetSurface) C2 = gs2->UIso(MS2[0]);
502     else {
503       const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs2);
504       const Handle(Geom_Surface) bs = gos->BasisSurface();
505       C2 = bs->UIso(MS2[0]);
506     }
507     GeomAdaptor_Curve gac(C2);
508     if(gac.GetType() == GeomAbs_Line) isoS2isLine[0] = Standard_True;
509   }
510   if(!S2->IsUPeriodic() && !S2->IsUClosed()) {
511     if(T2 != GeomAbs_OffsetSurface) C2 = gs2->VIso(MS2[1]);
512     else {
513       const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs2);
514       const Handle(Geom_Surface) bs = gos->BasisSurface();
515       C2 = bs->VIso(MS2[1]);
516     }
517     GeomAdaptor_Curve gac(C2);
518     if(gac.GetType() == GeomAbs_Line) isoS2isLine[1] = Standard_True;
519   }
520   Standard_Boolean IsBothLines = ((isoS1isLine[0] || isoS1isLine[1]) &&
521                                   (isoS2isLine[0] || isoS2isLine[1]));
522   if(!IsBothLines){
523     return;
524   }
525   // 2. Check: Uiso lines of both surfaces are collinear.
526   gp_Pnt puvS1, puvS2;
527   gp_Vec derS1[2], derS2[2];
528   S1->D1(MS1[0], MS1[1], puvS1, derS1[0], derS1[1]);
529   S2->D1(MS2[0], MS2[1], puvS2, derS2[0], derS2[1]);
530   C1.Nullify(); C2.Nullify();
531   Standard_Integer iso = 0;
532   if(isoS1isLine[0] && isoS2isLine[0] &&
533      derS1[1].IsParallel(derS2[1],Precision::Angular())) {
534     iso = 1;
535     FUN_GetViso(gs1,T1,S1->FirstUParameter(),S1->LastUParameter(),
536                 S1->IsUClosed(),S1->IsUPeriodic(),MS1[1],C1);
537     FUN_GetViso(gs2,T2,S2->FirstUParameter(),S2->LastUParameter(),
538                 S2->IsUClosed(),S2->IsUPeriodic(),MS2[1],C2);
539   }
540   else if(isoS1isLine[0] && isoS2isLine[1] &&
541           derS1[1].IsParallel(derS2[0],Precision::Angular())) {
542     iso = 1;
543     FUN_GetViso(gs1,T1,S1->FirstUParameter(),S1->LastUParameter(),
544                 S1->IsUClosed(),S1->IsUPeriodic(),MS1[1],C1);
545     FUN_GetUiso(gs2,T2,S2->FirstVParameter(),S2->LastVParameter(),
546                 S2->IsVClosed(),S2->IsVPeriodic(),MS2[0],C2);
547   }
548   else if(isoS1isLine[1] && isoS2isLine[0] &&
549           derS1[0].IsParallel(derS2[1],Precision::Angular())) {
550     iso = 0;
551     FUN_GetUiso(gs1,T1,S1->FirstVParameter(),S1->LastVParameter(),
552                 S1->IsVClosed(),S1->IsVPeriodic(),MS1[0],C1);
553     FUN_GetViso(gs2,T2,S2->FirstUParameter(),S2->LastUParameter(),
554                 S2->IsUClosed(),S2->IsUPeriodic(),MS2[1],C2);
555   }
556   else if(isoS1isLine[1] && isoS2isLine[1] &&
557           derS1[0].IsParallel(derS2[0],Precision::Angular())) {
558     iso = 0;
559     FUN_GetUiso(gs1,T1,S1->FirstVParameter(),S1->LastVParameter(),
560                 S1->IsVClosed(),S1->IsVPeriodic(),MS1[0],C1);
561     FUN_GetUiso(gs2,T2,S2->FirstVParameter(),S2->LastVParameter(),
562                 S2->IsVClosed(),S2->IsVPeriodic(),MS2[0],C2);
563   }
564   else {
565     IsOk = Standard_False;
566     return;
567   }
568   IsOk = Standard_True;
569   // 3. Make intersections of V(U)isos
570   if(C1.IsNull() || C2.IsNull()) return;
571   DV = derS1[iso];
572   Handle(Geom_Plane) GPln = new Geom_Plane(gp_Pln(puvS1,gp_Dir(DV)));
573   Handle(Geom_Curve) C1Prj =
574     GeomProjLib::ProjectOnPlane(C1,GPln,gp_Dir(DV),Standard_True);
575   Handle(Geom_Curve) C2Prj =
576     GeomProjLib::ProjectOnPlane(C2,GPln,gp_Dir(DV),Standard_True);
577   if(C1Prj.IsNull() || C2Prj.IsNull()) return;
578   Handle(Geom2d_Curve) C1Prj2d = GeomProjLib::Curve2d (C1Prj,GPln);
579   Handle(Geom2d_Curve) C2Prj2d = GeomProjLib::Curve2d (C2Prj,GPln);
580   Geom2dAPI_InterCurveCurve ICC(C1Prj2d,C2Prj2d,1.0e-7);
581   if(ICC.NbPoints() > 0 )
582   {
583     for(Standard_Integer ip = 1; ip <= ICC.NbPoints(); ip++)
584     {
585       gp_Pnt2d P = ICC.Point(ip);
586       gp_Pnt P3d = ElCLib::To3d(gp_Ax2(puvS1,gp_Dir(DV)),P);
587       SP.Append(P3d);
588     }
589   }
590 }
591 //================================================================================
592 //function: FUN_NewFirstLast
593 //================================================================================
594 static void FUN_NewFirstLast(const GeomAbs_CurveType& ga_ct,
595                              const Standard_Real&     Fst,
596                              const Standard_Real&     Lst,
597                              const Standard_Real&     TrVal,
598                              Standard_Real&           NewFst,
599                              Standard_Real&           NewLst,
600                              Standard_Boolean&        NeedTr)
601 {
602   NewFst = Fst; NewLst = Lst; NeedTr = Standard_False;
603   switch (ga_ct)
604   {
605     case GeomAbs_Line:
606     case GeomAbs_Parabola:
607     {
608       if(Abs(Lst - Fst) > TrVal)
609       {
610         if(Fst >= 0. && Lst >= 0.)
611         {
612           NewFst = Fst;
613           NewLst = ((Fst + TrVal) < Lst) ? (Fst + TrVal) : Lst;
614         }
615         if(Fst < 0. && Lst < 0.)
616         {
617           NewLst = Lst;
618           NewFst = ((Lst - TrVal) > Fst) ? (Lst - TrVal) : Fst;
619         }
620         else
621         {
622           NewFst = (Fst < -TrVal) ? -TrVal : Fst;
623           NewLst = (Lst > TrVal) ? TrVal : Lst;
624         }
625         NeedTr = Standard_True;
626       }
627       break;
628     }
629     case GeomAbs_Hyperbola:
630     {
631       if(Abs(Lst - Fst) > 10.)
632       { 
633         if(Fst >= 0. && Lst >= 0.)
634         {
635           if(Fst > 4.) return;
636           NewFst = Fst;
637           NewLst = (Lst > 4.) ? 4. : Lst;
638         }
639         if(Fst < 0. && Lst < 0.)
640         {
641           if(Lst < -4.) return;
642           NewLst = Lst;
643           NewFst = (Fst < -4.) ? -4. : Fst;
644         }
645         else
646         {
647           NewFst = (Fst < -4.) ? -4. : Fst;
648           NewLst = (Lst > 4.) ? 4. : Lst;
649         }
650         NeedTr = Standard_True;
651       }
652       break;
653     }
654     default:
655     break;
656   }
657 }
658 //================================================================================
659 //function: FUN_TrimBothSurf
660 //================================================================================
661 static void FUN_TrimBothSurf(const Handle(Adaptor3d_HSurface)& S1,
662                              const GeomAbs_SurfaceType&        T1,
663                              const Handle(Adaptor3d_HSurface)& S2,
664                              const GeomAbs_SurfaceType&        T2,
665                              const Standard_Real&              TV,
666                              Handle(Adaptor3d_HSurface)&       NS1,
667                              Handle(Adaptor3d_HSurface)&       NS2)
668 {
669   const GeomAdaptor_Surface & gas1 = *(GeomAdaptor_Surface*)(&(S1->Surface()));
670   const GeomAdaptor_Surface & gas2 = *(GeomAdaptor_Surface*)(&(S2->Surface()));
671   const Handle(Geom_Surface) gs1 = gas1.Surface();
672   const Handle(Geom_Surface) gs2 = gas2.Surface();
673   const Standard_Real UM1 = 0.5 * (S1->LastUParameter() + S1->FirstUParameter());
674   const Standard_Real UM2 = 0.5 * (S2->LastUParameter() + S2->FirstUParameter());
675   const Standard_Real VM1 = 0.5 * (S1->LastVParameter() + S1->FirstVParameter());
676   const Standard_Real VM2 = 0.5 * (S2->LastVParameter() + S2->FirstVParameter());
677   Handle(Geom_Curve) visoS1, visoS2, uisoS1, uisoS2;
678   if(T1 != GeomAbs_OffsetSurface){ visoS1 = gs1->VIso(VM1); uisoS1 = gs1->UIso(UM1); }
679   else
680   {
681     const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs1);
682     const Handle(Geom_Surface) bs = gos->BasisSurface();
683     visoS1 = bs->VIso(VM1); uisoS1 = bs->UIso(UM1);
684   }
685   if(T2 != GeomAbs_OffsetSurface){ visoS2 = gs2->VIso(VM2); uisoS2 = gs2->UIso(UM2); }
686   else
687   {
688     const Handle(Geom_OffsetSurface) gos = Handle(Geom_OffsetSurface)::DownCast (gs2);
689     const Handle(Geom_Surface) bs = gos->BasisSurface();
690     visoS2 = bs->VIso(VM2); uisoS2 = bs->UIso(UM2);
691   }
692   if(uisoS1.IsNull() || uisoS2.IsNull() || visoS1.IsNull() || visoS2.IsNull()){ NS1 = S1; NS2 = S2; return; }
693   GeomAdaptor_Curve gau1(uisoS1);
694   GeomAdaptor_Curve gav1(visoS1);
695   GeomAdaptor_Curve gau2(uisoS2);
696   GeomAdaptor_Curve gav2(visoS2);
697   GeomAbs_CurveType GA_U1 = gau1.GetType();
698   GeomAbs_CurveType GA_V1 = gav1.GetType();
699   GeomAbs_CurveType GA_U2 = gau2.GetType();
700   GeomAbs_CurveType GA_V2 = gav2.GetType();
701   Standard_Boolean TrmU1 = Standard_False;
702   Standard_Boolean TrmV1 = Standard_False;
703   Standard_Boolean TrmU2 = Standard_False;
704   Standard_Boolean TrmV2 = Standard_False;
705   Standard_Real V1S1,V2S1,U1S1,U2S1, V1S2,V2S2,U1S2,U2S2;
706   FUN_NewFirstLast(GA_U1,S1->FirstVParameter(),S1->LastVParameter(),TV,V1S1,V2S1,TrmV1);
707   FUN_NewFirstLast(GA_V1,S1->FirstUParameter(),S1->LastUParameter(),TV,U1S1,U2S1,TrmU1);
708   FUN_NewFirstLast(GA_U2,S2->FirstVParameter(),S2->LastVParameter(),TV,V1S2,V2S2,TrmV2);
709   FUN_NewFirstLast(GA_V2,S2->FirstUParameter(),S2->LastUParameter(),TV,U1S2,U2S2,TrmU2);
710   if(TrmV1) NS1 = S1->VTrim(V1S1, V2S1, 1.0e-7);
711   if(TrmV2) NS2 = S2->VTrim(V1S2, V2S2, 1.0e-7);
712   if(TrmU1)
713   {
714     if(TrmV1)
715     {
716       Handle(Adaptor3d_HSurface) TS = NS1;
717       NS1 = TS->UTrim(U1S1, U2S1, 1.0e-7);
718     }
719     else NS1 = S1->UTrim(U1S1, U2S1, 1.0e-7);
720   }
721   if(TrmU2)
722   {
723     if(TrmV2)
724     {
725       Handle(Adaptor3d_HSurface) TS = NS2;
726       NS2 = TS->UTrim(U1S2, U2S2, 1.0e-7);
727     }
728     else NS2 = S2->UTrim(U1S2, U2S2, 1.0e-7);
729   }
730 }
731
732 //=======================================================================
733 //function : Perform
734 //purpose  : 
735 //=======================================================================
736 void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)&  theS1,
737                                     const Handle(Adaptor3d_TopolTool)& theD1,
738                                     const Handle(Adaptor3d_HSurface)&  theS2,
739                                     const Handle(Adaptor3d_TopolTool)& theD2,
740                                     const Standard_Real TolArc,
741                                     const Standard_Real TolTang,
742                                     const Standard_Boolean isGeomInt,
743                                     const Standard_Boolean theIsReqToKeepRLine,
744                                     const Standard_Boolean theIsReqToPostWLProc)
745 {
746   myTolArc = TolArc;
747   myTolTang = TolTang;
748   if(myFleche <= Precision::PConfusion())
749     myFleche = 0.01;
750   if(myUVMaxStep <= Precision::PConfusion())
751     myUVMaxStep = 0.01;
752
753   done = Standard_False;
754   spnt.Clear();
755   slin.Clear();
756   empt = Standard_True;
757   tgte = Standard_False;
758   oppo = Standard_False;
759
760   GeomAbs_SurfaceType typs1 = theS1->GetType();
761   GeomAbs_SurfaceType typs2 = theS2->GetType();
762   
763   //treatment of the cases with cone or torus
764   Standard_Boolean TreatAsBiParametric = Standard_False;
765   Standard_Integer bGeomGeom = 0;
766   //
767   if (typs1 == GeomAbs_Cone  || typs2 == GeomAbs_Cone ||
768       typs1 == GeomAbs_Torus || typs2 == GeomAbs_Torus) {
769     gp_Ax1 aCTAx, aGeomAx;
770     GeomAbs_SurfaceType aCTType;
771     Standard_Boolean bToCheck;
772     //
773     const Handle(Adaptor3d_HSurface)& aCTSurf = 
774       (typs1 == GeomAbs_Cone || typs1 == GeomAbs_Torus) ? theS1 : theS2;
775     const Handle(Adaptor3d_HSurface)& aGeomSurf = 
776       (typs1 == GeomAbs_Cone || typs1 == GeomAbs_Torus) ? theS2 : theS1;
777     //
778     aCTType = aCTSurf->GetType();
779     bToCheck = Standard_False;
780     //
781     if (typs1 == GeomAbs_Cone  || typs2 == GeomAbs_Cone) {
782       const gp_Cone aCon1 = (aCTType == GeomAbs_Cone) ? 
783         aCTSurf->Cone() : aGeomSurf->Cone();
784       Standard_Real a1 = Abs(aCon1.SemiAngle());
785       bToCheck = (a1 < 0.02) || (a1 > 1.55);
786       //
787       if (typs1 == typs2) {
788         const gp_Cone aCon2 = aGeomSurf->Cone();
789         Standard_Real a2 = Abs(aCon2.SemiAngle());
790         bToCheck = bToCheck || (a2 < 0.02) || (a2 > 1.55);
791         //
792         if (a1 > 1.55 && a2 > 1.55) {//quasi-planes: if same domain, treat as canonic
793           const gp_Ax1 A1 = aCon1.Axis(), A2 = aCon2.Axis();
794           if (A1.IsParallel(A2,Precision::Angular())) {
795             const gp_Pnt Apex1 = aCon1.Apex(), Apex2 = aCon2.Apex();
796             const gp_Pln Plan1( Apex1, A1.Direction() );
797             if (Plan1.Distance( Apex2 ) <= Precision::Confusion()) {
798               bToCheck = Standard_False;
799             }
800           }
801         }
802       }
803       //
804       TreatAsBiParametric = bToCheck;
805       if (aCTType == GeomAbs_Cone) {
806         aCTAx = aCon1.Axis();
807       }
808     }
809     //
810     if (typs1 == GeomAbs_Torus || typs2 == GeomAbs_Torus) {
811       const gp_Torus aTor1 = (aCTType == GeomAbs_Torus) ? 
812         aCTSurf->Torus() : aGeomSurf->Torus();
813       bToCheck = aTor1.MajorRadius() > aTor1.MinorRadius();
814       if (typs1 == typs2) {
815         const gp_Torus aTor2 = aGeomSurf->Torus();
816         bToCheck = aTor2.MajorRadius() > aTor2.MinorRadius();
817       }
818       //
819       if (aCTType == GeomAbs_Torus) {
820         aCTAx = aTor1.Axis();
821       }
822     }
823     //
824     if (bToCheck) {
825       const gp_Lin aL1(aCTAx);
826       //
827       switch (aGeomSurf->GetType()) {
828       case GeomAbs_Plane: {
829         aGeomAx = aGeomSurf->Plane().Axis();
830         if (aCTType == GeomAbs_Cone) {
831           bGeomGeom = 1;
832           if (Abs(aCTSurf->Cone().SemiAngle()) < 0.02) {
833             Standard_Real ps = Abs(aCTAx.Direction().Dot(aGeomAx.Direction()));
834             if(ps < 0.015) {
835               bGeomGeom = 0;
836             }
837           }
838         }
839         else {
840           if (aCTAx.IsParallel(aGeomAx, Precision::Angular()) ||
841               (aCTAx.IsNormal(aGeomAx, Precision::Angular()) && 
842                (aGeomSurf->Plane().Distance(aCTAx.Location()) < Precision::Confusion()))) {
843             bGeomGeom = 1;
844           }
845         }
846         bToCheck = Standard_False;
847         break;
848       }
849       case GeomAbs_Sphere: {
850         if (aL1.Distance(aGeomSurf->Sphere().Location()) < Precision::Confusion()) {
851           bGeomGeom = 1;
852         }
853         bToCheck = Standard_False;
854         break;
855       }
856       case GeomAbs_Cylinder:
857         aGeomAx = aGeomSurf->Cylinder().Axis();
858         break;
859       case GeomAbs_Cone: 
860         aGeomAx = aGeomSurf->Cone().Axis();
861         break;
862       case GeomAbs_Torus: 
863         aGeomAx = aGeomSurf->Torus().Axis();
864         break;
865       default: 
866         bToCheck = Standard_False;
867         break;
868       }
869       //
870       if (bToCheck) {
871         if (aCTAx.IsParallel(aGeomAx, Precision::Angular()) &&
872             (aL1.Distance(aGeomAx.Location()) <= Precision::Confusion())) {
873           bGeomGeom = 1;
874         }
875       }
876       //
877       if (bGeomGeom == 1) {
878         TreatAsBiParametric = Standard_False;
879       }
880     }
881   }
882   //
883
884   if(theD1->DomainIsInfinite() || theD2->DomainIsInfinite()) {
885     TreatAsBiParametric= Standard_False;
886   }
887
888 //  Modified by skv - Mon Sep 26 14:58:30 2005 Begin
889 //   if(TreatAsBiParametric) { typs1 = typs2 = GeomAbs_BezierSurface; }
890   if(TreatAsBiParametric)
891   {
892     if (typs1 == GeomAbs_Cone && typs2 == GeomAbs_Plane)
893       typs1 = GeomAbs_BezierSurface; // Using Imp-Prm Intersector
894     else if (typs1 == GeomAbs_Plane && typs2 == GeomAbs_Cone)
895       typs2 = GeomAbs_BezierSurface; // Using Imp-Prm Intersector
896     else {
897       // Using Prm-Prm Intersector
898       typs1 = GeomAbs_BezierSurface;
899       typs2 = GeomAbs_BezierSurface;
900     }
901   }
902 //  Modified by skv - Mon Sep 26 14:58:30 2005 End
903
904   // Surface type definition
905   Standard_Integer ts1 = 0;
906   switch (typs1)
907   {
908     case GeomAbs_Plane:
909     case GeomAbs_Cylinder:
910     case GeomAbs_Sphere:
911     case GeomAbs_Cone: ts1 = 1; break;
912     case GeomAbs_Torus: ts1 = bGeomGeom; break;
913     default: break;
914   }
915
916   Standard_Integer ts2 = 0;
917   switch (typs2)
918   {
919     case GeomAbs_Plane:
920     case GeomAbs_Cylinder:
921     case GeomAbs_Sphere:
922     case GeomAbs_Cone: ts2 = 1; break;
923     case GeomAbs_Torus: ts2 = bGeomGeom; break;
924     default: break;
925   }
926   //
927   // treatment of the cases with torus and any other geom surface
928   //
929   // Possible intersection types: 1. ts1 == ts2 == 1 <Geom-Geom>
930   //                              2. ts1 != ts2      <Geom-Param>
931   //                              3. ts1 == ts2 == 0 <Param-Param>
932
933   // Geom - Geom
934   if(ts1 == ts2 && ts1 == 1)
935   {
936     IntSurf_ListOfPntOn2S ListOfPnts;
937     ListOfPnts.Clear();
938     if(isGeomInt)
939     {
940       GeomGeomPerfom(theS1, theD1, theS2, theD2, TolArc, TolTang,
941                      ListOfPnts, typs1, typs2, theIsReqToKeepRLine);
942     }
943     else
944     {
945       ParamParamPerfom(theS1, theD1, theS2, theD2, 
946               TolArc, TolTang, ListOfPnts, typs1, typs2);
947     }
948   }
949
950   // Geom - Param
951   if(ts1 != ts2)
952   {
953     GeomParamPerfom(theS1, theD1, theS2, theD2, ts1 == 0, typs1, typs2);
954   }
955
956   // Param - Param 
957   if(ts1 == ts2 && ts1 == 0)
958   {
959     IntSurf_ListOfPntOn2S ListOfPnts;
960     ListOfPnts.Clear();
961
962     ParamParamPerfom(theS1, theD1, theS2, theD2, TolArc,
963                         TolTang, ListOfPnts, typs1, typs2);
964   }
965
966   if(!theIsReqToPostWLProc)
967     return;
968
969   for(Standard_Integer i = slin.Lower(); i <= slin.Upper(); i++)
970   {
971     Handle(IntPatch_WLine) aWL = Handle(IntPatch_WLine)::DownCast(slin.Value(i));
972
973     if(aWL.IsNull())
974       continue;
975
976     if (!aWL->IsPurgingAllowed())
977       continue;
978
979     Handle(IntPatch_WLine) aRW =
980       IntPatch_WLineTool::ComputePurgedWLine(aWL, theS1, theS2, theD1, theD2);
981
982     if(aRW.IsNull())
983       continue;
984
985     slin.InsertAfter(i, aRW);
986     slin.Remove(i);
987   }
988 }
989
990 //=======================================================================
991 //function : Perform
992 //purpose  : 
993 //=======================================================================
994 void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)&  theS1,
995                                     const Handle(Adaptor3d_TopolTool)& theD1,
996                                     const Handle(Adaptor3d_HSurface)&  theS2,
997                                     const Handle(Adaptor3d_TopolTool)& theD2,
998                                     const Standard_Real TolArc,
999                                     const Standard_Real TolTang,
1000                                     IntSurf_ListOfPntOn2S& ListOfPnts,
1001                                     const Standard_Boolean isGeomInt,
1002                                     const Standard_Boolean theIsReqToKeepRLine,
1003                                     const Standard_Boolean theIsReqToPostWLProc)
1004 {
1005   myTolArc = TolArc;
1006   myTolTang = TolTang;
1007   if(myFleche <= Precision::PConfusion())
1008     myFleche = 0.01;
1009   if(myUVMaxStep <= Precision::PConfusion())
1010     myUVMaxStep = 0.01;
1011     
1012   done = Standard_False;
1013   spnt.Clear();
1014   slin.Clear();
1015   empt = Standard_True;
1016   tgte = Standard_False;
1017   oppo = Standard_False;
1018
1019   GeomAbs_SurfaceType typs1 = theS1->GetType();
1020   GeomAbs_SurfaceType typs2 = theS2->GetType();
1021   //
1022   //treatment of the cases with cone or torus
1023   Standard_Boolean TreatAsBiParametric = Standard_False;
1024   Standard_Integer bGeomGeom = 0;
1025   //
1026   if (typs1 == GeomAbs_Cone  || typs2 == GeomAbs_Cone ||
1027       typs1 == GeomAbs_Torus || typs2 == GeomAbs_Torus) {
1028     gp_Ax1 aCTAx, aGeomAx;
1029     GeomAbs_SurfaceType aCTType;
1030     Standard_Boolean bToCheck;
1031     //
1032     const Handle(Adaptor3d_HSurface)& aCTSurf = 
1033       (typs1 == GeomAbs_Cone || typs1 == GeomAbs_Torus) ? theS1 : theS2;
1034     const Handle(Adaptor3d_HSurface)& aGeomSurf = 
1035       (typs1 == GeomAbs_Cone || typs1 == GeomAbs_Torus) ? theS2 : theS1;
1036     //
1037     aCTType = aCTSurf->GetType();
1038     bToCheck = Standard_False;
1039     //
1040     if (typs1 == GeomAbs_Cone  || typs2 == GeomAbs_Cone) {
1041       const gp_Cone aCon1 = (aCTType == GeomAbs_Cone) ? 
1042         aCTSurf->Cone() : aGeomSurf->Cone();
1043       Standard_Real a1 = Abs(aCon1.SemiAngle());
1044       bToCheck = (a1 < 0.02) || (a1 > 1.55);
1045       //
1046       if (typs1 == typs2) {
1047         const gp_Cone aCon2 = aGeomSurf->Cone();
1048         Standard_Real a2 = Abs(aCon2.SemiAngle());
1049         bToCheck = bToCheck || (a2 < 0.02) || (a2 > 1.55);
1050         //
1051         if (a1 > 1.55 && a2 > 1.55) {//quasi-planes: if same domain, treat as canonic
1052           const gp_Ax1 A1 = aCon1.Axis(), A2 = aCon2.Axis();
1053           if (A1.IsParallel(A2,Precision::Angular())) {
1054             const gp_Pnt Apex1 = aCon1.Apex(), Apex2 = aCon2.Apex();
1055             const gp_Pln Plan1( Apex1, A1.Direction() );
1056             if (Plan1.Distance( Apex2 ) <= Precision::Confusion()) {
1057               bToCheck = Standard_False;
1058             }
1059           }
1060         }
1061       }
1062       //
1063       TreatAsBiParametric = bToCheck;
1064       if (aCTType == GeomAbs_Cone) {
1065         aCTAx = aCon1.Axis();
1066       }
1067     }
1068     //
1069     if (typs1 == GeomAbs_Torus || typs2 == GeomAbs_Torus) {
1070       const gp_Torus aTor1 = (aCTType == GeomAbs_Torus) ? 
1071         aCTSurf->Torus() : aGeomSurf->Torus();
1072       bToCheck = aTor1.MajorRadius() > aTor1.MinorRadius();
1073       if (typs1 == typs2) {
1074         const gp_Torus aTor2 = aGeomSurf->Torus();
1075         bToCheck = aTor2.MajorRadius() > aTor2.MinorRadius();
1076       }
1077       //
1078       if (aCTType == GeomAbs_Torus) {
1079         aCTAx = aTor1.Axis();
1080       }
1081     }
1082     //
1083     if (bToCheck) {
1084       const gp_Lin aL1(aCTAx);
1085       //
1086       switch (aGeomSurf->GetType()) {
1087       case GeomAbs_Plane: {
1088         aGeomAx = aGeomSurf->Plane().Axis();
1089         if (aCTType == GeomAbs_Cone) {
1090           bGeomGeom = 1;
1091           if (Abs(aCTSurf->Cone().SemiAngle()) < 0.02) {
1092             Standard_Real ps = Abs(aCTAx.Direction().Dot(aGeomAx.Direction()));
1093             if(ps < 0.015) {
1094               bGeomGeom = 0;
1095             }
1096           }
1097         }
1098         else {
1099           if (aCTAx.IsParallel(aGeomAx, Precision::Angular()) ||
1100               (aCTAx.IsNormal(aGeomAx, Precision::Angular()) && 
1101                (aGeomSurf->Plane().Distance(aCTAx.Location()) < Precision::Confusion()))) {
1102             bGeomGeom = 1;
1103           }
1104         }
1105         bToCheck = Standard_False;
1106         break;
1107       }
1108       case GeomAbs_Sphere: {
1109         if (aL1.Distance(aGeomSurf->Sphere().Location()) < Precision::Confusion()) {
1110           bGeomGeom = 1;
1111         }
1112         bToCheck = Standard_False;
1113         break;
1114       }
1115       case GeomAbs_Cylinder:
1116         aGeomAx = aGeomSurf->Cylinder().Axis();
1117         break;
1118       case GeomAbs_Cone: 
1119         aGeomAx = aGeomSurf->Cone().Axis();
1120         break;
1121       case GeomAbs_Torus: 
1122         aGeomAx = aGeomSurf->Torus().Axis();
1123         break;
1124       default: 
1125         bToCheck = Standard_False;
1126         break;
1127       }
1128       //
1129       if (bToCheck) {
1130         if (aCTAx.IsParallel(aGeomAx, Precision::Angular()) &&
1131             (aL1.Distance(aGeomAx.Location()) <= Precision::Confusion())) {
1132           bGeomGeom = 1;
1133         }
1134       }
1135       //
1136       if (bGeomGeom == 1) {
1137         TreatAsBiParametric = Standard_False;
1138       }
1139     }
1140   }
1141   //
1142
1143   if(theD1->DomainIsInfinite() || theD2->DomainIsInfinite()) {
1144     TreatAsBiParametric= Standard_False;
1145   }
1146
1147   if(TreatAsBiParametric)
1148   {
1149     // Using Prm-Prm Intersector
1150     typs1 = GeomAbs_BezierSurface;
1151     typs2 = GeomAbs_BezierSurface;
1152   }
1153
1154   // Surface type definition
1155   Standard_Integer ts1 = 0;
1156   switch (typs1)
1157   {
1158     case GeomAbs_Plane:
1159     case GeomAbs_Cylinder:
1160     case GeomAbs_Sphere:
1161     case GeomAbs_Cone: ts1 = 1; break;
1162     case GeomAbs_Torus: ts1 = bGeomGeom; break;
1163     default: break;
1164   }
1165
1166   Standard_Integer ts2 = 0;
1167   switch (typs2)
1168   {
1169     case GeomAbs_Plane:
1170     case GeomAbs_Cylinder:
1171     case GeomAbs_Sphere:
1172     case GeomAbs_Cone: ts2 = 1; break;
1173     case GeomAbs_Torus: ts2 = bGeomGeom; break;
1174     default: break;
1175   }
1176   //
1177   // Possible intersection types: 1. ts1 == ts2 == 1 <Geom-Geom>
1178   //                              2. ts1 != ts2      <Geom-Param>
1179   //                              3. ts1 == ts2 == 0 <Param-Param>
1180
1181   if(!isGeomInt)
1182   {
1183     ParamParamPerfom(theS1, theD1, theS2, theD2, 
1184                 TolArc, TolTang, ListOfPnts, typs1, typs2);
1185   }
1186   else if(ts1 != ts2)
1187   {
1188     GeomParamPerfom(theS1, theD1, theS2, theD2, ts1 == 0, typs1, typs2);
1189   }
1190   else if (ts1 == 0)
1191   {
1192     ParamParamPerfom(theS1, theD1, theS2, theD2,
1193                 TolArc, TolTang, ListOfPnts, typs1, typs2);
1194   }
1195   else if(ts1 == 1)
1196   {
1197     GeomGeomPerfom(theS1, theD1, theS2, theD2, TolArc, TolTang,
1198                    ListOfPnts, typs1, typs2, theIsReqToKeepRLine);
1199   }
1200
1201   if(!theIsReqToPostWLProc)
1202     return;
1203
1204   for(Standard_Integer i = slin.Lower(); i <= slin.Upper(); i++)
1205   {
1206     Handle(IntPatch_WLine) aWL = Handle(IntPatch_WLine)::DownCast(slin.Value(i));
1207
1208     if(aWL.IsNull())
1209       continue;
1210
1211     if(!aWL->IsPurgingAllowed())
1212       continue;
1213
1214     Handle(IntPatch_WLine) aRW = 
1215       IntPatch_WLineTool::ComputePurgedWLine(aWL, theS1, theS2, theD1, theD2);
1216
1217     if(aRW.IsNull())
1218       continue;
1219
1220     slin.InsertAfter(i, aRW);
1221     slin.Remove(i);
1222   }
1223 }
1224
1225 //=======================================================================
1226 //function : ParamParamPerfom
1227 //purpose  : 
1228 //=======================================================================
1229 void IntPatch_Intersection::ParamParamPerfom(const Handle(Adaptor3d_HSurface)&  theS1,
1230                                              const Handle(Adaptor3d_TopolTool)& theD1,
1231                                              const Handle(Adaptor3d_HSurface)&  theS2,
1232                                              const Handle(Adaptor3d_TopolTool)& theD2,
1233                                              const Standard_Real TolArc,
1234                                              const Standard_Real TolTang,
1235                                              IntSurf_ListOfPntOn2S& ListOfPnts,
1236                                              const GeomAbs_SurfaceType typs1,
1237                                              const GeomAbs_SurfaceType typs2)
1238 {
1239   IntPatch_PrmPrmIntersection interpp;
1240   if(!theD1->DomainIsInfinite() && !theD2->DomainIsInfinite())
1241   {
1242     Standard_Boolean ClearFlag = Standard_True;
1243     if(!ListOfPnts.IsEmpty())
1244     {
1245       interpp.Perform(theS1,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep, ListOfPnts);
1246       ClearFlag = Standard_False;
1247     }
1248     interpp.Perform(theS1,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep,ClearFlag);
1249   }
1250   else if((theD1->DomainIsInfinite()) ^ (theD2->DomainIsInfinite()))
1251   {
1252     gp_Pnt pMaxXYZ, pMinXYZ;
1253     if(theD1->DomainIsInfinite())
1254     {
1255       FUN_GetMinMaxXYZPnt( theS2, pMinXYZ, pMaxXYZ );
1256       const Standard_Real MU = Max(Abs(theS2->FirstUParameter()),Abs(theS2->LastUParameter()));
1257       const Standard_Real MV = Max(Abs(theS2->FirstVParameter()),Abs(theS2->LastVParameter()));
1258       const Standard_Real AP = Max(MU, MV);
1259       Handle(Adaptor3d_HSurface) SS;
1260       FUN_TrimInfSurf(pMinXYZ, pMaxXYZ, theS1, AP, SS);
1261       interpp.Perform(SS,theD1,theS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep);
1262     }
1263     else
1264     {
1265       FUN_GetMinMaxXYZPnt( theS1, pMinXYZ, pMaxXYZ );
1266       const Standard_Real MU = Max(Abs(theS1->FirstUParameter()),Abs(theS1->LastUParameter()));
1267       const Standard_Real MV = Max(Abs(theS1->FirstVParameter()),Abs(theS1->LastVParameter()));
1268       const Standard_Real AP = Max(MU, MV);
1269       Handle(Adaptor3d_HSurface) SS;
1270       FUN_TrimInfSurf(pMinXYZ, pMaxXYZ, theS2, AP, SS);
1271       interpp.Perform(theS1, theD1, SS, theD2,TolTang, TolArc,myFleche,myUVMaxStep);
1272     }
1273   }//(theD1->DomainIsInfinite()) ^ (theD2->DomainIsInfinite())
1274   else
1275   {
1276     if(typs1 == GeomAbs_OtherSurface || typs2 == GeomAbs_OtherSurface)
1277     {
1278       done = Standard_False;
1279       return;
1280     }
1281
1282     Standard_Boolean IsPLInt = Standard_False;
1283     TColgp_SequenceOfPnt sop;
1284     gp_Vec v;
1285     FUN_PL_Intersection(theS1,typs1,theS2,typs2,IsPLInt,sop,v);
1286
1287     if(IsPLInt)
1288     {
1289       if(sop.Length() > 0)
1290       {
1291         for(Standard_Integer ip = 1; ip <= sop.Length(); ip++)
1292         {
1293           gp_Lin lin(sop.Value(ip),gp_Dir(v));
1294           Handle(IntPatch_Line) gl = new IntPatch_GLine(lin,Standard_False);
1295           slin.Append(gl);
1296         }
1297
1298         done = Standard_True;
1299       }
1300       else
1301         done = Standard_False;
1302
1303       return;
1304     }// 'COLLINEAR LINES'
1305     else
1306     {
1307       Handle(Adaptor3d_HSurface) nS1 = theS1;
1308       Handle(Adaptor3d_HSurface) nS2 = theS2;
1309       FUN_TrimBothSurf(theS1,typs1,theS2,typs2,1.e+8,nS1,nS2);
1310       interpp.Perform(nS1,theD1,nS2,theD2,TolTang,TolArc,myFleche,myUVMaxStep);
1311     }// 'NON - COLLINEAR LINES'
1312   }// both domains are infinite
1313
1314   if (interpp.IsDone())
1315   {
1316     done = Standard_True;
1317     tgte = Standard_False;
1318     empt = interpp.IsEmpty();
1319
1320     for(Standard_Integer i = 1; i <= interpp.NbLines(); i++)
1321     {
1322       if(interpp.Line(i)->ArcType() != IntPatch_Walking)
1323         slin.Append(interpp.Line(i));
1324     }
1325
1326     for (Standard_Integer i = 1; i <= interpp.NbLines(); i++)
1327     {
1328       if(interpp.Line(i)->ArcType() == IntPatch_Walking)
1329         slin.Append(interpp.Line(i));
1330     }
1331   }
1332 }
1333
1334 //=======================================================================
1335 ////function : GeomGeomPerfom
1336 //purpose  : 
1337 //=======================================================================
1338 void IntPatch_Intersection::GeomGeomPerfom(const Handle(Adaptor3d_HSurface)& theS1,
1339                                            const Handle(Adaptor3d_TopolTool)& theD1,
1340                                            const Handle(Adaptor3d_HSurface)& theS2,
1341                                            const Handle(Adaptor3d_TopolTool)& theD2,
1342                                            const Standard_Real TolArc,
1343                                            const Standard_Real TolTang,
1344                                            IntSurf_ListOfPntOn2S& ListOfPnts,
1345                                            const GeomAbs_SurfaceType theTyps1,
1346                                            const GeomAbs_SurfaceType theTyps2,
1347                                            const Standard_Boolean theIsReqToKeepRLine)
1348 {
1349   IntPatch_ImpImpIntersection interii(theS1,theD1,theS2,theD2,
1350                                       myTolArc,myTolTang, theIsReqToKeepRLine);
1351
1352   if (!interii.IsDone())
1353   {
1354     done = Standard_False;
1355     ParamParamPerfom(theS1, theD1, theS2, theD2, 
1356                 TolArc, TolTang, ListOfPnts, theTyps1, theTyps2);
1357     return;
1358   }
1359
1360   done = (interii.GetStatus() == IntPatch_ImpImpIntersection::IntStatus_OK);
1361   empt = interii.IsEmpty();
1362
1363   if(empt)
1364   {
1365     return;
1366   }
1367
1368   const Standard_Integer aNbPointsInALine = 200;
1369
1370   tgte = interii.TangentFaces();
1371   if (tgte)
1372     oppo = interii.OppositeFaces();
1373
1374   Standard_Boolean isWLExist = Standard_False;
1375   IntPatch_ALineToWLine AToW(theS1, theS2, aNbPointsInALine);
1376
1377   for (Standard_Integer i = 1; i <= interii.NbLines(); i++)
1378   {
1379     const Handle(IntPatch_Line)& line = interii.Line(i);
1380     if (line->ArcType() == IntPatch_Analytic)
1381     {
1382       isWLExist = Standard_True;
1383       AToW.MakeWLine(Handle(IntPatch_ALine)::DownCast(line), slin);
1384     }
1385     else
1386     {
1387       if (line->ArcType() == IntPatch_Walking)
1388       {
1389         Handle(IntPatch_WLine)::DownCast(line)->EnablePurging(Standard_False);
1390       }
1391
1392       if((line->ArcType() != IntPatch_Restriction) || theIsReqToKeepRLine)
1393         slin.Append(line);
1394     }
1395   }
1396
1397   for (Standard_Integer i = 1; i <= interii.NbPnts(); i++)
1398   {
1399     spnt.Append(interii.Point(i));
1400   }
1401
1402   if((theTyps1 == GeomAbs_Cylinder) && (theTyps2 == GeomAbs_Cylinder))
1403   {
1404     IntPatch_WLineTool::JoinWLines(slin, spnt, theS1, theS2, TolTang);
1405   }
1406
1407   if(isWLExist)
1408   {
1409     Bnd_Box2d aBx1, aBx2;
1410     const Standard_Real aU1F = theS1->FirstUParameter(),
1411                         aU1L = theS1->LastUParameter(),
1412                         aV1F = theS1->FirstVParameter(),
1413                         aV1L = theS1->LastVParameter(),
1414                         aU2F = theS2->FirstUParameter(),
1415                         aU2L = theS2->LastUParameter(),
1416                         aV2F = theS2->FirstVParameter(),
1417                         aV2L = theS2->LastVParameter();
1418     aBx1.Add(gp_Pnt2d(aU1F, aV1F));
1419     aBx1.Add(gp_Pnt2d(aU1L, aV1F));
1420     aBx1.Add(gp_Pnt2d(aU1L, aV1L));
1421     aBx1.Add(gp_Pnt2d(aU1F, aV1L));
1422     aBx2.Add(gp_Pnt2d(aU2F, aV2F));
1423     aBx2.Add(gp_Pnt2d(aU2L, aV2F));
1424     aBx2.Add(gp_Pnt2d(aU2L, aV2L));
1425     aBx2.Add(gp_Pnt2d(aU2F, aV2L));
1426
1427     aBx1.Enlarge(Precision::PConfusion());
1428     aBx2.Enlarge(Precision::PConfusion());
1429
1430     const Standard_Real
1431             anArrOfPeriod[4] = {theS1->IsUPeriodic()? theS1->UPeriod() : 0.0,
1432                                 theS1->IsVPeriodic()? theS1->VPeriod() : 0.0,
1433                                 theS2->IsUPeriodic()? theS2->UPeriod() : 0.0,
1434                                 theS2->IsVPeriodic()? theS2->VPeriod() : 0.0};
1435     IntPatch_WLineTool::ExtendTwoWLines(slin, theS1, theS2, TolTang,
1436                                         anArrOfPeriod, aBx1, aBx2);
1437   }
1438 }
1439
1440 //=======================================================================
1441 //function : GeomParamPerfom
1442 //purpose  : 
1443 //=======================================================================
1444 void IntPatch_Intersection::
1445   GeomParamPerfom(const Handle(Adaptor3d_HSurface)&  theS1,
1446                   const Handle(Adaptor3d_TopolTool)& theD1,
1447                   const Handle(Adaptor3d_HSurface)&  theS2,
1448                   const Handle(Adaptor3d_TopolTool)& theD2,
1449                   const Standard_Boolean isNotAnalitical,
1450                   const GeomAbs_SurfaceType typs1,
1451                   const GeomAbs_SurfaceType typs2)
1452 {
1453   IntPatch_ImpPrmIntersection interip;
1454   if (myIsStartPnt)
1455   {
1456     if (isNotAnalitical/*ts1 == 0*/)
1457       interip.SetStartPoint(myU1Start,myV1Start);
1458     else
1459       interip.SetStartPoint(myU2Start,myV2Start);
1460   }
1461
1462   if(theD1->DomainIsInfinite() && theD2->DomainIsInfinite())
1463   {
1464     Standard_Boolean IsPLInt = Standard_False;
1465     TColgp_SequenceOfPnt sop;
1466     gp_Vec v;
1467     FUN_PL_Intersection(theS1,typs1,theS2,typs2,IsPLInt,sop,v);
1468     
1469     if(IsPLInt)
1470     {
1471       if(sop.Length() > 0)
1472       {
1473         for(Standard_Integer ip = 1; ip <= sop.Length(); ip++)
1474         {
1475           gp_Lin lin(sop.Value(ip),gp_Dir(v));
1476           Handle(IntPatch_Line) gl = new IntPatch_GLine(lin,Standard_False);
1477           slin.Append(gl);
1478         }
1479
1480         done = Standard_True;
1481       }
1482       else
1483         done = Standard_False;
1484
1485       return;
1486     }
1487     else
1488     {
1489       Handle(Adaptor3d_HSurface) nS1 = theS1;
1490       Handle(Adaptor3d_HSurface) nS2 = theS2;
1491       FUN_TrimBothSurf(theS1,typs1,theS2,typs2,1.e+5,nS1,nS2);
1492       interip.Perform(nS1,theD1,nS2,theD2,myTolArc,myTolTang,myFleche,myUVMaxStep);
1493     }
1494   }
1495   else
1496     interip.Perform(theS1,theD1,theS2,theD2,myTolArc,myTolTang,myFleche,myUVMaxStep);
1497
1498   if (interip.IsDone()) 
1499   {
1500     done = Standard_True;
1501     empt = interip.IsEmpty();
1502
1503     if (!empt)
1504     {
1505       const Standard_Integer aNbLines = interip.NbLines();
1506       for(Standard_Integer i = 1; i <= aNbLines; i++)
1507       {
1508         if(interip.Line(i)->ArcType() != IntPatch_Walking)
1509           slin.Append(interip.Line(i));
1510       }
1511
1512       for(Standard_Integer i = 1; i <= aNbLines; i++)
1513       {
1514         if(interip.Line(i)->ArcType() == IntPatch_Walking)
1515           slin.Append(interip.Line(i));
1516       }
1517
1518       for (Standard_Integer i = 1; i <= interip.NbPnts(); i++)
1519         spnt.Append(interip.Point(i));
1520     }
1521   }
1522 }
1523
1524 void IntPatch_Intersection::Perform(const Handle(Adaptor3d_HSurface)&  S1,
1525                                     const Handle(Adaptor3d_TopolTool)& D1,
1526                                     const Handle(Adaptor3d_HSurface)&  S2,
1527                                     const Handle(Adaptor3d_TopolTool)& D2,
1528                                     const Standard_Real U1,
1529                                     const Standard_Real V1,
1530                                     const Standard_Real U2,
1531                                     const Standard_Real V2,
1532                                     const Standard_Real TolArc,
1533                                     const Standard_Real TolTang)
1534 {
1535   myTolArc = TolArc;
1536   myTolTang = TolTang;
1537   if(myFleche == 0.0) {
1538 #if DEBUG
1539     //cout<<" -- IntPatch_Intersection::myFleche fixe par defaut a 0.01 --"<<endl;
1540     //cout<<" -- Utiliser la Methode SetTolerances( ... ) "<<endl;
1541 #endif
1542     myFleche = 0.01;
1543   }
1544   if(myUVMaxStep==0.0) {
1545 #if DEBUG
1546     //cout<<" -- IntPatch_Intersection::myUVMaxStep fixe par defaut a 0.01 --"<<endl;
1547     //cout<<" -- Utiliser la Methode SetTolerances( ... ) "<<endl;
1548 #endif
1549     myUVMaxStep = 0.01;
1550   }
1551
1552   done = Standard_False;
1553   spnt.Clear();
1554   slin.Clear();
1555
1556   empt = Standard_True;
1557   tgte = Standard_False;
1558   oppo = Standard_False;
1559
1560   const GeomAbs_SurfaceType typs1 = S1->GetType();
1561   const GeomAbs_SurfaceType typs2 = S2->GetType();
1562   
1563   if(   typs1==GeomAbs_Plane 
1564      || typs1==GeomAbs_Cylinder
1565      || typs1==GeomAbs_Sphere
1566      || typs1==GeomAbs_Cone
1567      || typs2==GeomAbs_Plane 
1568      || typs2==GeomAbs_Cylinder
1569      || typs2==GeomAbs_Sphere
1570      || typs2==GeomAbs_Cone)
1571   {
1572     myIsStartPnt = Standard_True;
1573     myU1Start = U1; myV1Start = V1; myU2Start = U2; myV2Start = V2;
1574     Perform(S1,D1,S2,D2,TolArc,TolTang);
1575     myIsStartPnt = Standard_False;
1576   }
1577   else
1578   {
1579     IntPatch_PrmPrmIntersection interpp;
1580     interpp.Perform(S1,D1,S2,D2,U1,V1,U2,V2,TolTang,TolArc,myFleche,myUVMaxStep);
1581     if (interpp.IsDone())
1582     {
1583       done = Standard_True;
1584       tgte = Standard_False;
1585       empt = interpp.IsEmpty();
1586       const Standard_Integer nblm = interpp.NbLines();
1587       Standard_Integer i = 1;
1588       for (; i<=nblm; i++) slin.Append(interpp.Line(i));
1589     }
1590   }
1591
1592   for(Standard_Integer i = slin.Lower(); i <= slin.Upper(); i++)
1593   {
1594     Handle(IntPatch_WLine) aWL = Handle(IntPatch_WLine)::DownCast(slin.Value(i));
1595
1596     if(aWL.IsNull())
1597       continue;
1598
1599     if (!aWL->IsPurgingAllowed())
1600       continue;
1601
1602     Handle(IntPatch_WLine) aRW =
1603       IntPatch_WLineTool::ComputePurgedWLine(aWL, S1, S2, D1, D2);
1604
1605     if(aRW.IsNull())
1606       continue;
1607
1608     slin.InsertAfter(i, aRW);
1609     slin.Remove(i);
1610   }
1611 }
1612
1613 #ifdef DUMPOFIntPatch_Intersection
1614
1615 void IntPatch_Intersection__MAJ_R(Handle(Adaptor2d_HCurve2d) *R1,
1616                                   Handle(Adaptor2d_HCurve2d) *,
1617                                   int *NR1,
1618                                   int *,
1619                                   Standard_Integer nbR1,
1620                                   Standard_Integer ,
1621                                   const IntPatch_Point& VTX)
1622
1623   
1624   if(VTX.IsOnDomS1()) { 
1625     
1626     //-- long unsigned ptr= *((long unsigned *)(((Handle(Standard_Transient) *)(&(VTX.ArcOnS1())))));
1627     for(Standard_Integer i=0; i<nbR1;i++) { 
1628       if(VTX.ArcOnS1()==R1[i]) { 
1629         NR1[i]++;
1630         printf("\n ******************************");
1631         return;
1632       }
1633     }
1634     printf("\n R Pas trouvee  (IntPatch)\n");
1635     
1636   }
1637 }
1638 #endif
1639
1640 void IntPatch_Intersection::Dump(const Standard_Integer /*Mode*/,
1641                                  const Handle(Adaptor3d_HSurface)&  /*S1*/,
1642                                  const Handle(Adaptor3d_TopolTool)& /*D1*/,
1643                                  const Handle(Adaptor3d_HSurface)&  /*S2*/,
1644                                  const Handle(Adaptor3d_TopolTool)& /*D2*/) const 
1645
1646 #ifdef DUMPOFIntPatch_Intersection
1647   const int MAXR = 200;
1648   //-- ----------------------------------------------------------------------
1649   //--  construction de la liste des restrictions & vertex 
1650   //--
1651   int NR1[MAXR],NR2[MAXR];
1652   Handle(Adaptor2d_HCurve2d) R1[MAXR],R2[MAXR];
1653   Standard_Integer nbR1=0,nbR2=0;
1654   for(D1->Init();D1->More() && nbR1<MAXR; D1->Next()) { 
1655     R1[nbR1]=D1->Value(); 
1656     NR1[nbR1]=0;
1657     nbR1++;
1658   }
1659   for(D2->Init();D2->More() && nbR2<MAXR; D2->Next()) {
1660     R2[nbR2]=D2->Value();
1661     NR2[nbR2]=0;
1662     nbR2++;
1663   }
1664   
1665   printf("\nDUMP_INT:  ----empt:%2ud  tgte:%2ud  oppo:%2ud ---------------------------------",empt,tgte,empt);
1666   Standard_Integer i,nbr1,nbr2,nbgl,nbgc,nbge,nbgp,nbgh,nbl,nbr,nbg,nbw,nba;
1667   nbl=nbr=nbg=nbw=nba=nbgl=nbge=nbr1=nbr2=nbgc=nbgp=nbgh=0;
1668   nbl=NbLines();
1669   for(i=1;i<=nbl;i++) { 
1670     const Handle(IntPatch_Line)& line=Line(i);
1671     const IntPatch_IType IType=line->ArcType();
1672     if(IType == IntPatch_Walking) nbw++;
1673     else     if(IType == IntPatch_Restriction) { 
1674       nbr++;
1675       Handle(IntPatch_RLine) rlin (Handle(IntPatch_RLine)::DownCast (line));
1676       if(rlin->IsArcOnS1()) nbr1++;
1677       if(rlin->IsArcOnS2()) nbr2++;
1678     }
1679     else     if(IType == IntPatch_Analytic) nba++;
1680     else     { 
1681       nbg++; 
1682       if(IType == IntPatch_Lin) nbgl++;
1683       else if(IType == IntPatch_Circle) nbgc++;
1684       else if(IType == IntPatch_Parabola) nbgp++;
1685       else if(IType == IntPatch_Hyperbola) nbgh++;
1686       else if(IType == IntPatch_Ellipse) nbge++;
1687     }
1688   }
1689   
1690   
1691   printf("\nDUMP_INT:Lines:%2d Wlin:%2d Restr:%2d(On1:%2d On2:%2d) Ana:%2d Geom:%2d(L:%2d C:%2d E:%2d H:%2d P:%2d)",
1692          nbl,nbw,nbr,nbr1,nbr2,nba,nbg,nbgl,nbgc,nbge,nbgh,nbgp);
1693   
1694   IntPatch_LineConstructor LineConstructor(2);
1695   
1696   Standard_Integer nbllc=0;
1697   nbw=nbr=nbg=nba=0;
1698   Standard_Integer nbva,nbvw,nbvr,nbvg;
1699   nbva=nbvr=nbvw=nbvg=0;
1700   for (j=1; j<=nbl; j++) {
1701     Standard_Integer v,nbvtx;
1702     const Handle(IntPatch_Line)& intersLinej = Line(j);
1703     Standard_Integer NbLines;
1704     LineConstructor.Perform(SequenceOfLine(),intersLinej,S1,D1,S2,D2,1e-7);
1705     NbLines = LineConstructor.NbLines();
1706     
1707     for(Standard_Integer k=1;k<=NbLines;k++) { 
1708       nbllc++;
1709       const Handle(IntPatch_Line)& LineK = LineConstructor.Line(k);
1710       if (LineK->ArcType() == IntPatch_Analytic) { 
1711         Handle(IntPatch_ALine) alin (Handle(IntPatch_ALine)::DownCast (LineK));
1712         nbvtx=alin->NbVertex();
1713         nbva+=nbvtx;        nba++;
1714         for(v=1;v<=nbvtx;v++) { 
1715           IntPatch_Intersection__MAJ_R(R1,R2,NR1,NR2,nbR1,nbR2,alin->Vertex(v));
1716         }
1717       }
1718       else if (LineK->ArcType() == IntPatch_Restriction) {
1719         Handle(IntPatch_RLine) rlin (Handle(IntPatch_RLine)::DownCast (LineK));
1720         nbvtx=rlin->NbVertex();
1721         nbvr+=nbvtx;        nbr++;
1722         for(v=1;v<=nbvtx;v++) { 
1723           IntPatch_Intersection__MAJ_R(R1,R2,NR1,NR2,nbR1,nbR2,rlin->Vertex(v));
1724         }
1725       }
1726       else if (LineK->ArcType() == IntPatch_Walking) {
1727         Handle(IntPatch_WLine) wlin (Handle(IntPatch_WLine)::DownCast (LineK));
1728         nbvtx=wlin->NbVertex();
1729         nbvw+=nbvtx;        nbw++;
1730         for(v=1;v<=nbvtx;v++) { 
1731           IntPatch_Intersection__MAJ_R(R1,R2,NR1,NR2,nbR1,nbR2,wlin->Vertex(v));
1732         }
1733       }
1734       else { 
1735         Handle(IntPatch_GLine) glin (Handle(IntPatch_GLine)::DownCast (LineK));
1736         nbvtx=glin->NbVertex();
1737         nbvg+=nbvtx;        nbg++;
1738         for(v=1;v<=nbvtx;v++) { 
1739           IntPatch_Intersection__MAJ_R(R1,R2,NR1,NR2,nbR1,nbR2,glin->Vertex(v));
1740         }
1741       }
1742     }
1743   }
1744   printf("\nDUMP_LC :Lines:%2d WLin:%2d Restr:%2d Ana:%2d Geom:%2d",
1745          nbllc,nbw,nbr,nba,nbg);
1746   printf("\nDUMP_LC :vtx          :%2d     r:%2d    :%2d     :%2d",
1747          nbvw,nbvr,nbva,nbvg);
1748
1749   printf("\n");
1750
1751 #endif 
1752 }