0024585: Wrong pcurve of the section curve
[occt.git] / src / IntPatch / IntPatch_WLine.cxx
1 // Created on: 1991-05-27
2 // Created by: Isabelle GRIGNON
3 // Copyright (c) 1991-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
8 // This library is free software; you can redistribute it and / or modify it
9 // under the terms of the GNU Lesser General Public version 2.1 as published
10 // by the Free Software Foundation, with special exception defined in the file
11 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12 // distribution for complete text of the license and disclaimer of any warranty.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 #include <IntPatch_WLine.ixx>
18
19 #define DEBUG 0
20 #define DEBUGV 0
21
22 #include <IntSurf_PntOn2S.hxx>
23 #include <Precision.hxx>
24 #include <stdio.h>
25
26
27 IntPatch_WLine::IntPatch_WLine (const Handle(IntSurf_LineOn2S)& Line,
28                                 const Standard_Boolean Tang,
29                                 const IntSurf_TypeTrans Trans1,
30                                 const IntSurf_TypeTrans Trans2) :
31   IntPatch_Line(Tang,Trans1,Trans2),fipt(Standard_False),lapt(Standard_False),
32   hasArcOnS1(Standard_False),hasArcOnS2(Standard_False)
33 {
34   typ = IntPatch_Walking;
35   curv = Line;
36   Buv1.SetWhole();
37   Buv2.SetWhole();
38   Bxyz.SetWhole();
39   u1period=v1period=u2period=v2period=0.0;
40 }
41
42
43 IntPatch_WLine::IntPatch_WLine (const Handle(IntSurf_LineOn2S)& Line,
44                                 const Standard_Boolean Tang,
45                                 const IntSurf_Situation Situ1,
46                                 const IntSurf_Situation Situ2) :
47   IntPatch_Line(Tang,Situ1,Situ2),fipt(Standard_False),lapt(Standard_False),
48   hasArcOnS1(Standard_False),hasArcOnS2(Standard_False)
49 {
50   typ = IntPatch_Walking;
51   curv = Line;
52   Buv1.SetWhole();
53   Buv2.SetWhole();
54   Bxyz.SetWhole();
55   u1period=v1period=u2period=v2period=0.0;
56 }
57
58
59 IntPatch_WLine::IntPatch_WLine (const Handle(IntSurf_LineOn2S)& Line,
60                                 const Standard_Boolean Tang) :
61   IntPatch_Line(Tang),fipt(Standard_False),lapt(Standard_False),
62   hasArcOnS1(Standard_False),hasArcOnS2(Standard_False)
63 {
64   typ = IntPatch_Walking;
65   curv = Line;
66   Buv1.SetWhole();
67   Buv2.SetWhole();
68   Bxyz.SetWhole();
69   u1period=v1period=u2period=v2period=0.0;
70 }
71
72
73 void IntPatch_WLine::SetPoint(const Standard_Integer Index,
74                               const IntPatch_Point& thepoint)
75 {
76   curv->Value(Index,thepoint.PntOn2S());
77 }
78
79
80 Handle(IntSurf_LineOn2S) IntPatch_WLine::Curve() const
81
82   return(curv);
83 }
84
85 static void RecadreMemePeriode(Standard_Real& u1,Standard_Real& v1,
86                                Standard_Real& u2,Standard_Real& v2,
87                                const Standard_Real anu1,const Standard_Real anv1,
88                                const Standard_Real anu2,const Standard_Real anv2,
89                                const Standard_Real U1Period,const Standard_Real V1Period,
90                                const Standard_Real U2Period,const Standard_Real V2Period) { 
91   if(U1Period) { 
92     while(anu1-u1 > 0.8*U1Period) { u1+=U1Period; }
93     while(u1-anu1 > 0.8*U1Period) { u1-=U1Period; }
94   }
95   if(U2Period) { 
96     while(anu2-u2 > 0.8*U2Period) { u2+=U2Period; }
97     while(u2-anu2 > 0.8*U2Period) { u2-=U2Period; }
98   }
99   if(V1Period) { 
100     while(anv1-v1 > 0.8*V1Period) { v1+=V1Period; }
101     while(v1-anv1 > 0.8*V1Period) { v1-=V1Period; }
102   }
103   if(V2Period) { 
104     while(anv2-v2 > 0.8*V2Period) { v2+=V2Period; }
105     while(v2-anv2 > 0.8*V2Period) { v2-=V2Period; }
106   }
107
108 }
109
110 static void RecadreMemePeriode(IntSurf_PntOn2S& POn2S,const IntSurf_PntOn2S& RefPOn2S,
111                                const Standard_Real up1,
112                                const Standard_Real vp1,
113                                const Standard_Real up2,
114                                const Standard_Real vp2) { 
115   Standard_Real u1,v1,u2,v2,pu1,pv1,pu2,pv2;
116   POn2S.Parameters(u1,v1,u2,v2);
117   RefPOn2S.Parameters(pu1,pv1,pu2,pv2);
118   RecadreMemePeriode(u1,v1,u2,v2,pu1,pv1,pu2,pv2,up1,vp1,up2,vp2);
119   POn2S.SetValue(u1,v1,u2,v2);
120 }
121
122 static Standard_Boolean CompareVertexAndPoint(const gp_Pnt& V,const gp_Pnt& P,const Standard_Real& Tol) { 
123   return(V.Distance(P)<=Tol);
124 }
125
126 void IntPatch_WLine::SetPeriod(const Standard_Real pu1,
127                                const Standard_Real pv1,
128                                const Standard_Real pu2,
129                                const Standard_Real pv2) { 
130   u1period=pu1; v1period=pv1; u2period=pu2; v2period=pv2;
131 }
132 Standard_Real IntPatch_WLine::U1Period() const {    return(u1period); }
133 Standard_Real IntPatch_WLine::V1Period() const {    return(v1period); }
134 Standard_Real IntPatch_WLine::U2Period() const {    return(u2period); }
135 Standard_Real IntPatch_WLine::V2Period() const {    return(v2period); }
136
137
138 //------------------------------------------------------------------------
139 //--  En Entree : Une ligne de cheminement     +    Une Liste de Vetex
140 //--
141 //--   LineOn2S   :       1------2-------3-------4-----5---- ----nbp
142 //-- 
143 //--   Vertex     :   a     b c          d    e      f
144 //--
145 //--
146 //--  En Sortie 
147 //--
148 //--                  1--2-3-4--5--------6----7--8--9--10--------
149 //--
150 //--  avec   a de parametre 1 
151 //--         b              3
152 //--
153 //--   etc ...
154 //--
155 //--
156 //-- !!!!!!!!!!!!!!! On considere que deux vertex ne peuvent pas etre 
157 //-- !!!!!!!!!!!!!!!  a une distance inferieure a Tol
158 //------------------------------------------------------------------------
159 //--
160 //-- On Teste si la LineOn2S contient des points confondus. 
161 //-- Dans ce cas, on remove ces points.
162 //--
163 //------------------------------------------------------------------------
164
165 Standard_Boolean SameVtxRst(const IntPatch_Point& vtx1,const IntPatch_Point& vtx2) { 
166   if(vtx1.IsOnDomS1()) { 
167     if(vtx2.IsOnDomS1()) { 
168       if(vtx1.ArcOnS1() == vtx2.ArcOnS1()) { 
169         if(vtx1.ParameterOnArc1() == vtx2.ParameterOnArc1()) { 
170           
171         }
172         else { 
173           return(Standard_False);
174         }
175       }
176       else { 
177         return(Standard_False); 
178       }
179     }
180     else { 
181       return(Standard_False);
182     }
183   }
184   else { 
185     if(vtx2.IsOnDomS1()) { 
186       return(Standard_False);
187     }
188   }
189   if(vtx1.IsOnDomS2()) { 
190     if(vtx2.IsOnDomS2()) { 
191       if(vtx1.ArcOnS2() == vtx2.ArcOnS2()) { 
192         if(vtx1.ParameterOnArc2() == vtx2.ParameterOnArc2()) { 
193           
194         }
195         else { 
196           return(Standard_False);
197         }
198       }
199       else { 
200         return(Standard_False); 
201       }
202     }
203     else { 
204       return(Standard_False);
205     }
206   }
207   else {
208     if(vtx2.IsOnDomS2()) {
209       return(Standard_False);
210     }
211   }
212   return(Standard_True);
213 }
214
215
216 static Standard_Boolean CompareVerticesOnSurf(const IntPatch_Point& vtx1,
217                                               const IntPatch_Point& vtx2,
218                                               const Standard_Boolean onFirst)
219 {
220   Standard_Real u1,v1,u2,v2, tolU, tolV;
221   if (onFirst) {
222     vtx1.ParametersOnS1(u1,v1);
223     vtx2.ParametersOnS1(u2,v2);
224   }
225   else {
226     vtx1.ParametersOnS2(u1,v1);
227     vtx2.ParametersOnS2(u2,v2);
228   }
229   tolU = Precision::PConfusion();
230   tolV = Precision::PConfusion();
231   return (Abs(u1-u2) <= tolU && Abs(v1-v2) <= tolV);
232 }
233
234 inline Standard_Boolean CompareVerticesOnS1(const IntPatch_Point& vtx1, const IntPatch_Point& vtx2)
235 {return CompareVerticesOnSurf (vtx1, vtx2, Standard_True);}
236
237 inline Standard_Boolean CompareVerticesOnS2(const IntPatch_Point& vtx1, const IntPatch_Point& vtx2)
238 {return CompareVerticesOnSurf (vtx1, vtx2, Standard_False);}
239
240
241 void IntPatch_WLine::ComputeVertexParameters( const Standard_Real RTol,
242                                               const Standard_Boolean hasBeenAdded)
243 {
244   // MSV Oct 15, 2001: use tolerance of vertex instead of RTol where 
245   //                   it is possible
246
247   Standard_Integer i,j,k,nbvtx,nbponline;
248   Standard_Integer indicevertexonline;
249   Standard_Real    indicevertex;
250
251   Standard_Boolean APointDeleted = Standard_False;
252   //----------------------------------------------------------
253   //--     F i l t r e   s u r   r e s t r i c t i o n s   --
254   //----------------------------------------------------------
255   //-- deux vertex sur la meme restriction et seulement 
256   //-- sur celle ci ne doivent pas avoir le meme parametre
257   //--
258   Standard_Real Tol=RTol;
259   nbvtx = NbVertex();
260
261 #if DEBUGV  
262   cout<<"\n----------- avant ComputeVertexParameters -------------"<<endl;
263   for(i=1;i<=nbvtx;i++) { 
264     Vertex(i).Dump();
265     Standard_Real  polr = Vertex(i).ParameterOnLine();
266     Standard_Real pol = (Standard_Integer)polr;
267     if(pol>=1 && pol<=nbvtx) { 
268       cout<<"----> IntSurf_PntOn2S : "<<polr<<"  Pnt ("<<Vertex(pol).Value().X()
269         <<","<<Vertex(pol).Value().Y()
270           <<","<<Vertex(pol).Value().Z()<<")"<<endl;
271     }
272   }
273   cout<<"\n----------------------------------------------------------"<<endl;
274 #endif  
275
276   
277   //-- ----------------------------------------------------------------------
278   //-- Traitement des aretes de couture : On duplique les points situes
279   //-- sur des restrictions differentes
280   //-- 
281   //-- Phase Creation de nouveaux points sur S1 
282   Standard_Boolean encoreunefois;
283   do { 
284     nbvtx=NbVertex();
285     encoreunefois=Standard_False;
286     for(i=1; i<=nbvtx && encoreunefois==Standard_False; i++) { 
287       IntPatch_Point& VTXi   = svtx.ChangeValue(i);
288       for(j=1; j<=nbvtx && encoreunefois==Standard_False; j++) { 
289         if(i!=j) { 
290           IntPatch_Point& VTXj   = svtx.ChangeValue(j);
291           if(VTXi.ParameterOnLine() != VTXj.ParameterOnLine()) { 
292             Standard_Real d = VTXi.Value().Distance(VTXj.Value());
293             Standard_Real toli = VTXi.Tolerance();
294             Standard_Real tolj = VTXj.Tolerance();
295             Standard_Real maxtol = Max(toli,tolj);
296             // MSV Oct 30, 2001: compare in 2D space also;
297             //                   increase tolerances
298             if (d < maxtol ||
299                CompareVerticesOnS1(VTXi,VTXj) || CompareVerticesOnS2(VTXi,VTXj)) { 
300               //-- Creation Vtx (REF:S1(i)  S2(j))    (On Garde S1(i))
301               Standard_Real newtoli = Max (toli, tolj+d*1.01);
302               Standard_Real newtolj = Max (tolj, toli+d*1.01);
303               Standard_Boolean acreer=Standard_False;
304               if(VTXi.IsOnDomS1()) { 
305                 if(VTXj.IsOnDomS1()) { 
306                   if(VTXj.ArcOnS1() != VTXi.ArcOnS1()) { 
307                     acreer=Standard_True;
308                   }
309                 }
310                 else { 
311                   acreer=Standard_True;
312                 }
313               }
314               if(acreer) { 
315                 IntPatch_Point vtx;
316                 vtx = VTXj;
317                 vtx.SetArc(Standard_True,
318                            VTXi.ArcOnS1(),
319                            VTXi.ParameterOnArc1(),
320                            VTXi.TransitionLineArc1(),
321                            VTXi.TransitionOnS1());
322                 for(k=1; encoreunefois==Standard_False && k<=nbvtx; k++) { 
323                   const IntPatch_Point& VTXk   = svtx.Value(k);
324                   if(SameVtxRst(VTXk,vtx)) { 
325                     encoreunefois=Standard_True;
326                   }
327                 }
328                 if(encoreunefois==Standard_False) {
329                   VTXi.SetTolerance(newtoli);
330                   VTXj.SetTolerance(newtolj);
331                   vtx.SetTolerance(newtolj);
332                   svtx.Append(vtx);
333                   encoreunefois=Standard_True;
334                 }
335                 else { 
336                   encoreunefois=Standard_False;
337                 }
338               }
339               //-- -----------------------------------------------------
340               //-- Creation Vtx (REF:S2(i)  S1(j))    (On Garde S2(i))
341               acreer=Standard_False;
342               if(VTXi.IsOnDomS2()) { 
343                 if(VTXj.IsOnDomS2()) { 
344                   if(VTXj.ArcOnS2() != VTXi.ArcOnS2()) { 
345                     acreer=Standard_True;
346                   }
347                 }
348                 else { 
349                   acreer=Standard_True;
350                 }
351               }
352               if(acreer) { 
353                 IntPatch_Point vtx;
354                 vtx = VTXj;
355                 vtx.SetArc(Standard_False,
356                            VTXi.ArcOnS2(),
357                            VTXi.ParameterOnArc2(),
358                            VTXi.TransitionLineArc2(),
359                            VTXi.TransitionOnS2());
360                 for(k=1; encoreunefois==Standard_False && k<=nbvtx; k++) { 
361                   const IntPatch_Point& VTXk   = svtx.Value(k);
362                   if(SameVtxRst(VTXk,vtx)) { 
363                     encoreunefois=Standard_True;
364                   }
365                 }
366                 if(encoreunefois==Standard_False) {
367                   VTXi.SetTolerance(newtoli);
368                   VTXj.SetTolerance(newtolj);
369                   vtx.SetTolerance(newtolj);
370                   svtx.Append(vtx);
371                   encoreunefois=Standard_True;
372                 }
373                 else { 
374                   encoreunefois=Standard_False;
375                 }
376               }     
377             }
378           }
379         }
380       }
381     }
382   }
383   while(encoreunefois);
384   
385   
386
387   //-- ----------------------------------------------------------------------
388
389
390
391   do { 
392     APointDeleted = Standard_False;
393     for(i=1; (i<=nbvtx) && (APointDeleted==Standard_False) ;i++) { 
394       const IntPatch_Point& VTXi   = svtx.Value(i);
395       if(VTXi.Tolerance() > Tol)        Tol = VTXi.Tolerance(); //-- 9 oct 97 
396       if((VTXi.IsOnDomS1()==Standard_True) && (VTXi.IsOnDomS2()==Standard_False)) { 
397         for(j=1; (j<=nbvtx) && (APointDeleted==Standard_False) ;j++) {
398           if(i!=j) { 
399             const IntPatch_Point& VTXj   = svtx.Value(j);
400             if((VTXj.IsOnDomS1()==Standard_True) && (VTXj.IsOnDomS2()==Standard_False)) {
401               if(VTXi.ParameterOnLine() == VTXj.ParameterOnLine()) { 
402                 if(VTXi.ArcOnS1() == VTXj.ArcOnS1()) { 
403                   svtx.Remove(j);
404                   nbvtx--;
405                   if(lapt) { if(indl>=j) indl--; } 
406                   if(fipt) { if(indf>=j) indf--; } 
407                   APointDeleted = Standard_True;
408                 }
409               }
410             }
411           }
412         }
413       }
414     }
415   }
416   while(APointDeleted == Standard_True);
417
418
419   do { 
420     APointDeleted = Standard_False;
421     for(i=1; (i<=nbvtx) && (APointDeleted==Standard_False) ;i++) { 
422       const IntPatch_Point& VTXi   = svtx.Value(i);
423       if((VTXi.IsOnDomS2()==Standard_True) && (VTXi.IsOnDomS1()==Standard_False)) { 
424         for(j=1; (j<=nbvtx) && (APointDeleted==Standard_False) ;j++) {
425           if(i!=j) { 
426             const IntPatch_Point& VTXj   = svtx.Value(j);
427             if((VTXj.IsOnDomS2()==Standard_True) && (VTXj.IsOnDomS1()==Standard_False)) {
428               if(VTXi.ParameterOnLine() == VTXj.ParameterOnLine()) { 
429                 if(VTXi.ArcOnS2() == VTXj.ArcOnS2()) { 
430                   svtx.Remove(j);
431                   nbvtx--;
432                   if(lapt) { if(indl>=j) indl--; } 
433                   if(fipt) { if(indf>=j) indf--; } 
434                   APointDeleted = Standard_True;
435                 }
436               }
437             }
438           }
439         }
440       }
441     }
442   }
443   while(APointDeleted == Standard_True);
444         
445   nbvtx     = NbVertex();
446   nbponline = NbPnts();
447
448   //----------------------------------------------------
449   //-- On trie les Vertex 
450   Standard_Boolean SortIsOK;
451   do { 
452     SortIsOK = Standard_True;
453     for(i=2; i<=nbvtx; i++) { 
454       if(svtx.Value(i-1).ParameterOnLine()  > svtx.Value(i).ParameterOnLine()) { 
455         SortIsOK = Standard_False;
456         svtx.Exchange(i-1,i);
457       }
458     }
459   }
460   while(!SortIsOK);
461   
462   //----------------------------------------------------
463   //-- On detecte les points confondus dans la LineOn2S
464   Standard_Real dmini = Precision::Confusion();
465   dmini*=dmini;
466   for(i=2; i<=nbponline; i++) { 
467     const IntSurf_PntOn2S& aPnt1=curv->Value(i-1);
468     const IntSurf_PntOn2S& aPnt2=curv->Value(i);
469     Standard_Real d = (aPnt1.Value()).SquareDistance((aPnt2.Value()));
470     if(d < dmini) { 
471       curv->RemovePoint(i);
472       nbponline--;
473       //----------------------------------------------
474       //-- On recadre les Vertex si besoin 
475       //-- 
476       for(j=1; j<=nbvtx; j++) { 
477         indicevertex = svtx.Value(j).ParameterOnLine();
478         if(indicevertex >= i) {
479           svtx.ChangeValue(j).SetParameter(indicevertex-1.0);
480         }
481       }
482       //modified by NIZNHY-PKV Mon Feb 11 09:28:02 2002 f
483       i--;
484       //modified by NIZNHY-PKV Mon Feb 11 09:28:04 2002 t
485     }
486   }
487   //----------------------------------------------------
488   for(i=1; i<=nbvtx; i++) {
489     const gp_Pnt& P    = svtx.Value(i).Value();
490     Standard_Real vTol = svtx.Value(i).Tolerance();
491     
492     if(hasBeenAdded)
493     {
494       if(nbvtx == 2)
495       {
496         if(i == nbvtx)
497         {
498           indicevertex = curv->NbPoints();
499         }
500         else
501         {
502           indicevertex = svtx.Value(i).ParameterOnLine();
503         }
504       }
505       else
506       {
507         indicevertex = svtx.Value(i).ParameterOnLine();
508       }
509     }
510     else
511     {
512       indicevertex = svtx.Value(i).ParameterOnLine();
513     }
514     
515     indicevertexonline = (Standard_Integer)indicevertex;
516     //--------------------------------------------------
517     //-- On Compare le vertex avec les points de la ligne
518     //-- d indice   indicevertexOnLine-1
519     //--            indicevertexOnLine
520     //--            indicevertexOnLine+1
521     //--------------------------------------------------
522     if(indicevertexonline<1) { 
523       if(CompareVertexAndPoint(P,curv->Value(1).Value(),vTol)) {
524         //-------------------------------------------------------
525         //-- On remplace le point cheminement(1) par vertex(i)
526         //-- et   vertex(i) prend pour parametre 1
527         //-------------------------------------------------------
528         
529         IntSurf_PntOn2S POn2S = svtx.Value(i).PntOn2S();
530         RecadreMemePeriode(POn2S,curv->Value(1),U1Period(),V1Period(),U2Period(),V2Period());
531         curv->Value(1,POn2S);
532
533         //--curv->Value(1,svtx.Value(i).PntOn2S());
534         svtx.ChangeValue(i).SetParameter(1.0);
535       }
536       else { 
537         //-------------------------------------------------------
538         //-- On insere le point de cheminement Vertex(i)
539         //-- On recadre les parametres des autres vertex
540         //-------------------------------------------------------
541         IntSurf_PntOn2S POn2S = svtx.Value(i).PntOn2S();
542         RecadreMemePeriode(POn2S,curv->Value(1),U1Period(),V1Period(),U2Period(),V2Period());
543         curv->InsertBefore(1,POn2S);
544
545         //-- curv->InsertBefore(1,svtx.Value(i).PntOn2S());
546         svtx.ChangeValue(i).SetParameter(1.0);
547         nbponline++;
548         for(j=1;j<=nbvtx;j++) {
549           if(j!=1) { 
550             Standard_Real t = svtx.Value(j).ParameterOnLine();
551             if(t>1.0) { 
552               svtx.ChangeValue(j).SetParameter(t+1.0);
553             }
554           }
555         }
556       }
557     } //--- fin : if(indicevertexonline<1) 
558     else { 
559       //---------------------------------------------------------
560       //-- vertex(i)   ==   cheminement (indicevertexonline-1)
561       //-- vertex(i)   ==   cheminement (indicevertexonline)
562       //-- vertex(i)   ==   cheminement (indicevertexonline+1)
563       //---------------------------------------------------------
564       Standard_Boolean Substitution = Standard_False;
565       //-- for(k=indicevertexonline+1; !Substitution && k>=indicevertexonline-1;k--) {   avant le 9 oct 97 
566       for(k=indicevertexonline+1; k>=indicevertexonline-1;k--) { 
567         if(k>0 && k<=nbponline) { 
568           if(CompareVertexAndPoint(P,curv->Value(k).Value(),vTol)) {
569             //-------------------------------------------------------
570             //-- On remplace le point cheminement(k) 
571             //-- par vertex(i)  et vertex(i) prend pour parametre k
572             //-------------------------------------------------------
573             IntSurf_PntOn2S POn2S = svtx.Value(i).PntOn2S();
574             RecadreMemePeriode(POn2S,curv->Value(k),U1Period(),V1Period(),U2Period(),V2Period());
575             curv->Value(k,POn2S);
576             Standard_Real mu1,mv1,mu2,mv2;
577             POn2S.Parameters(mu1,mv1,mu2,mv2);
578             svtx.ChangeValue(i).SetParameter(k);
579             svtx.ChangeValue(i).SetParameters(mu1,mv1,mu2,mv2);
580             Substitution = Standard_True;
581           }
582         }
583       }
584
585       //Remove duplicating points
586       if (Substitution)
587       {
588         Standard_Integer ind_point;
589         for(ind_point = 2; (ind_point <= nbponline && nbponline > 2); ind_point++) { 
590           Standard_Real d = (curv->Value(ind_point-1).Value()).SquareDistance((curv->Value(ind_point).Value()));
591           if(d < dmini) { 
592             curv->RemovePoint(ind_point);
593             nbponline--;
594             //----------------------------------------------
595             //-- On recadre les Vertex si besoin 
596             //-- 
597             for(j=1; j<=nbvtx; j++) { 
598               indicevertex = svtx.Value(j).ParameterOnLine();
599               if(indicevertex >= ind_point) {
600                 svtx.ChangeValue(j).SetParameter(indicevertex-1.0);
601               }
602             }
603             //modified by NIZNHY-PKV Mon Feb 11 09:28:02 2002 f
604             ind_point--;
605             //modified by NIZNHY-PKV Mon Feb 11 09:28:04 2002 t
606           }
607         }
608       }
609       
610       //--static int deb6nov98=1;    Ne resout rien (a part partiellement BUC60409)
611       //--if(deb6nov98) { 
612       //--Substitution=Standard_True;
613       //-- }
614       
615       if(Substitution==Standard_False) { 
616         //-------------------------------------------------------
617         //-- On insere le point de cheminement Vertex(i)
618         //-- On recadre les parametres des autres vertex
619         //-------------------------------------------------------
620         IntSurf_PntOn2S POn2S = svtx.Value(i).PntOn2S();
621         if(indicevertexonline >= nbponline) { 
622           RecadreMemePeriode(POn2S,curv->Value(nbponline),U1Period(),V1Period(),U2Period(),V2Period());
623           curv->Add(POn2S);
624         }
625         else { 
626           RecadreMemePeriode(POn2S,curv->Value(indicevertexonline+1),U1Period(),V1Period(),U2Period(),V2Period());
627           curv->InsertBefore(indicevertexonline+1,POn2S);
628         }
629         //-- curv->InsertBefore(indicevertexonline+1,svtx.Value(i).PntOn2S());
630         svtx.ChangeValue(i).SetParameter(indicevertexonline+1);
631         nbponline++;
632         for(j=1;j<=nbvtx;j++) { 
633           if(j!=i) { 
634             Standard_Real t = svtx.Value(j).ParameterOnLine();
635             if(t>(Standard_Real)indicevertexonline) { 
636               svtx.ChangeValue(j).SetParameter(t+1.0);
637             }
638           }
639         }
640       } //-- Substitution
641     } //-- indicevertexonline>=1
642
643   } //-- boucle i sur vertex
644
645   
646   
647   
648   do {  
649     APointDeleted = Standard_False;
650     for(i=1; i<=nbvtx && (APointDeleted == Standard_False); i++) { 
651       const IntPatch_Point& VTX   = svtx.Value(i);      
652       for(j=1; j<=nbvtx && (APointDeleted == Standard_False) ; j++) { 
653         if(i!=j) { 
654           const IntPatch_Point& VTXM1 = svtx.Value(j);
655           
656           Standard_Boolean kill   = Standard_False;
657           Standard_Boolean killm1 = Standard_False;
658           if(VTXM1.ParameterOnLine() == VTX.ParameterOnLine()) { 
659             if(VTXM1.IsOnDomS1() && VTX.IsOnDomS1()) {  //-- OnS1    OnS1
660               if(VTXM1.ArcOnS1() == VTX.ArcOnS1()) {    //-- OnS1 == OnS1
661                 if(VTXM1.IsOnDomS2()) {                 //-- OnS1 == OnS1  OnS2  
662                   if(VTX.IsOnDomS2()==Standard_False) {   //-- OnS1 == OnS1  OnS2 PasOnS2
663                     kill=Standard_True;   
664                   }
665                   else {
666                     if(VTXM1.ArcOnS2() == VTX.ArcOnS2()) { //-- OnS1 == OnS1  OnS2 == OnS2
667                       kill=Standard_True;
668                     }
669                   }
670                 }
671                 else {                                  //-- OnS1 == OnS1  PasOnS2  
672                   if(VTX.IsOnDomS2()) {                 //-- OnS1 == OnS1  PasOnS2  OnS2
673                     killm1=Standard_True;
674                   }
675                 }
676               }
677             }
678             
679             if(!(kill || killm1)) {
680               if(VTXM1.IsOnDomS2() && VTX.IsOnDomS2()) {  //-- OnS2    OnS2
681                 if(VTXM1.ArcOnS2() == VTX.ArcOnS2()) {    //-- OnS2 == OnS2
682                   if(VTXM1.IsOnDomS1()) {                 //-- OnS2 == OnS2  OnS1  
683                     if(VTX.IsOnDomS1()==Standard_False) {   //-- OnS2 == OnS2  OnS1 PasOnS1
684                       kill=Standard_True;   
685                     }
686                     else {
687                       if(VTXM1.ArcOnS1() == VTX.ArcOnS1()) { //-- OnS2 == OnS2  OnS1 == OnS1
688                         kill=Standard_True;
689                       }
690                     }
691                   }
692                   else {                                  //-- OnS2 == OnS2  PasOnS1  
693                     if(VTX.IsOnDomS1()) {                 //-- OnS2 == OnS2  PasOnS1  OnS1
694                       killm1=Standard_True;
695                     }
696                   }
697                 }
698               }
699             }
700             if(kill) { 
701               APointDeleted = Standard_True;
702               svtx.Remove(i);
703               nbvtx--;
704             }
705             else if(killm1) { 
706               APointDeleted = Standard_True;
707               svtx.Remove(j);
708               nbvtx--; 
709             }
710           }
711         }
712       }
713     }
714   }
715   while(APointDeleted == Standard_True);
716   
717   do {  
718     SortIsOK = Standard_True;
719     for(i=2; i<=nbvtx && SortIsOK; i++) {
720       const IntPatch_Point& Pim1=svtx.Value(i-1);
721       const IntPatch_Point& Pii  =svtx.Value(i);
722       if(Pim1.ParameterOnLine()==Pii.ParameterOnLine()) { 
723         if(   (Pii.IsOnDomS1() == Standard_False)
724            && (Pii.IsOnDomS2() == Standard_False)) { 
725           SortIsOK = Standard_False;
726           svtx.Remove(i);
727           nbvtx--;
728         }
729         else {
730           if(   (Pim1.IsOnDomS1() == Standard_False)
731              && (Pim1.IsOnDomS2() == Standard_False)) { 
732             SortIsOK = Standard_False;
733             svtx.Remove(i-1);
734             nbvtx--;
735           }       
736         }
737       }
738     }
739   }
740   while(!SortIsOK);
741   //-- ----------------------------------------------------------------------------
742   //-- On ajoute les vertex de debut et de fin de ligne s il ne sont pas presents.
743   //-- 
744   //-- Existe t il un vertex de debut de ligne, de fin .
745   //--
746   //-- Si Besoin : il faudra dedoubler les points de debut et de fin sur les periodiques ??????
747
748
749
750   
751   Standard_Boolean bFirst = Standard_False;
752   Standard_Boolean bLast  = Standard_False;
753   nbponline = NbPnts();
754   for(i=1;i<=nbvtx;i++) { 
755     Standard_Real pol = svtx.Value(i).ParameterOnLine();
756     if(pol==1.0)       {
757       bFirst = fipt = Standard_True;
758       indf   = i;
759     }
760     if(pol==nbponline) {
761       bLast = lapt = Standard_True;
762       indl  = i;
763     }
764   }
765   if(bFirst == Standard_False) { 
766     Standard_Real pu1,pv1,pu2,pv2;
767     Standard_Boolean vtxfound = Standard_False;
768     IntPatch_Point vtx;
769     curv->Value(1).Parameters(pu1,pv1,pu2,pv2);
770     for(i=1;
771         (vtxfound==Standard_False) && (i<=nbvtx);i++) { 
772       const IntPatch_Point&  V = svtx.Value(i);
773       Standard_Real vTol = V.Tolerance();
774       if(CompareVertexAndPoint(V.Value(),curv->Value(1).Value(),vTol)) { 
775         vtx = V;
776         vtx.SetParameters(pu1,pv1,pu2,pv2);
777         vtxfound = Standard_True;
778       }
779     }
780     if(vtxfound == Standard_False)  { 
781       vtx.SetValue(curv->Value(1).Value(),Tol,Standard_False);
782       vtx.SetParameters(pu1,pv1,pu2,pv2);
783     }
784     vtx.SetParameter(1);
785     svtx.Prepend(vtx);    nbvtx++;
786     fipt = Standard_True;
787     indf = 1;
788   }
789   if(bLast == Standard_False) { 
790     Standard_Real pu1,pv1,pu2,pv2;
791     Standard_Boolean vtxfound = Standard_False;    
792     IntPatch_Point vtx;
793     curv->Value(nbponline).Parameters(pu1,pv1,pu2,pv2);   
794     for(i=1;
795         (vtxfound==Standard_False) && (i<=nbvtx);i++) { 
796       const IntPatch_Point&  V = svtx.Value(i);
797       Standard_Real vTol = V.Tolerance();
798       if(CompareVertexAndPoint(V.Value(),curv->Value(nbponline).Value(),vTol)) { 
799         vtx = V;
800         vtx.SetParameters(pu1,pv1,pu2,pv2);
801         vtxfound = Standard_True;
802       }
803     }
804     if(vtxfound == Standard_False)  {     
805       vtx.SetValue(curv->Value(nbponline).Value(),Tol,Standard_False);
806       vtx.SetParameters(pu1,pv1,pu2,pv2);
807     }
808     vtx.SetParameter(nbponline);
809     svtx.Append(vtx); nbvtx++;
810     lapt = Standard_True;
811     indl = nbvtx; 
812   }
813   
814
815
816
817   //--------------------------------------------------------------
818   //-- ** Detection de points trouves sur une meme restriction 
819   //--    avec la meme transition et avec des params on line 
820   //--    voisins.   
821   //-- ** Dans ce cas (-> donnerait un baillemenmt) on supprime 
822   //--    le point 'intermediaire'. 
823   //-- ** (exemple Vtx(1)  .....  Vtx(204) Vtx(205))
824   //--    on supprime le Vtx(204)
825   //-- ** (exemple Vtx(1) Vtx(2)  .....  Vtx(205))
826   //--    on supprime le Vtx(2)
827   //-- ** (exemple Vtx(1)  ...  Vtx(100) Vtx(101) ... Vtx(205))
828   //--    on supprime le Vtx(100)  (Vtx(100)et101 sur m restr)
829
830   //--------------------------------------------------------------
831   nbvtx = NbVertex();
832   do { 
833     APointDeleted = Standard_False;
834     for(i=1; (i<=nbvtx) && (APointDeleted==Standard_False) ;i++) { 
835       const IntPatch_Point& VTXi   = svtx.Value(i);
836       if((VTXi.IsOnDomS1()==Standard_True) && (VTXi.IsOnDomS2()==Standard_False)) { 
837         for(j=1; (j<=nbvtx) && (APointDeleted==Standard_False) ;j++) {
838           if(i!=j) { 
839             const IntPatch_Point& VTXj   = svtx.Value(j);
840             if((VTXj.IsOnDomS1()==Standard_True) && (VTXj.IsOnDomS2()==Standard_False)) {
841               if(   (VTXi.ParameterOnLine() == VTXj.ParameterOnLine()+1)
842                  || (VTXi.ParameterOnLine() == VTXj.ParameterOnLine()-1)) { 
843                 if(VTXi.ArcOnS1() == VTXj.ArcOnS1()) { 
844                   IntSurf_Transition t1 = VTXi.TransitionLineArc1();
845                   IntSurf_Transition t2 = VTXj.TransitionLineArc1();
846                   if(t1.TransitionType()==t2.TransitionType()) { 
847                     if((VTXj.ParameterOnLine()!=1) && (VTXj.ParameterOnLine()!=NbPnts())) {   
848                       svtx.Remove(j);
849                       nbvtx--;
850                       if(lapt) { if(indl>=j) indl--; } 
851                       if(fipt) { if(indf>=j) indf--; } 
852                       APointDeleted = Standard_True;
853                     }
854                   }
855                 }
856               }
857             }
858           }
859         }
860       }
861     }
862   }
863   
864   //-- meme traitement sur les restrictions du second shape
865
866   while(APointDeleted == Standard_True);
867   nbvtx = NbVertex();
868   do { 
869     APointDeleted = Standard_False;
870     for(i=1; (i<=nbvtx) && (APointDeleted==Standard_False) ;i++) { 
871       const IntPatch_Point& VTXi   = svtx.Value(i);
872       if((VTXi.IsOnDomS1()==Standard_False) && (VTXi.IsOnDomS2()==Standard_True)) { 
873         for(j=1; (j<=nbvtx) && (APointDeleted==Standard_False) ;j++) {
874           if(i!=j) { 
875             const IntPatch_Point& VTXj   = svtx.Value(j);
876             if((VTXj.IsOnDomS1()==Standard_False) && (VTXj.IsOnDomS2()==Standard_True)) {
877               if(   (VTXi.ParameterOnLine() == VTXj.ParameterOnLine()+1)
878                  || (VTXi.ParameterOnLine() == VTXj.ParameterOnLine()-1)) { 
879                 if(VTXi.ArcOnS2() == VTXj.ArcOnS2()) { 
880                   IntSurf_Transition t1 = VTXi.TransitionLineArc2();
881                   IntSurf_Transition t2 = VTXj.TransitionLineArc2();
882                   if(t1.TransitionType()==t2.TransitionType()) { 
883                     if((VTXj.ParameterOnLine()!=1) && (VTXj.ParameterOnLine()!=NbPnts())) {   
884                       svtx.Remove(j);
885                       nbvtx--;
886                       if(lapt) { if(indl>=j) indl--; } 
887                       if(fipt) { if(indf>=j) indf--; } 
888                       APointDeleted = Standard_True;
889                     }
890                   }
891                 }
892               }
893             }
894           }
895         }
896       }
897     }
898   }
899   while(APointDeleted == Standard_True);
900   //--------------------------------------------------------------
901
902   //--------------------------------------------------------------
903   //-- dans le cas de lignes periodiques du type : 
904   //--    Un point sur restriction R1 de param p1  -> P3d1   Vtx1
905   //--    Un point sur restriction R2 de param p2  -> P3d1   Vtx2
906   //--    
907   //--    Un point sur restriction R1 de param p1  -> P3d1   Vtx3
908   //--    pas de point sur R2 
909   //--
910   //-- On doit dans ce cas creer un nouveau Vtx4 = Vtx3 sur la 
911   //-- restriction R2
912   //--
913   //-- Ce cas se produit qd on a corrige un baillement avec le filtre
914   //-- precedent
915   //-- 
916   
917
918
919
920   
921
922   nbvtx = NbVertex();
923   do { 
924     SortIsOK = Standard_True;
925     for(i=2; i<=nbvtx; i++) { 
926       if(svtx.Value(i-1).ParameterOnLine()  > svtx.Value(i).ParameterOnLine()) { 
927         SortIsOK = Standard_False;
928         svtx.Exchange(i-1,i);
929       }
930     }
931   }
932   while(!SortIsOK);
933   
934   //-- Dump();
935
936 #if DEBUGV  
937   cout<<"\n----------- apres ComputeVertexParameters -------------"<<endl;
938   for(i=1;i<=nbvtx;i++) { 
939     Vertex(i).Dump();
940     Standard_Real  polr = Vertex(i).ParameterOnLine();
941     Standard_Real pol = (Standard_Integer)polr;
942     if(pol>=1 && pol<=nbvtx) { 
943       cout<<"----> IntSurf_PntOn2S : "<<polr<<"  Pnt ("<<Vertex(pol).Value().X()
944         <<","<<Vertex(pol).Value().Y()
945           <<","<<Vertex(pol).Value().Z()<<")"<<endl;
946     }
947   }
948   cout<<"\n----------------------------------------------------------"<<endl;
949 #endif  
950
951
952 }
953
954
955
956 Standard_Boolean IntPatch_WLine::IsOutSurf1Box(const gp_Pnt2d& P1uv)  { 
957   if(Buv1.IsWhole()) {
958     Standard_Integer n=NbPnts();
959     Standard_Real pu1,pu2,pv1,pv2;
960     Buv1.SetVoid();
961     for(Standard_Integer i=1;i<=n;i++) { 
962       curv->Value(i).Parameters(pu1,pv1,pu2,pv2);
963       Buv1.Add(gp_Pnt2d(pu1,pv1));
964     }
965     Buv1.Get(pu1,pv1,pu2,pv2);
966     pu2-=pu1;
967     pv2-=pv1;
968     if(pu2>pv2) { 
969       Buv1.Enlarge(pu2*0.01);
970     }
971     else { 
972       Buv1.Enlarge(pv2*0.01);
973     }
974   }
975   Standard_Boolean out=Buv1.IsOut(P1uv);
976   return(out);
977 }
978
979 Standard_Boolean IntPatch_WLine::IsOutSurf2Box(const gp_Pnt2d& P2uv)  { 
980   if(Buv2.IsWhole()) { 
981     Standard_Integer n=NbPnts();
982     Standard_Real pu1,pu2,pv1,pv2;
983     Buv2.SetVoid();
984     for(Standard_Integer i=1;i<=n;i++) { 
985       curv->Value(i).Parameters(pu1,pv1,pu2,pv2);
986       Buv2.Add(gp_Pnt2d(pu2,pv2));
987     }
988     Buv2.Get(pu1,pv1,pu2,pv2);
989     pu2-=pu1;
990     pv2-=pv1;
991     if(pu2>pv2) { 
992       Buv2.Enlarge(pu2*0.01);
993     }
994     else { 
995       Buv2.Enlarge(pv2*0.01);
996     }    
997   }
998   Standard_Boolean out=Buv2.IsOut(P2uv);
999   return(out);
1000 }
1001
1002 Standard_Boolean IntPatch_WLine::IsOutBox(const gp_Pnt& Pxyz)  { 
1003   if(Bxyz.IsWhole()) { 
1004     Standard_Integer n=NbPnts();
1005     Bxyz.SetVoid();
1006     for(Standard_Integer i=1;i<=n;i++) { 
1007       gp_Pnt P=curv->Value(i).Value();
1008       Bxyz.Add(P);
1009     }
1010     Standard_Real x0,y0,z0,x1,y1,z1;
1011     Bxyz.Get(x0,y0,z0,x1,y1,z1);
1012     x1-=x0; y1-=y0; z1-=z0;
1013     if(x1>y1) {
1014       if(x1>z1) {
1015         Bxyz.Enlarge(x1*0.01);
1016       }
1017       else { 
1018         Bxyz.Enlarge(z1*0.01);
1019       }
1020     }
1021     else { 
1022       if(y1>z1) { 
1023         Bxyz.Enlarge(y1*0.01);
1024       }
1025       else { 
1026         Bxyz.Enlarge(z1*0.01);
1027       }
1028     }
1029   }
1030   Standard_Boolean out=Bxyz.IsOut(Pxyz);
1031   return(out);
1032 }
1033
1034
1035 Standard_Boolean IntPatch_WLine::HasArcOnS1() const  {
1036   return(hasArcOnS1);
1037 }
1038
1039 void IntPatch_WLine::SetArcOnS1(const Handle(Adaptor2d_HCurve2d)& A) { 
1040   hasArcOnS1=Standard_True;
1041   theArcOnS1=A;
1042 }
1043
1044 const Handle(Adaptor2d_HCurve2d)& IntPatch_WLine::GetArcOnS1() const  { 
1045   return(theArcOnS1);
1046 }
1047
1048 Standard_Boolean IntPatch_WLine::HasArcOnS2() const  {
1049   return(hasArcOnS2);
1050 }
1051
1052 void IntPatch_WLine::SetArcOnS2(const Handle(Adaptor2d_HCurve2d)& A) { 
1053   hasArcOnS2=Standard_True;
1054   theArcOnS2=A;
1055 }
1056
1057 const Handle(Adaptor2d_HCurve2d)& IntPatch_WLine::GetArcOnS2() const  { 
1058   return(theArcOnS2);
1059 }
1060
1061
1062 void IntPatch_WLine::Dump() const { 
1063   
1064   cout<<" ----------- D u m p    I n t P a t c h  _  W L i n e  --------------"<<endl;
1065   Standard_Integer i;
1066   Standard_Integer nbp = NbPnts();
1067   printf("Num    [X  Y  Z]     [U1  V1]   [U2  V2]\n");
1068 //  for(Standard_Integer i=1;i<=nbp;i++) { 
1069   for(i=1;i<=nbp;i++) {
1070     Standard_Real u1,v1,u2,v2;
1071     Point(i).Parameters(u1,v1,u2,v2);
1072     printf("%4d  [%+5.8e %+5.8e %+5.8e]  [%+5.8e %+5.8e]  [%+5.8e %+5.8e]\n",
1073            i,
1074            Point(i).Value().X(),
1075            Point(i).Value().Y(),
1076            Point(i).Value().Z(),
1077            u1,v1,u2,v2);
1078     
1079     
1080     //cout<<"IntSurf_PntOn2S : "<<i<<"  Pnt ("<<curv->Value(i).Value().X()
1081     //  <<","<<curv->Value(i).Value().Y()
1082     //  <<","<<curv->Value(i).Value().Z()<<")"<<endl;
1083     //cout<<"                :   u1("<<u1<<")   v1("<<v1<<")   u2("<<u2<<")   v2("<<v2<<")"<<endl; 
1084   }
1085   nbp = NbVertex();
1086   for(i=1;i<=nbp;i++) { 
1087     Vertex(i).Dump();
1088     Standard_Real  polr = Vertex(i).ParameterOnLine();
1089     Standard_Integer pol = (Standard_Integer)polr;
1090     if(pol>=1 && pol<=nbp) { 
1091       cout<<"----> IntSurf_PntOn2S : "<<polr<<"  Pnt ("<<Vertex(pol).Value().X()
1092         <<","<<Vertex(pol).Value().Y()
1093           <<","<<Vertex(pol).Value().Z()<<")"<<endl;
1094     }
1095   }
1096   cout<<"\n----------------------------------------------------------"<<endl;  
1097 }
1098