7fd59977 |
1 | // File: IntPatch_ImpImpIntersection_0.gxx |
2 | // Created: Thu May 7 08:47:45 1992 |
3 | // Author: Jacques GOUSSARD |
4 | // Copyright: OPEN CASCADE 1992 |
5 | |
6 | // Modified by skv - Thu Jan 15 15:57:15 2004 OCC4455 |
7 | |
8 | static void PutPointsOnLine(const Handle(Adaptor3d_HSurface)& S1, |
9 | const Handle(Adaptor3d_HSurface)& S2, |
10 | const IntPatch_SequenceOfPathPointOfTheSOnBounds&, |
11 | const IntPatch_SequenceOfLine&, |
12 | const Standard_Boolean, |
13 | const Handle(Adaptor3d_TopolTool)&, |
14 | const IntSurf_Quadric&, |
15 | const IntSurf_Quadric&, |
16 | const Standard_Boolean, |
17 | const Standard_Real); |
18 | |
19 | static Standard_Boolean MultiplePoint (const IntPatch_SequenceOfPathPointOfTheSOnBounds&, |
20 | const Handle(Adaptor3d_TopolTool)&, |
21 | const IntSurf_Quadric&, |
22 | const gp_Vec&, |
23 | const IntPatch_SequenceOfLine&, |
24 | TColStd_Array1OfInteger&, |
25 | TColStd_Array1OfInteger&, |
26 | const Standard_Integer, |
27 | const Standard_Boolean); |
28 | |
29 | static Standard_Boolean PointOnSecondDom (const IntPatch_SequenceOfPathPointOfTheSOnBounds&, |
30 | const Handle(Adaptor3d_TopolTool)&, |
31 | const IntSurf_Quadric&, |
32 | const gp_Vec&, |
33 | const gp_Vec&, |
34 | const Handle(IntPatch_Line)&, |
35 | TColStd_Array1OfInteger&, |
36 | const Standard_Integer); |
37 | |
38 | static Standard_Boolean SingleLine (const gp_Pnt&, |
39 | const Handle(IntPatch_Line)&, |
40 | const Standard_Real, |
41 | Standard_Real&, |
42 | gp_Vec&); |
43 | |
44 | |
45 | static Standard_Boolean FindLine (gp_Pnt&, |
46 | const IntPatch_SequenceOfLine&, |
47 | const Standard_Real, |
48 | Standard_Real&, |
49 | gp_Vec&, |
50 | Standard_Integer&, |
51 | Standard_Integer, |
52 | const Handle(Adaptor2d_HCurve2d)&, |
53 | Standard_Real&, |
54 | gp_Pnt& pointonarc, |
55 | const IntSurf_Quadric&); |
56 | |
57 | static void ProcessSegments (const IntPatch_SequenceOfSegmentOfTheSOnBounds&, |
58 | IntPatch_SequenceOfLine&, |
59 | const IntSurf_Quadric&, |
60 | const IntSurf_Quadric&, |
61 | const Standard_Boolean, |
62 | const Standard_Real); |
63 | |
64 | static void ProcessRLine (IntPatch_SequenceOfLine&, |
65 | #ifndef DEB |
66 | const IntSurf_Quadric&, |
67 | const IntSurf_Quadric&, |
68 | #else |
69 | const Handle(Adaptor3d_HSurface)&, |
70 | const Handle(Adaptor3d_HSurface)&, |
71 | #endif |
72 | const Standard_Real); |
73 | |
74 | |
75 | |
76 | |
77 | //-- le calcul de dist est completement faux ds la routine ci dessous a revoir (lbr le 18 nov 97) |
78 | Standard_Boolean IntersectionWithAnArc(gp_Pnt& PSurf, |
79 | const Handle(IntPatch_ALine)& alin, |
80 | Standard_Real& para, |
81 | const Handle(Adaptor2d_HCurve2d)& thearc, |
82 | Standard_Real& _theparameteronarc, |
83 | gp_Pnt& thepointonarc, |
84 | const IntSurf_Quadric& QuadSurf, |
85 | const Standard_Real u0alin, |
86 | const Standard_Real u1alin, |
87 | Standard_Real& actualdist) { |
88 | Standard_Real dtheta,theta; |
89 | #ifdef DEB |
90 | //Standard_Real u,v,A,B,C,cost,sint,sign; |
91 | #endif |
92 | //-- recherche bete du point le plus proche de thearc->Value(...) |
93 | dtheta = (u1alin-u0alin)*0.01; |
94 | Standard_Real du=0.000000001; |
95 | Standard_Real distmin = RealLast(); |
96 | #ifndef DEB |
97 | Standard_Real thetamin = 0.; |
98 | #else |
99 | Standard_Real thetamin; |
100 | #endif |
101 | Standard_Real theparameteronarc = _theparameteronarc; |
102 | for(Standard_Real _theta=u0alin+dtheta; _theta<=u1alin-dtheta; _theta+=dtheta) { |
103 | gp_Pnt P=alin->Value(_theta); |
104 | Standard_Real d=P.Distance(PSurf); |
105 | if(d<distmin) { |
106 | thetamin=_theta; |
107 | distmin=d; |
108 | } |
109 | } |
110 | #ifndef DEB |
111 | Standard_Real bestpara =0., besttheta =0., bestdist =0., distinit =0. ; |
112 | #else |
113 | Standard_Real bestpara,besttheta,bestdist,distinit; |
114 | #endif |
115 | //-- Distance initiale |
116 | { |
117 | gp_Pnt pp0 = alin->Value(thetamin); |
118 | Standard_Real ua0,va0; |
119 | QuadSurf.Parameters(pp0,ua0,va0); |
120 | gp_Pnt2d p2d; |
121 | gp_Vec2d d2d; |
122 | thearc->D1(theparameteronarc,p2d,d2d); |
123 | gp_Vec2d PaPr(gp_Pnt2d(ua0,va0),p2d); |
124 | distinit=PaPr.Magnitude(); |
125 | } |
126 | theta = thetamin; |
127 | //-- recherche a partir de theta et theparameteronarc |
128 | Standard_Boolean cpasok=Standard_True; |
129 | Standard_Integer nbiter=0; |
130 | Standard_Real drmax = (thearc->LastParameter() - thearc->FirstParameter())*0.05; |
131 | Standard_Real damax = (u1alin-u0alin)*0.05; |
132 | |
133 | |
134 | |
135 | bestdist = RealLast(); |
136 | |
137 | do { |
138 | Standard_Real ua0,va0,ua1,va1; |
139 | //-- alin->Curve().InternalUVValue(theta,ua0,va0,A,B,C,cost,sint,sign); |
140 | //-- alin->Curve().InternalUVValue(theta+du,ua1,va1,A,B,C,cost,sint,sign); |
141 | gp_Pnt pp0 = alin->Value(theta); |
142 | gp_Pnt pp1 = alin->Value(theta+du); |
143 | QuadSurf.Parameters(pp0,ua0,va0); |
144 | QuadSurf.Parameters(pp1,ua1,va1); |
145 | |
146 | |
147 | gp_Vec2d D1a((ua1-ua0)/du,(va1-va0)/du); |
148 | gp_Pnt2d p2d; |
149 | gp_Vec2d d2d; |
150 | thearc->D1(theparameteronarc,p2d,d2d); |
151 | gp_Vec2d PaPr(gp_Pnt2d(ua0,va0),p2d); |
152 | |
153 | Standard_Real pbd=PaPr.Magnitude(); |
154 | if(bestdist>pbd) { |
155 | bestdist = pbd; |
156 | bestpara = theparameteronarc; |
157 | besttheta = theta; |
158 | } |
159 | |
160 | D1a.SetCoord(-D1a.X(),-D1a.Y()); |
161 | |
162 | Standard_Real d = D1a.X() * d2d.Y() - D1a.Y() * d2d.X(); |
163 | |
164 | Standard_Real da = (-PaPr.X())* d2d.Y() - (-PaPr.Y()) * d2d.X(); |
165 | Standard_Real dr = D1a.X() * (-PaPr.Y()) - D1a.Y() * (-PaPr.X()); |
166 | if(Abs(d)>1e-15) { |
167 | da/=d; |
168 | dr/=d; |
169 | } |
170 | else { |
171 | if(Abs(PaPr.X())>Abs(PaPr.Y())) { |
172 | Standard_Real xx=PaPr.X(); |
173 | xx*=0.5; |
174 | if(D1a.X()) { |
175 | da = -xx/D1a.X(); |
176 | } |
177 | if(d2d.X()) { |
178 | dr = -xx/d2d.X(); |
179 | } |
180 | } |
181 | else { |
182 | Standard_Real yy=PaPr.Y(); |
183 | yy*=0.5; |
184 | if(D1a.Y()) { |
185 | da = -yy/D1a.Y(); |
186 | } |
187 | if(d2d.Y()) { |
188 | dr = -yy/d2d.Y(); |
189 | } |
190 | } |
191 | } |
192 | //-- Standard_Real da = -PaPr.Dot(D1a); |
193 | //-- Standard_Real dr = -PaPr.Dot(d2d); |
194 | |
195 | if(da<-damax) da=-damax; |
196 | else if(da>damax) da=damax; |
197 | if(dr<-drmax) dr=-drmax; |
198 | else if(dr>drmax) dr=drmax; |
199 | |
200 | if(Abs(da)<1e-10 && Abs(dr)<1e-10) { |
201 | para = theta; |
202 | PSurf = alin->Value(para); |
203 | _theparameteronarc=theparameteronarc; |
204 | thepointonarc = alin->Value(para); |
205 | cpasok=Standard_False; |
206 | //-- printf("\nt:%d",nbiter); |
207 | actualdist = bestdist; |
208 | return(Standard_True); |
209 | } |
210 | else { |
211 | theta+=da; |
212 | theparameteronarc+=dr; |
213 | if( theparameteronarc>thearc->LastParameter() ) { |
214 | theparameteronarc = thearc->LastParameter(); |
215 | } |
216 | if( theparameteronarc<thearc->FirstParameter() ) { |
217 | theparameteronarc = thearc->FirstParameter(); |
218 | } |
219 | if( theta < u0alin) { |
220 | theta = u0alin; |
221 | } |
222 | if( theta > u1alin-du) { |
223 | theta = u1alin-du-du; |
224 | } |
225 | } |
226 | nbiter++; |
227 | } |
228 | while(cpasok && nbiter<20); |
229 | if(bestdist < distinit) { |
230 | para = besttheta; |
231 | PSurf = alin->Value(para); |
232 | _theparameteronarc=bestpara; |
233 | thepointonarc = alin->Value(para); |
234 | //-- printf("\nT:%d",nbiter); |
235 | actualdist=bestdist; |
236 | return(Standard_True); |
237 | } |
238 | //-- printf("\nF:%d",nbiter); |
239 | return(Standard_False); |
240 | } |
241 | |
242 | |
243 | |
244 | |
245 | |
246 | //-- ====================================================================== |
247 | static void Recadre(const Handle(Adaptor3d_HSurface)& myHS1, |
248 | const Handle(Adaptor3d_HSurface)& myHS2, |
249 | Standard_Real& u1, |
250 | Standard_Real& v1, |
251 | Standard_Real& u2, |
252 | Standard_Real& v2) { |
253 | Standard_Real f,l,lmf,fpls2; |
254 | GeomAbs_SurfaceType typs1 = myHS1->GetType(); |
255 | GeomAbs_SurfaceType typs2 = myHS2->GetType(); |
256 | |
257 | Standard_Boolean myHS1IsUPeriodic,myHS1IsVPeriodic; |
258 | switch (typs1) { |
259 | case GeomAbs_Cylinder: |
260 | case GeomAbs_Cone: |
261 | case GeomAbs_Sphere: |
262 | { |
263 | myHS1IsUPeriodic = Standard_True; |
264 | myHS1IsVPeriodic = Standard_False; |
265 | break; |
266 | } |
267 | case GeomAbs_Torus: |
268 | { |
269 | myHS1IsUPeriodic = myHS1IsVPeriodic = Standard_True; |
270 | break; |
271 | } |
272 | default: |
273 | { |
274 | //-- Le cas de biparametrees periodiques est gere en amont |
275 | myHS1IsUPeriodic = myHS1IsVPeriodic = Standard_False; |
276 | break; |
277 | } |
278 | } |
279 | |
280 | Standard_Boolean myHS2IsUPeriodic,myHS2IsVPeriodic; |
281 | switch (typs2) { |
282 | case GeomAbs_Cylinder: |
283 | case GeomAbs_Cone: |
284 | case GeomAbs_Sphere: |
285 | { |
286 | myHS2IsUPeriodic = Standard_True; |
287 | myHS2IsVPeriodic = Standard_False; |
288 | break; |
289 | } |
290 | case GeomAbs_Torus: |
291 | { |
292 | myHS2IsUPeriodic = myHS2IsVPeriodic = Standard_True; |
293 | break; |
294 | } |
295 | default: |
296 | { |
297 | //-- Le cas de biparametrees periodiques est gere en amont |
298 | myHS2IsUPeriodic = myHS2IsVPeriodic = Standard_False; |
299 | break; |
300 | } |
301 | } |
302 | if(myHS1IsUPeriodic) { |
303 | lmf = PI+PI; //-- myHS1->UPeriod(); |
304 | f = myHS1->FirstUParameter(); |
305 | l = myHS1->LastUParameter(); |
306 | fpls2=0.5*(f+l); |
307 | while((u1 < f)&&((fpls2-u1) > (u1+lmf-fpls2) )) { u1+=lmf; } |
308 | while((u1 > l)&&((u1-fpls2) > (fpls2-(u1-lmf)) )) { u1-=lmf; } |
309 | |
310 | } |
311 | if(myHS1IsVPeriodic) { |
312 | lmf = PI+PI; //-- myHS1->VPeriod(); |
313 | f = myHS1->FirstVParameter(); |
314 | l = myHS1->LastVParameter(); |
315 | fpls2=0.5*(f+l); |
316 | while((v1 < f)&&((fpls2-v1) > (v1+lmf-fpls2) )) { v1+=lmf; } |
317 | while((v1 > l)&&((v1-fpls2) > (fpls2-(v1-lmf)) )) { v1-=lmf; } |
318 | //-- while(v1 < f) { v1+=lmf; } |
319 | //-- while(v1 > l) { v1-=lmf; } |
320 | } |
321 | if(myHS2IsUPeriodic) { |
322 | lmf = PI+PI; //-- myHS2->UPeriod(); |
323 | f = myHS2->FirstUParameter(); |
324 | l = myHS2->LastUParameter(); |
325 | fpls2=0.5*(f+l); |
326 | while((u2 < f)&&((fpls2-u2) > (u2+lmf-fpls2) )) { u2+=lmf; } |
327 | while((u2 > l)&&((u2-fpls2) > (fpls2-(u2-lmf)) )) { u2-=lmf; } |
328 | //-- while(u2 < f) { u2+=lmf; } |
329 | //-- while(u2 > l) { u2-=lmf; } |
330 | } |
331 | if(myHS2IsVPeriodic) { |
332 | lmf = PI+PI; //-- myHS2->VPeriod(); |
333 | f = myHS2->FirstVParameter(); |
334 | l = myHS2->LastVParameter(); |
335 | fpls2=0.5*(f+l); |
336 | while((v2 < f)&&((fpls2-v2) > (v2+lmf-fpls2) )) { v2+=lmf; } |
337 | while((v2 > l)&&((v2-fpls2) > (fpls2-(v2-lmf)) )) { v2-=lmf; } |
338 | //-- while(v2 < f) { v2+=lmf; } |
339 | //-- while(v2 > l) { v2-=lmf; } |
340 | } |
341 | } |
342 | //======================================================================= |
343 | //function : PutPointsOnLine |
344 | //purpose : |
345 | //======================================================================= |
346 | void PutPointsOnLine(const Handle(Adaptor3d_HSurface)& S1, |
347 | const Handle(Adaptor3d_HSurface)& S2, |
348 | const IntPatch_SequenceOfPathPointOfTheSOnBounds& listpnt, |
349 | const IntPatch_SequenceOfLine& slin, |
350 | const Standard_Boolean OnFirst, |
351 | const Handle(Adaptor3d_TopolTool)& Domain, |
352 | const IntSurf_Quadric& QuadSurf, |
353 | const IntSurf_Quadric& OtherQuad, |
354 | const Standard_Boolean multpoint, |
355 | const Standard_Real Tolarc) { |
356 | |
357 | // Traitement des point (de listpnt) de depart. On les replace sur |
358 | // la ligne d intersection, en leur affectant la transition correcte sur |
359 | // cette ligne. |
360 | Standard_Integer nbpnt = listpnt.Length(); |
361 | Standard_Integer nblin=slin.Length(); |
362 | |
363 | if (!slin.Length() || !nbpnt) { |
364 | return; |
365 | } |
366 | // |
367 | Standard_Integer i,k; |
368 | Standard_Integer linenumber; |
369 | Standard_Real paraint,currentparameter,tolerance; |
370 | Standard_Real U1,V1,U2,V2; |
371 | Standard_Boolean goon; |
372 | |
373 | |
374 | gp_Pnt Psurf, ptbid; |
375 | gp_Vec Normale, Vtgint, Vtgrst; |
376 | |
377 | gp_Vec d1u,d1v; |
378 | gp_Pnt2d p2d; |
379 | gp_Vec2d d2d; |
380 | |
381 | IntSurf_Transition Transline,Transarc; |
382 | |
383 | Handle(Adaptor2d_HCurve2d) currentarc; |
384 | Handle(Adaptor3d_HVertex) vtx,vtxbis; |
385 | |
386 | IntPatch_Point solpnt; |
387 | IntPatch_ThePathPointOfTheSOnBounds currentpointonrst; |
388 | IntPatch_IType TheType; |
389 | |
390 | TColStd_Array1OfInteger UsedLine(1,nblin); |
391 | TColStd_Array1OfInteger Done(1,nbpnt); |
392 | for(i=1;i<=nbpnt;i++) Done(i) = 0; //-- Initialisation a la main |
393 | |
394 | for (i=1; i<=nbpnt; i++) { |
395 | |
396 | if (Done(i) != 1) { |
397 | currentpointonrst = listpnt.Value(i); |
398 | Psurf = currentpointonrst.Value(); // Point dans l espace |
399 | tolerance = currentpointonrst.Tolerance(); |
400 | |
401 | // On recherche d abord si on a correspondance avec un "point multiple" |
402 | UsedLine.Init(0); |
403 | |
404 | goon = Standard_True; |
405 | if (multpoint) { |
406 | #if 1 |
407 | Normale = QuadSurf.Normale(Psurf); // Normale a la surface au point |
408 | currentarc = currentpointonrst.Arc(); |
409 | currentparameter = currentpointonrst.Parameter(); |
410 | currentarc->D1(currentparameter,p2d,d2d); |
411 | QuadSurf.D1(p2d.X(),p2d.Y(),ptbid,d1u,d1v); |
412 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
413 | #endif |
414 | goon = MultiplePoint(listpnt,Domain,QuadSurf,Normale,slin,Done, UsedLine, |
415 | i,OnFirst); |
416 | } |
417 | if (goon) { |
418 | Standard_Boolean linefound; |
419 | |
420 | for(Standard_Integer indiceline = 1; indiceline <=slin.Length(); indiceline++) { |
421 | if( UsedLine(indiceline) != 0 ) |
422 | continue; |
423 | linenumber = indiceline; |
424 | |
425 | //-- Attention , les points peuvent etre deplaces |
426 | //-- il faut reprendre le point original |
427 | currentpointonrst = listpnt.Value(i); |
428 | currentarc = currentpointonrst.Arc(); |
429 | currentparameter = currentpointonrst.Parameter(); |
430 | Psurf = currentpointonrst.Value(); // Point dans l espace |
431 | tolerance = currentpointonrst.Tolerance(); |
432 | //-- |
433 | |
434 | |
435 | // Modified by skv - Thu Jan 15 15:57:15 2004 OCC4455 Begin |
436 | if (! currentpointonrst.IsNew()) { |
437 | Handle(Adaptor3d_HVertex) aVtx = currentpointonrst.Vertex(); |
438 | Standard_Real aVtxTol = aVtx->Resolution(currentarc); |
439 | Standard_Real aTolAng = 0.01*tolerance; |
440 | |
441 | tolerance = Max(tolerance, aVtxTol); |
442 | |
443 | gp_Vec aNorm1 = QuadSurf.Normale(Psurf); |
444 | gp_Vec aNorm2 = OtherQuad.Normale(Psurf); |
445 | // |
446 | if (aNorm1.Magnitude()>gp::Resolution() && |
447 | aNorm2.Magnitude()>gp::Resolution()) { |
448 | |
449 | if (aNorm1.IsParallel(aNorm2, aTolAng)) |
450 | tolerance = Sqrt(tolerance); |
451 | }// |
452 | } |
453 | // Modified by skv - Thu Jan 15 15:57:15 2004 OCC4455 End |
454 | gp_Pnt pointonarc; |
455 | Vtgint.SetCoord(0,0,0); |
456 | linefound = FindLine(Psurf,slin,tolerance,paraint,Vtgint,linenumber,indiceline, |
457 | currentarc,currentparameter,pointonarc,QuadSurf); |
458 | if (linefound) { |
459 | |
460 | #if 1 |
461 | Normale = QuadSurf.Normale(Psurf); // Normale a la surface au point |
462 | currentarc = currentpointonrst.Arc(); |
463 | //-- currentparameter = currentpointonrst.Parameter(); |
464 | currentarc->D1(currentparameter,p2d,d2d); |
465 | QuadSurf.D1(p2d.X(),p2d.Y(),ptbid,d1u,d1v); |
466 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
467 | #endif |
468 | |
469 | |
470 | |
471 | const Handle(IntPatch_Line)& lin = slin.Value(linenumber); |
472 | TheType = lin->ArcType(); |
473 | |
474 | if (!OnFirst) { // on cherche la correspondance entre point sur domaine |
475 | // de la premiere surface et point sur domaine de la |
476 | // deuxieme surface |
477 | |
478 | goon = PointOnSecondDom (listpnt, Domain, QuadSurf, Normale, |
479 | Vtgint, lin, Done, i); |
480 | } |
481 | |
482 | if (goon) { |
483 | //-- Modification du 4 avril 97 tolerance->Tolarc |
484 | //-- on replace sur le vertex la tolerance d entree et |
485 | //-- non la tolerance qui a servi au FindLine |
486 | solpnt.SetValue(Psurf,Tolarc,Standard_False); |
487 | |
488 | U1 = p2d.X(); V1 = p2d.Y(); |
489 | OtherQuad.Parameters(Psurf,U2,V2); |
490 | |
491 | if (OnFirst) { |
492 | Recadre(S1,S2,U1,V1,U2,V2); |
493 | solpnt.SetParameters(U1,V1,U2,V2); |
494 | } |
495 | else { |
496 | Recadre(S1,S2,U2,V2,U1,V1); |
497 | solpnt.SetParameters(U2,V2,U1,V1); |
498 | } |
499 | solpnt.SetParameter(paraint); |
500 | |
501 | if (! currentpointonrst.IsNew()) { |
502 | vtx = currentpointonrst.Vertex(); |
503 | solpnt.SetVertex(OnFirst,vtx); |
504 | } |
505 | else { |
506 | //-- goon = Standard_False; ???? |
507 | } |
508 | |
509 | if(Normale.SquareMagnitude()<1e-16) { |
510 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
511 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
512 | } |
513 | else { |
514 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale,Transline,Transarc); |
515 | } |
516 | solpnt.SetArc(OnFirst,currentarc, currentparameter, |
517 | Transline,Transarc); |
518 | if (TheType == IntPatch_Analytic) { |
519 | (*((Handle(IntPatch_ALine)*)&lin))->AddVertex(solpnt); |
520 | } |
521 | else { |
522 | (*((Handle(IntPatch_GLine)*)&lin))->AddVertex(solpnt); |
523 | } |
524 | Done(i) = 1; |
525 | |
526 | if (goon) { |
527 | for (k=i+1; k<= nbpnt; k++) { |
528 | if (Done(k) != 1) { |
529 | currentpointonrst = listpnt.Value(k); |
530 | if (!currentpointonrst.IsNew()) { |
531 | vtxbis = currentpointonrst.Vertex(); |
532 | if(vtx.IsNull()) { |
533 | } |
534 | else if (Domain->Identical(vtx, vtxbis)) { |
535 | solpnt.SetVertex(OnFirst,vtxbis); |
536 | currentarc = currentpointonrst.Arc(); |
537 | currentparameter = currentpointonrst.Parameter(); |
538 | |
539 | // currentarc->D1(currentparameter,ptbid,Vtgrst); |
540 | currentarc->D1(currentparameter,p2d,d2d); |
541 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
542 | if(Normale.SquareMagnitude()<1e-16) { |
543 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
544 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
545 | } |
546 | else { |
547 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale, |
548 | Transline,Transarc); |
549 | } |
550 | solpnt.SetArc(OnFirst,currentarc,currentparameter, |
551 | Transline,Transarc); |
552 | if (TheType == IntPatch_Analytic) { |
553 | (*((Handle(IntPatch_ALine)*)&lin))->AddVertex(solpnt); |
554 | } |
555 | else { |
556 | (*((Handle(IntPatch_GLine)*)&lin))->AddVertex(solpnt); |
557 | } |
558 | Done(k) = 1; |
559 | } |
560 | } |
561 | } |
562 | } |
563 | } |
564 | } |
565 | } |
566 | else { |
567 | Done(i) = 1; // il faudra tester si IsNew ou pas |
568 | // et traiter en consequence |
569 | } |
570 | } |
571 | } |
572 | } |
573 | } |
574 | } |
575 | |
576 | |
577 | Standard_Boolean MultiplePoint (const IntPatch_SequenceOfPathPointOfTheSOnBounds& listpnt, |
578 | const Handle(Adaptor3d_TopolTool)& Domain, |
579 | const IntSurf_Quadric& QuadSurf, |
580 | const gp_Vec& Normale, |
581 | const IntPatch_SequenceOfLine& slin, |
582 | TColStd_Array1OfInteger& Done, |
583 | TColStd_Array1OfInteger& UsedLine, |
584 | const Standard_Integer Index, |
585 | const Standard_Boolean OnFirst) { |
586 | |
587 | // Traitement des points "multiples". |
588 | |
589 | |
590 | Standard_Integer k,ii,jj,nbvtx; |
591 | Standard_Integer nblin = slin.Length(); |
592 | IntPatch_IType TheType; |
593 | |
594 | |
595 | IntSurf_Transition Transline,Transarc; |
596 | |
597 | |
598 | IntPatch_Point intpt; |
599 | Handle(Adaptor2d_HCurve2d) currentarc; |
600 | Handle(Adaptor3d_HVertex) vtx,vtxbis; |
601 | |
602 | Standard_Integer nbpnt = listpnt.Length(); |
603 | IntPatch_ThePathPointOfTheSOnBounds currentpointonrst = listpnt.Value(Index); |
604 | IntPatch_ThePathPointOfTheSOnBounds otherpt; |
605 | gp_Pnt Point = currentpointonrst.Value(); |
606 | TColStd_Array1OfInteger localdone(1,nbpnt); localdone.Init(0); |
607 | for (ii=1; ii<=nbpnt; ii++) { |
608 | localdone(ii)=Done(ii); |
609 | } |
610 | |
611 | Standard_Real currentparameter; |
612 | Standard_Real Paraint; |
613 | gp_Vec Vtgint,Vtgrst; |
614 | gp_Pnt ptbid; |
615 | |
616 | gp_Vec d1u,d1v; |
617 | gp_Pnt2d p2d; |
618 | gp_Vec2d d2d; |
619 | |
620 | Standard_Boolean goon; |
621 | |
622 | Standard_Boolean Retvalue = Standard_True; |
623 | |
624 | for (ii = 1; ii <= nblin; ii++) { |
625 | const Handle(IntPatch_Line)& slinValueii = slin.Value(ii); |
626 | TheType = slinValueii->ArcType(); |
627 | if (TheType == IntPatch_Analytic) { |
628 | nbvtx = (*((Handle(IntPatch_ALine)*)&slinValueii))->NbVertex(); |
629 | } |
630 | else { |
631 | nbvtx = (*((Handle(IntPatch_GLine)*)&slinValueii))->NbVertex(); |
632 | } |
633 | jj = 1; |
634 | while (jj <= nbvtx) { |
635 | if (TheType == IntPatch_Analytic) { |
636 | intpt = (*((Handle(IntPatch_ALine)*)&slinValueii))->Vertex(jj); |
637 | } |
638 | else { |
639 | intpt = (*((Handle(IntPatch_GLine)*)&slinValueii))->Vertex(jj); |
640 | } |
641 | if (intpt.IsMultiple() && |
642 | (( OnFirst && !intpt.IsOnDomS1()) || |
643 | (!OnFirst && !intpt.IsOnDomS2()))) { |
644 | if (Point.Distance(intpt.Value()) <= intpt.Tolerance()) { |
645 | Retvalue = Standard_False; |
646 | Standard_Boolean foo = SingleLine(Point,slinValueii, |
647 | intpt.Tolerance(),Paraint,Vtgint); |
648 | if (!foo) { |
649 | return Standard_False; // ne doit pas se produire |
650 | } |
651 | |
652 | if (!currentpointonrst.IsNew()) { |
653 | goon = Standard_True; |
654 | vtx = currentpointonrst.Vertex(); |
655 | intpt.SetVertex(OnFirst,vtx); |
656 | } |
657 | else { |
658 | goon = Standard_False; |
659 | } |
660 | currentarc = currentpointonrst.Arc(); |
661 | currentparameter = currentpointonrst.Parameter(); |
662 | currentarc->D1(currentparameter,p2d,d2d); |
663 | QuadSurf.D1(p2d.X(),p2d.Y(),ptbid,d1u,d1v); |
664 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
665 | |
666 | //-- Si la normale est nulle (apex d un cone) On simule une transition UNKNOWN |
667 | if(Normale.SquareMagnitude()<1e-16) { |
668 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
669 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
670 | } |
671 | else { |
672 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale,Transline,Transarc); |
673 | } |
674 | |
675 | //-- Avant, on ne mettait pas ce point (17 nov 97) |
676 | //--printf("\n ImpImp_0 : Point(%g,%g,%g) intpt(%g,%g,%g) \n", |
677 | //-- Point.X(),Point.Y(),Point.Z(),intpt.Value().X(),intpt.Value().Y(),intpt.Value().Z()); |
678 | intpt.SetValue(Point); |
679 | |
680 | intpt.SetArc(OnFirst,currentarc,currentparameter, |
681 | Transline,Transarc); |
682 | |
683 | |
684 | if (TheType == IntPatch_Analytic) { |
685 | (*((Handle(IntPatch_ALine)*)&slinValueii))->Replace(jj,intpt); |
686 | } |
687 | else { |
688 | (*((Handle(IntPatch_GLine)*)&slinValueii))->Replace(jj,intpt); |
689 | } |
690 | localdone(Index) = 1; |
691 | if (goon) { |
692 | for (k=Index+1; k<= nbpnt; k++) { |
693 | if (Done(k) != 1) { |
694 | otherpt= listpnt.Value(k); |
695 | if (!otherpt.IsNew()) { |
696 | vtxbis = otherpt.Vertex(); |
697 | if (Domain->Identical(vtx, vtxbis)) { |
698 | intpt.SetVertex(OnFirst,vtxbis); |
699 | currentarc = otherpt.Arc(); |
700 | currentparameter = otherpt.Parameter(); |
701 | |
702 | currentarc->D1(currentparameter,p2d,d2d); |
703 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
704 | if(Normale.SquareMagnitude()<1e-16) { |
705 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
706 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
707 | } |
708 | else { |
709 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale, |
710 | Transline,Transarc); |
711 | } |
712 | intpt.SetArc(OnFirst,currentarc,currentparameter, |
713 | Transline,Transarc); |
714 | if (TheType == IntPatch_Analytic) { |
715 | (*((Handle(IntPatch_ALine)*)&slinValueii))->AddVertex(intpt); |
716 | } |
717 | else { |
718 | (*((Handle(IntPatch_GLine)*)&slinValueii))->AddVertex(intpt); |
719 | } |
720 | UsedLine(ii) = 1; |
721 | Retvalue = Standard_True; |
722 | localdone(k) = 1; |
723 | } |
724 | } |
725 | } |
726 | } |
727 | } |
728 | //-- jj = nbvtx +1; |
729 | } |
730 | //-- else { |
731 | jj = jj+1; |
732 | //-- } |
733 | } |
734 | else { |
735 | jj = jj+1; |
736 | } |
737 | } |
738 | } |
739 | |
740 | for (ii=1; ii<=nbpnt;ii++) { |
741 | Done(ii) = localdone(ii); |
742 | } |
743 | |
744 | return Retvalue; |
745 | } |
746 | |
747 | |
748 | |
749 | Standard_Boolean PointOnSecondDom (const IntPatch_SequenceOfPathPointOfTheSOnBounds& listpnt, |
750 | const Handle(Adaptor3d_TopolTool)& Domain, |
751 | const IntSurf_Quadric& QuadSurf, |
752 | const gp_Vec& Normale, |
753 | const gp_Vec& Vtgint, |
754 | const Handle(IntPatch_Line)& lin, |
755 | TColStd_Array1OfInteger& Done, |
756 | const Standard_Integer Index) |
757 | |
758 | |
759 | // Duplication des points sur domaine de l autre surface. |
760 | // On sait que le vertex sous-jacent est PntRef |
761 | |
762 | |
763 | { |
764 | |
765 | Standard_Integer k,jj,nbvtx; |
766 | IntPatch_IType TheType; |
767 | |
768 | IntSurf_Transition Transline,Transarc; |
769 | IntPatch_Point intpt; |
770 | Handle(Adaptor2d_HCurve2d) currentarc; |
771 | Handle(Adaptor3d_HVertex) vtx,vtxbis; |
772 | gp_Pnt ptbid; |
773 | gp_Vec Vtgrst; |
774 | |
775 | gp_Vec d1u,d1v; |
776 | gp_Pnt2d p2d; |
777 | gp_Vec2d d2d; |
778 | |
779 | Standard_Integer nbpnt = listpnt.Length(); |
780 | IntPatch_ThePathPointOfTheSOnBounds currentpointonrst = listpnt.Value(Index); |
781 | Standard_Real currentparameter; |
782 | |
783 | Standard_Boolean goon; |
784 | Standard_Boolean Retvalue = Standard_True; |
785 | |
786 | TheType = lin->ArcType(); |
787 | if (TheType == IntPatch_Analytic) { |
788 | nbvtx = (*((Handle(IntPatch_ALine)*)&lin))->NbVertex(); |
789 | } |
790 | else { |
791 | nbvtx = (*((Handle(IntPatch_GLine)*)&lin))->NbVertex(); |
792 | } |
793 | jj = 1; |
794 | while (jj <= nbvtx) { |
795 | if (TheType == IntPatch_Analytic) { |
796 | intpt = (*((Handle(IntPatch_ALine)*)&lin))->Vertex(jj); |
797 | } |
798 | else { |
799 | intpt = (*((Handle(IntPatch_GLine)*)&lin))->Vertex(jj); |
800 | } |
801 | if (!intpt.IsOnDomS2()) { |
802 | if (currentpointonrst.Value().Distance(intpt.Value()) <= |
803 | intpt.Tolerance()) { |
804 | Retvalue = Standard_False; |
805 | if (!currentpointonrst.IsNew()) { |
806 | goon = Standard_True; |
807 | vtx = currentpointonrst.Vertex(); |
808 | intpt.SetVertex(Standard_False,vtx); |
809 | } |
810 | else { |
811 | goon = Standard_False; |
812 | } |
813 | currentarc = currentpointonrst.Arc(); |
814 | currentparameter = currentpointonrst.Parameter(); |
815 | currentarc->D1(currentparameter,p2d,d2d); |
816 | QuadSurf.D1(p2d.X(),p2d.Y(),ptbid,d1u,d1v); |
817 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
818 | if(Normale.SquareMagnitude()<1e-16) { |
819 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
820 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
821 | } |
822 | else { |
823 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale,Transline,Transarc); |
824 | } |
825 | intpt.SetArc(Standard_False,currentarc,currentparameter, |
826 | Transline,Transarc); |
827 | if (TheType == IntPatch_Analytic) { |
828 | (*((Handle(IntPatch_ALine)*)&lin))->Replace(jj,intpt); |
829 | } |
830 | else { |
831 | (*((Handle(IntPatch_GLine)*)&lin))->Replace(jj,intpt); |
832 | } |
833 | Done(Index) = 1; |
834 | |
835 | if (goon) { |
836 | for (k=Index+1; k<= nbpnt; k++) { |
837 | if (Done(k) != 1) { |
838 | currentpointonrst = listpnt.Value(k); |
839 | if (!currentpointonrst.IsNew()) { |
840 | vtxbis = currentpointonrst.Vertex(); |
841 | if (Domain->Identical(vtx, vtxbis)) { |
842 | intpt.SetVertex(Standard_False,vtxbis); |
843 | currentarc = currentpointonrst.Arc(); |
844 | currentparameter = currentpointonrst.Parameter(); |
845 | currentarc->D1(currentparameter,p2d,d2d); |
846 | Vtgrst.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
847 | if(Normale.SquareMagnitude()<1e-16) { |
848 | Transline.SetValue(Standard_True,IntSurf_Undecided); |
849 | Transarc.SetValue(Standard_True,IntSurf_Undecided); |
850 | } |
851 | else { |
852 | IntSurf::MakeTransition(Vtgint,Vtgrst,Normale, |
853 | Transline,Transarc); |
854 | } |
855 | intpt.SetArc(Standard_False,currentarc,currentparameter, |
856 | Transline,Transarc); |
857 | if (TheType == IntPatch_Analytic) { |
858 | (*((Handle(IntPatch_ALine)*)&lin))->AddVertex(intpt); |
859 | } |
860 | else { |
861 | (*((Handle(IntPatch_GLine)*)&lin))->AddVertex(intpt); |
862 | } |
863 | Done(k) = 1; |
864 | } |
865 | } |
866 | } |
867 | } |
868 | } |
869 | //-- jj = nbvtx + 1; |
870 | jj++; |
871 | } |
872 | else { |
873 | jj = jj+1; |
874 | } |
875 | } |
876 | else { |
877 | jj = jj+1; |
878 | } |
879 | if (TheType == IntPatch_Analytic) { |
880 | nbvtx = (*((Handle(IntPatch_ALine)*)&lin))->NbVertex(); |
881 | } |
882 | else { |
883 | nbvtx = (*((Handle(IntPatch_GLine)*)&lin))->NbVertex(); |
884 | } |
885 | } |
886 | return Retvalue; |
887 | } |
888 | |
889 | |
890 | |
891 | Standard_Boolean FindLine (gp_Pnt& Psurf, |
892 | const IntPatch_SequenceOfLine& slin, |
893 | const Standard_Real Tol, |
894 | Standard_Real& Paraint, |
895 | gp_Vec& Vtgtint, |
896 | Standard_Integer& Range, |
897 | Standard_Integer OnlyThisLine, |
898 | const Handle(Adaptor2d_HCurve2d)& thearc, |
899 | Standard_Real& theparameteronarc, |
900 | gp_Pnt& thepointonarc, |
901 | const IntSurf_Quadric& QuadSurf) |
902 | { |
903 | |
904 | // Traitement du point de depart ayant pour representation Psurf |
905 | // dans l espace. On recherche la ligne d intersection contenant ce point. |
906 | // On a en sortie la ligne, et le parametre et sa tangente du point sur |
907 | // la ligne d intersection. |
908 | |
909 | Standard_Real distmin = RealLast(); |
910 | Standard_Real dist,para; |
911 | Standard_Real lower,upper; |
912 | gp_Pnt pt; |
913 | Standard_Integer i; |
914 | IntPatch_IType typarc; |
915 | |
916 | Standard_Integer nblin = slin.Length(); |
917 | for (i=1; i<=nblin; i++) { |
918 | if(OnlyThisLine) { i=OnlyThisLine; nblin=0; } |
919 | const Handle(IntPatch_Line)& lin = slin.Value(i); |
920 | typarc = lin->ArcType(); |
921 | if (typarc == IntPatch_Analytic) { |
922 | Standard_Boolean foo; |
923 | lower = (*((Handle(IntPatch_ALine)*)&lin))->FirstParameter(foo); |
924 | upper = (*((Handle(IntPatch_ALine)*)&lin))->LastParameter(foo); |
925 | } |
926 | else { |
927 | if ((*((Handle(IntPatch_GLine)*)&lin))->HasFirstPoint()) { |
928 | lower = (*((Handle(IntPatch_GLine)*)&lin))->FirstPoint().ParameterOnLine(); |
929 | } |
930 | else { |
931 | lower = RealFirst(); |
932 | } |
933 | if ((*((Handle(IntPatch_GLine)*)&lin))->HasLastPoint()) { |
934 | upper = (*((Handle(IntPatch_GLine)*)&lin))->LastPoint().ParameterOnLine(); |
935 | } |
936 | else { |
937 | upper = RealLast(); |
938 | } |
939 | } |
940 | |
941 | switch (typarc) { |
942 | case IntPatch_Lin : |
943 | { |
944 | para = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Line(),Psurf); |
945 | if (para <= upper && para >= lower) { |
946 | pt = ElCLib::Value(para,(*((Handle(IntPatch_GLine)*)&lin))->Line()); |
947 | dist = Psurf.Distance(pt); |
948 | if (dist< distmin) { |
949 | distmin = dist; |
950 | Paraint = para; |
951 | Range = i; |
952 | } |
953 | } |
954 | } |
955 | break; |
956 | case IntPatch_Circle : |
957 | { |
958 | para = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Circle(),Psurf); |
959 | if ((para <= upper && para >= lower) || |
960 | (para + 2.*PI <=upper && para + 2.*PI >= lower) || |
961 | (para - 2.*PI <=upper && para - 2.*PI >= lower)) { |
962 | pt = ElCLib::Value(para,(*((Handle(IntPatch_GLine)*)&lin))->Circle()); |
963 | dist = Psurf.Distance(pt); |
964 | if (dist< distmin) { |
965 | distmin = dist; |
966 | Paraint = para; |
967 | Range = i; |
968 | } |
969 | } |
970 | } |
971 | break; |
972 | case IntPatch_Ellipse : |
973 | { |
974 | para = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Ellipse(),Psurf); |
975 | if ((para <= upper && para >= lower) || |
976 | (para + 2.*PI <=upper && para + 2.*PI >= lower) || |
977 | (para - 2.*PI <=upper && para - 2.*PI >= lower)) { |
978 | pt = ElCLib::Value(para,(*((Handle(IntPatch_GLine)*)&lin))->Ellipse()); |
979 | dist = Psurf.Distance(pt); |
980 | if (dist< distmin) { |
981 | distmin = dist; |
982 | Paraint = para; |
983 | Range = i; |
984 | } |
985 | } |
986 | } |
987 | break; |
988 | case IntPatch_Parabola : |
989 | { |
990 | |
991 | #if 0 |
992 | para = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Parabola(),Psurf); |
993 | if (para <= upper && para >= lower) { |
994 | pt = ElCLib::Value(para,(*((Handle(IntPatch_GLine)*)&lin))->Parabola()); |
995 | dist = Psurf.Distance(pt); |
996 | if (dist< distmin) { |
997 | distmin = dist; |
998 | Paraint = para; |
999 | Range = i; |
1000 | } |
1001 | } |
1002 | #else |
1003 | //-- Le calcul du parametre sur une parabole est mal fait ds ElCLib. Il ne tient pas compte |
1004 | //-- de la meilleure facon de calculer (axe X ou axe Y). Bilan : Si la parabole est tres |
1005 | //-- pointue (focal de l'ordre de 1e-2 et si le point est a un parametre grand, ca foire. ) |
1006 | //-- On ne peut pas modifier faciolement ds ElCLib car on ne passe pas la focale. ... |
1007 | const gp_Parab& Parab=(*((Handle(IntPatch_GLine)*)&lin))->Parabola(); |
1008 | para = ElCLib::Parameter(Parab,Psurf); |
1009 | if (para <= upper && para >= lower) { |
1010 | Standard_Integer amelioration=0; |
1011 | //-- cout<<"\n ****** \n"; |
1012 | do { |
1013 | Standard_Real parabis = para+0.0000001; |
1014 | |
1015 | pt = ElCLib::Value(para,Parab); |
1016 | dist = Psurf.Distance(pt); |
1017 | |
1018 | gp_Pnt ptbis = ElCLib::Value(parabis,Parab); |
1019 | Standard_Real distbis = Psurf.Distance(ptbis); |
1020 | |
1021 | Standard_Real ddist = distbis-dist; |
1022 | |
1023 | //--cout<<" para: "<<para<<" dist:"<<dist<<" ddist:"<<ddist<<endl; |
1024 | |
1025 | if (dist< distmin) { |
1026 | distmin = dist; |
1027 | Paraint = para; |
1028 | Range = i; |
1029 | } |
1030 | if(dist<1.0e-9 && dist>-1.0e-9) { amelioration=100; } |
1031 | |
1032 | if(ddist>1.0e-9 || ddist<-1.0e-9 ) { |
1033 | para=para-dist*(parabis-para)/ddist; |
1034 | } |
1035 | else { |
1036 | amelioration=100; |
1037 | } |
1038 | } |
1039 | while(++amelioration < 5); |
1040 | } |
1041 | |
1042 | |
1043 | #endif |
1044 | } |
1045 | break; |
1046 | case IntPatch_Hyperbola : |
1047 | { |
1048 | para = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Hyperbola(),Psurf); |
1049 | if (para <= upper && para >= lower) { |
1050 | pt = ElCLib::Value(para,(*((Handle(IntPatch_GLine)*)&lin))->Hyperbola()); |
1051 | dist = Psurf.Distance(pt); |
1052 | if (dist< distmin) { |
1053 | distmin = dist; |
1054 | Paraint = para; |
1055 | Range = i; |
1056 | } |
1057 | } |
1058 | } |
1059 | break; |
1060 | |
1061 | case IntPatch_Analytic : |
1062 | { |
1063 | const Handle(IntPatch_ALine)& alin = (*((Handle(IntPatch_ALine)*)&lin)); |
1064 | Standard_Boolean ok = alin->FindParameter(Psurf,para); |
1065 | if (ok) { |
1066 | pt = alin->Value(para); |
1067 | dist = Psurf.Distance(pt); |
1068 | if (dist< distmin) { |
1069 | distmin = dist; |
1070 | Paraint = para; |
1071 | Range = i; |
1072 | } |
1073 | } |
1074 | else { |
1075 | //-- le point n a pas ete trouve par bete projection. |
1076 | //-- on essaie l intersection avec la restriction en 2d |
1077 | Standard_Real theparamonarc = theparameteronarc; |
1078 | #ifdef DEB |
1079 | Standard_Real anpara=para; |
1080 | #endif |
1081 | gp_Pnt CopiePsurf=Psurf; |
1082 | Standard_Boolean ok=IntersectionWithAnArc(CopiePsurf,alin,para,thearc,theparamonarc,thepointonarc,QuadSurf,lower,upper,dist); |
1083 | |
1084 | //--printf("\nIntersectionWithAnArc %d \n Psurf(%g,%g,%g)->(%g,%g,%g) dist=%g\n para(%g)->(%g)\n paraonarc(%g)->(%g)", |
1085 | //-- ok,Psurf.X(),Psurf.Y(),Psurf.Z(),thepointonarc.X(),thepointonarc.Y(),thepointonarc.Z(),dist, |
1086 | //-- anpara,para,theparameteronarc,theparamonarc); |
1087 | dist = CopiePsurf.Distance(Psurf); |
1088 | if(ok) { |
1089 | if(dist<Tol) { |
1090 | theparameteronarc = theparamonarc; |
1091 | Psurf = thepointonarc; |
1092 | distmin = dist; |
1093 | Paraint = para; |
1094 | Range = i; |
1095 | } |
1096 | } |
1097 | } |
1098 | } |
1099 | break; |
1100 | |
1101 | case IntPatch_Walking: // impossible . c est pour eviter les warnings |
1102 | { |
1103 | } |
1104 | case IntPatch_Restriction: // impossible . c est pour eviter les warnings |
1105 | { |
1106 | } |
1107 | } |
1108 | } |
1109 | |
1110 | if (distmin > Tol) { |
1111 | return Standard_False; |
1112 | } |
1113 | |
1114 | typarc = slin.Value(Range)->ArcType(); |
1115 | |
1116 | // Calcul de la tangente. |
1117 | switch (typarc) { |
1118 | case IntPatch_Lin : |
1119 | Vtgtint = (*((Handle(IntPatch_GLine)*)&slin(Range)))->Line().Direction(); |
1120 | break; |
1121 | case IntPatch_Circle : |
1122 | Vtgtint = ElCLib::DN(Paraint,(*((Handle(IntPatch_GLine)*)&slin(Range)))->Circle(),1); |
1123 | break; |
1124 | case IntPatch_Ellipse : |
1125 | Vtgtint = ElCLib::DN(Paraint,(*((Handle(IntPatch_GLine)*)&slin(Range)))->Ellipse(),1); |
1126 | break; |
1127 | case IntPatch_Parabola : |
1128 | Vtgtint = ElCLib::DN(Paraint,(*((Handle(IntPatch_GLine)*)&slin(Range)))->Parabola(),1); |
1129 | break; |
1130 | case IntPatch_Hyperbola : |
1131 | Vtgtint = ElCLib::DN(Paraint,(*((Handle(IntPatch_GLine)*)&slin(Range)))->Hyperbola(),1); |
1132 | break; |
1133 | |
1134 | case IntPatch_Analytic: |
1135 | { |
1136 | const Handle(IntPatch_ALine)& alin = (*((Handle(IntPatch_ALine)*)&slin(Range))); |
1137 | Standard_Boolean abid = alin->D1(Paraint,pt,Vtgtint); |
1138 | if (!abid) { |
1139 | Standard_Real domaininf,domainsup,paramproche; |
1140 | Standard_Boolean boolbid; |
1141 | domaininf = alin->FirstParameter(boolbid); |
1142 | domainsup = alin->LastParameter(boolbid); |
1143 | if(Paraint>=domaininf && Paraint<=domainsup) { |
1144 | Standard_Real DeltaParam = 0.001 * (domainsup-domaininf); |
1145 | if(Paraint-domaininf >= domainsup-Paraint) { |
1146 | //-- On decale le point vers le parametre le plus eloigne. |
1147 | DeltaParam = -DeltaParam; |
1148 | } |
1149 | Standard_Integer kountbid = 0; |
1150 | Standard_Boolean bornok = Standard_True; |
1151 | paramproche = Paraint; |
1152 | do { |
1153 | paramproche+=DeltaParam; |
1154 | kountbid++; |
1155 | gp_Pnt ptbid; |
1156 | if(paramproche>=domaininf && paramproche<=domainsup) { |
1157 | abid = alin->D1(paramproche,ptbid,Vtgtint); |
1158 | } |
1159 | else { |
1160 | bornok = Standard_False; |
1161 | } |
1162 | } |
1163 | while(abid==Standard_False && kountbid<5 && bornok); |
1164 | //-- Attention aux points de tangence (croisement de 4 lignes ) |
1165 | bornok = Standard_True; |
1166 | kountbid = 0; |
1167 | gp_Vec OVtgtint(0.0,0.0,0.0); |
1168 | paramproche = Paraint; |
1169 | do { |
1170 | paramproche-=DeltaParam; |
1171 | kountbid++; |
1172 | gp_Pnt ptbid; |
1173 | if(paramproche>=domaininf && paramproche<=domainsup) { |
1174 | abid = alin->D1(paramproche,ptbid,OVtgtint); |
1175 | } |
1176 | else { |
1177 | bornok = Standard_False; |
1178 | } |
1179 | } |
1180 | while(abid==Standard_False && kountbid<5 && bornok); |
1181 | if(bornok) { |
1182 | paramproche = Vtgtint.Dot(OVtgtint); |
1183 | if(paramproche<=0.0) abid = Standard_False; |
1184 | } |
1185 | } |
1186 | if(!abid) { |
1187 | //-- cout << "Pb sur Calcul de derivee 111 " << endl; |
1188 | Vtgtint.SetCoord(0.,0.,0.); |
1189 | } |
1190 | } |
1191 | } |
1192 | break; |
1193 | case IntPatch_Walking: // impossible . c est pour eviter les warnings |
1194 | { |
1195 | } |
1196 | case IntPatch_Restriction: // impossible . c est pour eviter les warnings |
1197 | { |
1198 | } |
1199 | |
1200 | } |
1201 | return Standard_True; |
1202 | } |
1203 | |
1204 | |
1205 | Standard_Boolean SingleLine (const gp_Pnt& Psurf, |
1206 | const Handle(IntPatch_Line)& lin, |
1207 | const Standard_Real Tol, |
1208 | Standard_Real& Paraint, |
1209 | gp_Vec& Vtgtint) { |
1210 | |
1211 | // Traitement du point de depart ayant pour representation Psurf |
1212 | // dans l espace. On le replace sur la ligne d intersection; On a en sortie |
1213 | // son parametre et sa tangente sur la ligne d intersection. |
1214 | // La fonction renvoie False si le point projete est a une distance |
1215 | // superieure a Tol du point a projeter. |
1216 | |
1217 | IntPatch_IType typarc = lin->ArcType(); |
1218 | |
1219 | Standard_Real parproj; |
1220 | gp_Vec tgint; |
1221 | gp_Pnt ptproj; |
1222 | Standard_Boolean retvalue; |
1223 | |
1224 | |
1225 | switch (typarc) { |
1226 | case IntPatch_Lin : |
1227 | parproj = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Line(),Psurf); |
1228 | ElCLib::D1(parproj,(*((Handle(IntPatch_GLine)*)&lin))->Line(),ptproj,tgint); |
1229 | break; |
1230 | case IntPatch_Circle : |
1231 | parproj = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Circle(),Psurf); |
1232 | ElCLib::D1(parproj,(*((Handle(IntPatch_GLine)*)&lin))->Circle(),ptproj,tgint); |
1233 | break; |
1234 | case IntPatch_Ellipse : |
1235 | parproj = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Ellipse(),Psurf); |
1236 | ElCLib::D1(parproj,(*((Handle(IntPatch_GLine)*)&lin))->Ellipse(),ptproj,tgint); |
1237 | break; |
1238 | case IntPatch_Parabola : |
1239 | parproj = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Parabola(),Psurf); |
1240 | ElCLib::D1(parproj,(*((Handle(IntPatch_GLine)*)&lin))->Parabola(),ptproj,tgint); |
1241 | break; |
1242 | case IntPatch_Hyperbola : |
1243 | parproj = ElCLib::Parameter((*((Handle(IntPatch_GLine)*)&lin))->Hyperbola(),Psurf); |
1244 | ElCLib::D1(parproj,(*((Handle(IntPatch_GLine)*)&lin))->Hyperbola(),ptproj,tgint); |
1245 | break; |
1246 | case IntPatch_Analytic : |
1247 | { |
1248 | const Handle(IntPatch_ALine)& alin = (*((Handle(IntPatch_ALine)*)&lin)); |
1249 | Standard_Boolean ok = alin->FindParameter(Psurf,parproj); |
1250 | if (ok) { |
1251 | gp_Pnt ptbid; |
1252 | Standard_Boolean bid = alin->D1(parproj,ptbid,tgint); |
1253 | if (!bid) { |
1254 | Standard_Real domaininf,domainsup,paramproche; |
1255 | Standard_Boolean boolbid; |
1256 | domaininf = alin->FirstParameter(boolbid); |
1257 | domainsup = alin->LastParameter(boolbid); |
1258 | if(parproj>=domaininf && parproj<=domainsup) { |
1259 | Standard_Real DeltaParam = 0.001 * (domainsup-domaininf); |
1260 | if(parproj-domaininf >= domainsup-parproj) { |
1261 | //-- On decale le point vers le parametre le plus eloigne. |
1262 | DeltaParam = -DeltaParam; |
1263 | } |
1264 | Standard_Integer kountbid = 0; |
1265 | paramproche = parproj; |
1266 | do { |
1267 | paramproche+=DeltaParam; |
1268 | kountbid++; |
1269 | bid = alin->D1(paramproche,ptbid,tgint); |
1270 | } |
1271 | while(bid==Standard_False && kountbid<5); |
1272 | ptproj = Psurf; |
1273 | } |
1274 | if(!bid) { |
1275 | //-- cout << "Pb sur Calcul de derivee ALine " << endl; |
1276 | tgint.SetCoord(0.,0.,0.); |
1277 | return(Standard_False); |
1278 | } |
1279 | } |
1280 | else { |
1281 | ptproj = Psurf; |
1282 | } |
1283 | } |
1284 | else { |
1285 | //-- cout << "---- Pb sur ligne analytique dans SingleLine" << endl; |
1286 | //-- cout << " Find Parameter"<<endl; |
1287 | return Standard_False; |
1288 | } |
1289 | } |
1290 | break; |
1291 | case IntPatch_Walking: // impossible . c est pour eviter les warnings |
1292 | { |
1293 | } |
1294 | case IntPatch_Restriction: // impossible . c est pour eviter les warnings |
1295 | { |
1296 | } |
1297 | } |
1298 | |
1299 | if (Psurf.Distance(ptproj) <= Tol) { |
1300 | Paraint = parproj; |
1301 | Vtgtint = tgint; |
1302 | retvalue = Standard_True; |
1303 | } |
1304 | else { |
1305 | retvalue = Standard_False; |
1306 | } |
1307 | return retvalue; |
1308 | } |
1309 | |
1310 | |
1311 | void ProcessSegments (const IntPatch_SequenceOfSegmentOfTheSOnBounds& listedg, |
1312 | IntPatch_SequenceOfLine& slin, |
1313 | const IntSurf_Quadric& Quad1, |
1314 | const IntSurf_Quadric& Quad2, |
1315 | const Standard_Boolean OnFirst, |
1316 | const Standard_Real TolArc) { |
1317 | |
1318 | Standard_Integer i,j,k; |
1319 | Standard_Integer nbedg = listedg.Length(); |
1320 | Standard_Integer Nblines,Nbpts; |
1321 | |
1322 | Handle(Adaptor2d_HCurve2d) arcRef; |
1323 | IntPatch_Point ptvtx, newptvtx; |
1324 | |
1325 | Handle(IntPatch_RLine) rline; //-- On fait rline = new ... par la suite |
1326 | |
1327 | IntPatch_TheSegmentOfTheSOnBounds thesegsol; |
1328 | IntPatch_ThePathPointOfTheSOnBounds PStartf,PStartl; |
1329 | Standard_Boolean dofirst,dolast,procf,procl; |
1330 | #ifndef DEB |
1331 | Standard_Real paramf =0.,paraml =0.,U1 =0.,V1 =0.,U2 =0.,V2 =0.; |
1332 | #else |
1333 | Standard_Real paramf,paraml,U1,V1,U2,V2; |
1334 | #endif |
1335 | IntPatch_IType typ; |
1336 | IntSurf_TypeTrans trans1,trans2; |
1337 | IntSurf_Transition TRest,TArc; |
1338 | gp_Vec tgline,norm1,norm2,tgarc; |
1339 | gp_Pnt valpt; |
1340 | |
1341 | gp_Vec d1u,d1v; |
1342 | gp_Pnt2d p2d; |
1343 | gp_Vec2d d2d; |
1344 | |
1345 | |
1346 | for (i = 1; i <= nbedg; i++) { |
1347 | Standard_Boolean EdgeDegenere=Standard_False; |
1348 | thesegsol = listedg.Value(i); |
1349 | arcRef = thesegsol.Curve(); |
1350 | |
1351 | |
1352 | rline = new IntPatch_RLine(Standard_False); |
1353 | if(OnFirst) { |
1354 | rline->SetArcOnS1(arcRef); |
1355 | } |
1356 | else { |
1357 | rline->SetArcOnS2(arcRef); |
1358 | } |
1359 | |
1360 | // Traitement des points debut/fin du segment solution. |
1361 | |
1362 | dofirst = Standard_False; |
1363 | dolast = Standard_False; |
1364 | procf = Standard_False; |
1365 | procl = Standard_False; |
1366 | |
1367 | if (thesegsol.HasFirstPoint()) { |
1368 | dofirst = Standard_True; |
1369 | PStartf = thesegsol.FirstPoint(); |
1370 | paramf = PStartf.Parameter(); |
1371 | } |
1372 | if (thesegsol.HasLastPoint()) { |
1373 | dolast = Standard_True; |
1374 | PStartl = thesegsol.LastPoint(); |
1375 | paraml = PStartl.Parameter(); |
1376 | } |
1377 | |
1378 | if (dofirst && dolast) { // determination de la transition de la ligne |
1379 | arcRef->D1(0.5*(paramf+paraml),p2d,d2d); |
1380 | if (OnFirst) { |
1381 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1382 | } |
1383 | else { |
1384 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1385 | } |
1386 | tgline.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1387 | |
1388 | if(d1u.Magnitude()<1e-7) { //-- edge degenere ? |
1389 | EdgeDegenere=Standard_True; |
1390 | for(Standard_Integer edg=0;edg<=10;edg++) { |
1391 | arcRef->D1(paramf+(paraml-paramf)*edg*0.1,p2d,d2d); |
1392 | if (OnFirst) { |
1393 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1394 | } |
1395 | else { |
1396 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1397 | } |
1398 | |
1399 | if(d1u.Magnitude()>1e-7) { |
1400 | EdgeDegenere=Standard_False; |
1401 | } |
1402 | } |
1403 | rline = new IntPatch_RLine(Standard_False); |
1404 | if(OnFirst) { |
1405 | rline->SetArcOnS1(arcRef); |
1406 | } |
1407 | else { |
1408 | rline->SetArcOnS2(arcRef); |
1409 | } |
1410 | } |
1411 | else { |
1412 | norm2 = Quad2.Normale(valpt); |
1413 | norm1 = Quad1.Normale(valpt); |
1414 | |
1415 | if (tgline.DotCross(norm2,norm1) > 0.000000001) { |
1416 | trans1 = IntSurf_Out; |
1417 | trans2 = IntSurf_In; |
1418 | } |
1419 | else if (tgline.DotCross(norm2,norm1) < -0.000000001){ |
1420 | trans1 = IntSurf_In; |
1421 | trans2 = IntSurf_Out; |
1422 | } |
1423 | else { |
1424 | trans1 = trans2 = IntSurf_Undecided; |
1425 | } |
1426 | rline = new IntPatch_RLine(Standard_False,trans1,trans2); |
1427 | if(OnFirst) { |
1428 | rline->SetArcOnS1(arcRef); |
1429 | } |
1430 | else { |
1431 | rline->SetArcOnS2(arcRef); |
1432 | } |
1433 | } |
1434 | } |
1435 | else { |
1436 | rline = new IntPatch_RLine(Standard_False); |
1437 | if(OnFirst) { |
1438 | rline->SetArcOnS1(arcRef); |
1439 | } |
1440 | else { |
1441 | rline->SetArcOnS2(arcRef); |
1442 | } |
1443 | } |
1444 | |
1445 | if (dofirst || dolast) { |
1446 | Nblines = slin.Length(); |
1447 | for (j=1; j<=Nblines; j++) { |
1448 | const Handle(IntPatch_Line)& slinj = slin(j); |
1449 | typ = slinj->ArcType(); |
1450 | if (typ == IntPatch_Analytic) { |
1451 | Nbpts = (*((Handle(IntPatch_ALine)*)&slinj))->NbVertex(); |
1452 | } |
1453 | else if (typ == IntPatch_Restriction) { |
1454 | Nbpts = (*((Handle(IntPatch_RLine)*)&slinj))->NbVertex(); |
1455 | } |
1456 | else { |
1457 | Nbpts = (*((Handle(IntPatch_GLine)*)&slinj))->NbVertex(); |
1458 | } |
1459 | for (k=1; k<=Nbpts;k++) { |
1460 | if (typ == IntPatch_Analytic) { |
1461 | ptvtx = (*((Handle(IntPatch_ALine)*)&slinj))->Vertex(k); |
1462 | } |
1463 | else if (typ == IntPatch_Restriction) { |
1464 | ptvtx = (*((Handle(IntPatch_RLine)*)&slinj))->Vertex(k); |
1465 | } |
1466 | else { |
1467 | ptvtx = (*((Handle(IntPatch_GLine)*)&slinj))->Vertex(k); |
1468 | } |
1469 | |
1470 | if (EdgeDegenere==Standard_False && dofirst) { |
1471 | if (ptvtx.Value().Distance(PStartf.Value()) <=TolArc) { |
1472 | ptvtx.SetMultiple(Standard_True); |
1473 | if (typ == IntPatch_Analytic) { |
1474 | (*((Handle(IntPatch_ALine)*)&slinj))->Replace(k,ptvtx); |
1475 | } |
1476 | else if (typ == IntPatch_Restriction) { |
1477 | (*((Handle(IntPatch_RLine)*)&slinj))->Replace(k,ptvtx); |
1478 | } |
1479 | else { |
1480 | (*((Handle(IntPatch_GLine)*)&slinj))->Replace(k,ptvtx); |
1481 | } |
1482 | newptvtx = ptvtx; |
1483 | newptvtx.SetParameter(paramf); |
1484 | //Recalcul des transitions si point sur restriction |
1485 | |
1486 | arcRef->D1(paramf,p2d,d2d); |
1487 | if (OnFirst) { |
1488 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1489 | } |
1490 | else { |
1491 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1492 | } |
1493 | tgline.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1494 | if (ptvtx.IsOnDomS1()) { |
1495 | const Handle(Adaptor2d_HCurve2d)& thearc = ptvtx.ArcOnS1(); |
1496 | thearc->D1(ptvtx.ParameterOnArc1(),p2d,d2d); |
1497 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1498 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1499 | norm1 = d1u.Crossed(d1v); |
1500 | if(norm1.SquareMagnitude()<1e-16) { |
1501 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1502 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1503 | } |
1504 | else { |
1505 | IntSurf::MakeTransition(tgline,tgarc,norm1,TRest,TArc); |
1506 | } |
1507 | newptvtx.SetArc(Standard_True,thearc,ptvtx.ParameterOnArc1(), |
1508 | TRest,TArc); |
1509 | } |
1510 | if (ptvtx.IsOnDomS2()) { |
1511 | const Handle(Adaptor2d_HCurve2d)& thearc = ptvtx.ArcOnS2(); |
1512 | thearc->D1(ptvtx.ParameterOnArc2(),p2d,d2d); |
1513 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1514 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1515 | norm2 = d1u.Crossed(d1v); |
1516 | if(norm2.SquareMagnitude()<1e-16) { |
1517 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1518 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1519 | } |
1520 | else { |
1521 | IntSurf::MakeTransition(tgline,tgarc,norm2,TRest,TArc); |
1522 | } |
1523 | newptvtx.SetArc(Standard_False,thearc,ptvtx.ParameterOnArc2(), |
1524 | TRest,TArc); |
1525 | } |
1526 | |
1527 | rline->AddVertex(newptvtx); |
1528 | if (!procf){ |
1529 | procf=Standard_True; |
1530 | rline->SetFirstPoint(rline->NbVertex()); |
1531 | } |
1532 | } |
1533 | } |
1534 | if (EdgeDegenere==Standard_False && dolast) { |
1535 | if (ptvtx.Value().Distance(PStartl.Value()) <=TolArc) { |
1536 | ptvtx.SetMultiple(Standard_True); |
1537 | if (typ == IntPatch_Analytic) { |
1538 | (*((Handle(IntPatch_ALine)*)&slinj))->Replace(k,ptvtx); |
1539 | } |
1540 | else if (typ == IntPatch_Restriction) { |
1541 | (*((Handle(IntPatch_RLine)*)&slinj))->Replace(k,ptvtx); |
1542 | } |
1543 | else { |
1544 | (*((Handle(IntPatch_GLine)*)&slinj))->Replace(k,ptvtx); |
1545 | } |
1546 | |
1547 | newptvtx = ptvtx; |
1548 | newptvtx.SetParameter(paraml); |
1549 | //Recalcul des transitions si point sur restriction |
1550 | |
1551 | arcRef->D1(paraml,p2d,d2d); |
1552 | if (OnFirst) { |
1553 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1554 | } |
1555 | else { |
1556 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1557 | } |
1558 | tgline.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1559 | if (ptvtx.IsOnDomS1()) { |
1560 | const Handle(Adaptor2d_HCurve2d)& thearc = ptvtx.ArcOnS1(); |
1561 | thearc->D1(ptvtx.ParameterOnArc1(),p2d,d2d); |
1562 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1563 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1564 | norm1 = d1u.Crossed(d1v); |
1565 | if(norm1.SquareMagnitude()<1e-16) { |
1566 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1567 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1568 | } |
1569 | else { |
1570 | IntSurf::MakeTransition(tgline,tgarc,norm1,TRest,TArc); |
1571 | } |
1572 | newptvtx.SetArc(Standard_True,thearc,ptvtx.ParameterOnArc1(), |
1573 | TRest,TArc); |
1574 | } |
1575 | if (ptvtx.IsOnDomS2()) { |
1576 | const Handle(Adaptor2d_HCurve2d)& thearc = ptvtx.ArcOnS2(); |
1577 | thearc->D1(ptvtx.ParameterOnArc2(),p2d,d2d); |
1578 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1579 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1580 | norm2 = d1u.Crossed(d1v); |
1581 | if(norm2.SquareMagnitude()<1e-16) { |
1582 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1583 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1584 | } |
1585 | else { |
1586 | IntSurf::MakeTransition(tgline,tgarc,norm2,TRest,TArc); |
1587 | } |
1588 | newptvtx.SetArc(Standard_False,thearc,ptvtx.ParameterOnArc2(), |
1589 | TRest,TArc); |
1590 | } |
1591 | |
1592 | rline->AddVertex(newptvtx); |
1593 | if (!procl){ |
1594 | procl=Standard_True; |
1595 | rline->SetLastPoint(rline->NbVertex()); |
1596 | } |
1597 | } |
1598 | } |
1599 | } |
1600 | // Si on a traite le pt debut et/ou fin, on ne doit pas recommencer si |
1601 | // il (ils) correspond(ent) a un point multiple. |
1602 | |
1603 | if (procf) { |
1604 | dofirst = Standard_False; |
1605 | } |
1606 | if (procl) { |
1607 | dolast = Standard_False; |
1608 | } |
1609 | } |
1610 | } |
1611 | // Si on n a pas trouve le point debut et./ou fin sur une des lignes |
1612 | // d intersection, il faut quand-meme le placer sur la restriction solution |
1613 | |
1614 | if (dofirst) { |
1615 | ptvtx.SetValue(PStartf.Value(),PStartf.Tolerance(),Standard_False); |
1616 | Quad1.Parameters(PStartf.Value(),U1,V1); |
1617 | Quad2.Parameters(PStartf.Value(),U2,V2); |
1618 | ptvtx.SetParameters(U1,V1,U2,V2); |
1619 | ptvtx.SetParameter(paramf); |
1620 | if (! PStartf.IsNew()) { |
1621 | IntSurf_Transition Transline; |
1622 | IntSurf_Transition Transarc; |
1623 | ptvtx.SetVertex(OnFirst,PStartf.Vertex()); |
1624 | ptvtx.SetArc(OnFirst,PStartf.Arc(),PStartf.Parameter(), |
1625 | Transline,Transarc); |
1626 | } |
1627 | |
1628 | rline->AddVertex(ptvtx); |
1629 | rline->SetFirstPoint(rline->NbVertex()); |
1630 | } |
1631 | if (dolast) { |
1632 | ptvtx.SetValue(PStartl.Value(),PStartl.Tolerance(),Standard_False); |
1633 | Quad1.Parameters(PStartl.Value(),U1,V1); |
1634 | Quad2.Parameters(PStartl.Value(),U2,V2); |
1635 | ptvtx.SetParameters(U1,V1,U2,V2); |
1636 | ptvtx.SetParameter(paraml); |
1637 | if (! PStartl.IsNew()) { |
1638 | IntSurf_Transition Transline; |
1639 | IntSurf_Transition Transarc; |
1640 | |
1641 | ptvtx.SetVertex(OnFirst,PStartl.Vertex()); |
1642 | ptvtx.SetArc(OnFirst,PStartl.Arc(),PStartl.Parameter(), |
1643 | Transline,Transarc); |
1644 | } |
1645 | |
1646 | rline->AddVertex(ptvtx); |
1647 | rline->SetLastPoint(rline->NbVertex()); |
1648 | } |
1649 | slin.Append(rline); |
1650 | } |
1651 | } |
1652 | |
1653 | |
1654 | void ProcessRLine (IntPatch_SequenceOfLine& slin, |
1655 | // const Handle(Adaptor3d_HSurface)& Surf1, |
1656 | // const Handle(Adaptor3d_HSurface)& Surf2, |
1657 | const IntSurf_Quadric& Quad1, |
1658 | const IntSurf_Quadric& Quad2, |
1659 | const Standard_Real _TolArc) { |
1660 | |
1661 | // On cherche a placer sur les restrictions solutions les points "multiples" |
1662 | // des autres lignes d intersection |
1663 | // Pas forcemment le plus efficace : on rique de projeter plusieurs fois |
1664 | // le meme point sur la meme restriction... |
1665 | |
1666 | Standard_Real TolArc=100.0*_TolArc; |
1667 | if(TolArc>0.1) TolArc=0.1; |
1668 | |
1669 | Standard_Integer i,j,k; |
1670 | Standard_Integer Nblin,Nbvtx, Nbpt; |
1671 | #ifndef DEB |
1672 | Standard_Boolean OnFirst = Standard_False,project = Standard_False,keeppoint = Standard_False; |
1673 | #else |
1674 | Standard_Boolean OnFirst,project,keeppoint; |
1675 | #endif |
1676 | Handle(Adaptor2d_HCurve2d) arcref; |
1677 | Standard_Real paramproj,paramf,paraml; |
1678 | |
1679 | TColgp_SequenceOfPnt seq_Pnt3d; |
1680 | TColStd_SequenceOfReal seq_Real; |
1681 | |
1682 | gp_Pnt ptproj,toproj,valpt; |
1683 | |
1684 | gp_Pnt2d p2d; |
1685 | gp_Vec2d d2d; |
1686 | gp_Vec d1u,d1v,tgrest,tgarc,norm; |
1687 | IntSurf_Transition TRest,TArc; |
1688 | #ifndef DEB |
1689 | Standard_Real U =0.,V =0.; |
1690 | #else |
1691 | Standard_Real U,V; |
1692 | #endif |
1693 | IntPatch_Point Ptvtx,newptvtx; |
1694 | |
1695 | IntPatch_IType typ1,typ2; |
1696 | |
1697 | |
1698 | Nblin = slin.Length(); |
1699 | for (i=1; i<=Nblin; i++) { |
1700 | const Handle(IntPatch_Line)& slini = slin(i); |
1701 | typ1 = slini->ArcType(); |
1702 | if (typ1 == IntPatch_Restriction) { |
1703 | seq_Pnt3d.Clear(); |
1704 | seq_Real.Clear(); |
1705 | for (j=1; j<=Nblin; j++) { |
1706 | const Handle(IntPatch_Line)& slinj = slin(j); |
1707 | Nbpt = seq_Pnt3d.Length(); // important que ce soit ici |
1708 | typ2 = slinj->ArcType(); |
1709 | if (typ2 != IntPatch_Restriction) { |
1710 | |
1711 | //-- arcref = (*((Handle(IntPatch_RLine)*)&slini))->Arc(); |
1712 | //-- OnFirst = (*((Handle(IntPatch_RLine)*)&slini))->IsOnFirstSurface(); |
1713 | |
1714 | //-- DES CHOSES A FAIRE ICI |
1715 | if((*((Handle(IntPatch_RLine)*)&slini))->IsArcOnS1()) { |
1716 | OnFirst=Standard_True; |
1717 | arcref= (*((Handle(IntPatch_RLine)*)&slini))->ArcOnS1(); |
1718 | } |
1719 | else if((*((Handle(IntPatch_RLine)*)&slini))->IsArcOnS2()) { |
1720 | arcref= (*((Handle(IntPatch_RLine)*)&slini))->ArcOnS2(); |
1721 | OnFirst=Standard_False; |
1722 | } |
1723 | if ((*((Handle(IntPatch_RLine)*)&slini))->HasFirstPoint()) { |
1724 | paramf = (*((Handle(IntPatch_RLine)*)&slini))->FirstPoint().ParameterOnLine(); |
1725 | } |
1726 | else { |
1727 | // cout << "Pas de param debut sur rst solution" << endl; |
1728 | paramf = RealFirst(); |
1729 | } |
1730 | if ((*((Handle(IntPatch_RLine)*)&slini))->HasLastPoint()) { |
1731 | paraml = (*((Handle(IntPatch_RLine)*)&slini))->LastPoint().ParameterOnLine(); |
1732 | } |
1733 | else { |
1734 | // cout << "Pas de param debut sur rst solution" << endl; |
1735 | paraml = RealLast(); |
1736 | } |
1737 | |
1738 | if (typ2 == IntPatch_Analytic) { |
1739 | Nbvtx = (*((Handle(IntPatch_ALine)*)&slinj))->NbVertex(); |
1740 | } |
1741 | else { |
1742 | Nbvtx = (*((Handle(IntPatch_GLine)*)&slinj))->NbVertex(); |
1743 | } |
1744 | |
1745 | |
1746 | Standard_Boolean EdgeDegenere=Standard_True; |
1747 | for(Standard_Integer edg=0;EdgeDegenere && edg<=10;edg++) { |
1748 | arcref->D1(paramf+(paraml-paramf)*edg*0.1,p2d,d2d); |
1749 | if (OnFirst) { |
1750 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1751 | } |
1752 | else { |
1753 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1754 | } |
1755 | if(d1u.Magnitude()>1e-7) { |
1756 | EdgeDegenere=Standard_False; |
1757 | } |
1758 | } |
1759 | |
1760 | for (k=1; EdgeDegenere==Standard_False && k<=Nbvtx; k++) { |
1761 | if (typ2 == IntPatch_Analytic) { |
1762 | Ptvtx = (*((Handle(IntPatch_ALine)*)&slinj))->Vertex(k); |
1763 | } |
1764 | else { |
1765 | Ptvtx = (*((Handle(IntPatch_GLine)*)&slinj))->Vertex(k); |
1766 | } |
1767 | if ((OnFirst && !Ptvtx.IsOnDomS1()) || |
1768 | (!OnFirst && !Ptvtx.IsOnDomS2())) { |
1769 | // Si OnFirst && OnDomS1, c est qu on est a une extremite |
1770 | // ca doit etre traite par Process Segment... |
1771 | project = Standard_True; |
1772 | keeppoint = Standard_False; |
1773 | toproj = Ptvtx.Value(); |
1774 | |
1775 | Standard_Integer jj; |
1776 | for (jj = 1; jj <= Nbpt; jj++) { |
1777 | //for (Standard_Integer jj = 1; jj <= Nbpt; jj++) { |
1778 | if (toproj.Distance(seq_Pnt3d(jj)) < _TolArc) { |
1779 | project = Standard_False; |
1780 | break; |
1781 | } |
1782 | } |
1783 | if (project) { //-- il faut projeter pour trouver le point sur la rline. |
1784 | if (OnFirst) { |
1785 | Ptvtx.ParametersOnS1(U,V); |
1786 | } |
1787 | else { |
1788 | Ptvtx.ParametersOnS2(U,V); |
1789 | } |
1790 | |
1791 | project = IntPatch_HInterTool::Project(arcref,gp_Pnt2d(U,V), |
1792 | paramproj,p2d); |
1793 | |
1794 | if (project) { |
1795 | if (OnFirst) { |
1796 | ptproj = Quad1.Value(p2d.X(),p2d.Y()); |
1797 | } |
1798 | else { |
1799 | ptproj = Quad2.Value(p2d.X(),p2d.Y()); |
1800 | } |
1801 | if ((toproj.Distance(ptproj) <=100*TolArc) && |
1802 | (paramproj >= paramf) && (paramproj <= paraml)){ |
1803 | newptvtx = Ptvtx; |
1804 | newptvtx.SetParameter(paramproj); |
1805 | keeppoint = Standard_True; |
1806 | seq_Pnt3d.Append(toproj); |
1807 | seq_Real.Append(paramproj); |
1808 | |
1809 | //-- verifier que si la restriction arcref est trouvee, elle porte ce vertex |
1810 | for (int ri=1; ri<=Nblin; ri++) { |
1811 | const Handle(IntPatch_Line)& slinri = slin(ri); |
1812 | if (slinri->ArcType() == IntPatch_Restriction) { |
1813 | if(OnFirst && (*((Handle(IntPatch_RLine)*)&slinri))->IsArcOnS1()) { |
1814 | if(arcref == (*((Handle(IntPatch_RLine)*)&slinri))->ArcOnS1()) { |
1815 | (*((Handle(IntPatch_RLine)*)&slinri))->AddVertex(newptvtx); |
1816 | //printf("\n ImpImpIntersection_0.gxx CAS1 \n"); |
1817 | } |
1818 | } |
1819 | else if(OnFirst==Standard_False && (*((Handle(IntPatch_RLine)*)&slinri))->IsArcOnS2()) { |
1820 | if(arcref == (*((Handle(IntPatch_RLine)*)&slinri))->ArcOnS2()) { |
1821 | (*((Handle(IntPatch_RLine)*)&slinri))->AddVertex(newptvtx); |
1822 | //printf("\n ImpImpIntersection_0.gxx CAS2 \n"); |
1823 | } |
1824 | } |
1825 | } |
1826 | } |
1827 | // -- -------------------------------------------------- |
1828 | } |
1829 | } |
1830 | } |
1831 | else { |
1832 | keeppoint = Standard_True; |
1833 | newptvtx = Ptvtx; |
1834 | newptvtx.SetParameter(seq_Real(jj)); |
1835 | } |
1836 | if (keeppoint) { |
1837 | Ptvtx.SetMultiple(Standard_True); |
1838 | newptvtx.SetMultiple(Standard_True); |
1839 | |
1840 | if (typ2 == IntPatch_Analytic) { |
1841 | (*((Handle(IntPatch_ALine)*)&slinj))->Replace(k,Ptvtx); |
1842 | } |
1843 | else { |
1844 | (*((Handle(IntPatch_GLine)*)&slinj))->Replace(k,Ptvtx); |
1845 | } |
1846 | |
1847 | if (Ptvtx.IsOnDomS1() || Ptvtx.IsOnDomS2()) { |
1848 | |
1849 | arcref->D1(newptvtx.ParameterOnLine(),p2d,d2d); |
1850 | |
1851 | if (OnFirst) { // donc OnDomS2 |
1852 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1853 | tgrest.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1854 | |
1855 | const Handle(Adaptor2d_HCurve2d)& thearc = Ptvtx.ArcOnS2(); |
1856 | thearc->D1(Ptvtx.ParameterOnArc2(),p2d,d2d); |
1857 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1858 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1859 | norm = d1u.Crossed(d1v); //Quad2.Normale(valpt); |
1860 | if(norm.SquareMagnitude()<1e-16) { |
1861 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1862 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1863 | } |
1864 | else { |
1865 | IntSurf::MakeTransition(tgrest,tgarc,norm,TRest,TArc); |
1866 | } |
1867 | newptvtx.SetArc(Standard_False,thearc, |
1868 | Ptvtx.ParameterOnArc2(),TRest,TArc); |
1869 | |
1870 | } |
1871 | else { // donc OnDomS1 |
1872 | Quad2.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1873 | tgrest.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1874 | |
1875 | const Handle(Adaptor2d_HCurve2d)& thearc = Ptvtx.ArcOnS1(); |
1876 | thearc->D1(Ptvtx.ParameterOnArc1(),p2d,d2d); |
1877 | Quad1.D1(p2d.X(),p2d.Y(),valpt,d1u,d1v); |
1878 | tgarc.SetLinearForm(d2d.X(),d1u,d2d.Y(),d1v); |
1879 | norm = d1u.Crossed(d1v); //Quad1.Normale(valpt); |
1880 | if(norm.SquareMagnitude()<1e-16) { |
1881 | TRest.SetValue(Standard_True,IntSurf_Undecided); |
1882 | TArc.SetValue(Standard_True,IntSurf_Undecided); |
1883 | } |
1884 | else { |
1885 | IntSurf::MakeTransition(tgrest,tgarc,norm,TRest,TArc); |
1886 | } |
1887 | newptvtx.SetArc(Standard_True,thearc, |
1888 | Ptvtx.ParameterOnArc1(),TRest,TArc); |
1889 | } |
1890 | } //-- if (Ptvtx.IsOnDomS1() || Ptvtx.IsOnDomS2()) |
1891 | |
1892 | (*((Handle(IntPatch_RLine)*)&slini))->AddVertex(newptvtx); |
1893 | |
1894 | } //-- if (keeppoint) |
1895 | } //-- if ((OnFirst && !Ptvtx.IsOnDomS1())||(!OnFirst && !Ptvtx.IsOnDomS2())) |
1896 | } //-- boucle sur les vertex |
1897 | } //-- if (typ2 != IntPatch_Restriction) |
1898 | } //-- for (j=1; j<=Nblin; j++) |
1899 | } //-- if (typ1 == IntPatch_Restriction) |
1900 | } //-- for (i=1; i<=Nblin; i++) |
1901 | } |