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