Integration of OCCT 6.5.0 from SVN
[occt.git] / src / Bisector / Bisector_BisecAna.cxx
CommitLineData
7fd59977 1// File: Bisector_BisecAna.cxx
2// Created: Mon Oct 19 10:34:33 1992
3// Author: Remi GILET
4// <reg@phobox>
5
6// Modified by skv - Fri Jul 1 16:23:17 2005 IDEM(Airbus)
7// Modified by skv - Wed Jul 7 17:21:09 2004 IDEM(Airbus)
8
9#include <Bisector_BisecAna.ixx>
10#include <Geom2d_Line.hxx>
11#include <Geom2d_Circle.hxx>
12#include <Geom2d_Parabola.hxx>
13#include <Geom2d_Hyperbola.hxx>
14#include <Geom2d_Ellipse.hxx>
15#include <Geom2dAdaptor_Curve.hxx>
16#include <Geom2d_TrimmedCurve.hxx>
17#include <GccInt_IType.hxx>
18#include <GccInt_BLine.hxx>
19#include <GccAna_Circ2dBisec.hxx>
20#include <GccAna_Pnt2dBisec.hxx>
21#include <GccAna_CircLin2dBisec.hxx>
22#include <GccAna_Lin2dBisec.hxx>
23#include <GccAna_CircPnt2dBisec.hxx>
24#include <GccAna_LinPnt2dBisec.hxx>
25#include <gp.hxx>
26#include <gp_Pnt2d.hxx>
27#include <ElCLib.hxx>
28#include <StdFail_NotDone.hxx>
29#include <IntAna2d_AnaIntersection.hxx>
30#include <IntAna2d_IntPoint.hxx>
31#include <IntRes2d_Domain.hxx>
32#include <IntRes2d_Domain.hxx>
33#include <IntRes2d_IntersectionSegment.hxx>
34#include <Geom2dInt_GInter.hxx>
35#include <Standard_NotImplemented.hxx>
36#include <Precision.hxx>
37
38static Standard_Boolean Degenerate(Handle(GccInt_Bisec)& aBisector,
39 const Standard_Real Tolerance);
40
41//=============================================================================
42//function :
43//=============================================================================
44Bisector_BisecAna::Bisector_BisecAna()
45{
46}
47
48//=============================================================================
49// calcul de la distance du point a la bissectrice. +
50// et orientation de la bissectrice. +
51// apoint : point de passage. +
52// abisector : la bissectrice calculee. +
53// afirstvector : premier vecteur. \ +
54// asecondvector : deuxieme vecteur./ pour choisir le bon cadran. +
55// adirection : indique si bissectrice interieure ou exterieure. +
56// aparameter : out : le parametre de depart de la bissectrice. +
57// asense : out : le sens de la bissectrice. +
58// astatus : out : indique si on garde la bissectrice. +
59//=============================================================================
60Standard_Real Bisector_BisecAna::Distance (
61 const gp_Pnt2d& apoint,
62 const Handle(GccInt_Bisec)& abisector,
63 const gp_Vec2d& afirstvector ,
64 const gp_Vec2d& asecondvector,
65 const Standard_Real adirection,
66 Standard_Real& aparameter,
67 Standard_Boolean& asense,
68 Standard_Boolean& astatus)
69{
70 astatus = Standard_True;
71
72 gp_Hypr2d gphyperbola;
73 gp_Parab2d gpparabola ;
74 gp_Elips2d gpellipse ;
75 gp_Circ2d gpcircle ;
76 gp_Lin2d gpline ;
77
78 Standard_Real distance = 0.;
79 gp_Vec2d tangent;
80 gp_Pnt2d point;
81
82 GccInt_IType type = abisector->ArcType();
83
84 if (type == GccInt_Lin) {
85 gpline = abisector->Line();
86 aparameter = ElCLib::Parameter(gpline,apoint);
87 ElCLib::D1(aparameter,gpline,point,tangent);
88 }
89 else if (type == GccInt_Cir) {
90 gpcircle = abisector->Circle();
91 aparameter = ElCLib::Parameter(gpcircle,apoint);
92 ElCLib::D1(aparameter,gpcircle,point,tangent);
93 }
94 else if (type == GccInt_Hpr) {
95 gphyperbola = abisector->Hyperbola();
96 aparameter = ElCLib::Parameter(gphyperbola,apoint);
97 ElCLib::D1(aparameter,gphyperbola,point,tangent);
98 }
99 else if (type == GccInt_Par) {
100 gpparabola = abisector->Parabola();
101 aparameter = ElCLib::Parameter(gpparabola,apoint);
102 ElCLib::D1(aparameter,gpparabola,point,tangent);
103 }
104 else if (type == GccInt_Ell) {
105 gpellipse = abisector->Ellipse();
106 aparameter = ElCLib::Parameter(gpellipse,apoint);
107 ElCLib::D1(aparameter,gpellipse,point,tangent);
108 }
109
110 distance = apoint.Distance(point);
111
112 gp_Dir2d afirstdir (afirstvector);
113 gp_Dir2d aseconddir(asecondvector);
114 gp_Dir2d tangdir (tangent);
115 gp_Dir2d secdirrev = aseconddir.Reversed();
116
117
118// 1er passage pour savoir si la courbe est dans le bon cadran
119
120 if(asense) {
121 // le status n est determiner que dans le cas oncurve ie:
122 // la tangente a la bissectrice est bisectrice des deux vecteurs.
123 Standard_Real SinPlat = 1.e-3;
124 if (Abs(afirstdir^aseconddir) < SinPlat) { //plat
125 if (afirstdir*aseconddir >= 0.0) { //tangente confondues
126 // bonne si le produit scalaire est proche de 1.
127 if (Abs(tangdir*afirstdir) < 0.5) {
128 astatus = Standard_False;
129 }
130 }
131 else { // tangentes opposees.
132 // bonne si le produit scalaire proche de 0.
133 if (Abs(tangdir*afirstdir) > 0.5 ) {
134 astatus = Standard_False;
135 }
136 }
137 }
138 else if ((afirstdir^tangdir)*(tangdir^aseconddir) < -1.E-8) {
139 astatus = Standard_False;
140 }
141 }
142 else {
143 asense = Standard_True;
144
145// Modified by Sergey KHROMOV - Tue Oct 22 16:35:51 2002 Begin
146// Replacement of -1.E-8 for a tolerance 1.e-4
147 Standard_Real aTol = 1.e-4;
148
149 if ((afirstdir^secdirrev)*adirection < -0.1) { // rentrant
150 if((afirstdir^tangdir)*adirection < aTol &&
151 (secdirrev^tangdir)*adirection < aTol) asense = Standard_False;
152 }
153 else if((afirstdir^secdirrev)*adirection > 0.1) { // sortant
154 if((afirstdir^tangdir)*adirection < aTol ||
155 (secdirrev^tangdir)*adirection < aTol) asense = Standard_False;
156 }
157 else { // plat
158 if (afirstdir.Dot(secdirrev) > 0.) { // tangent
159 if ((afirstdir^tangdir)*adirection < 0.) asense = Standard_False;
160 }
161 else{ // rebroussement
162// Modified by Sergey KHROMOV - Thu Oct 31 14:16:53 2002
163// if ((afirstdir.Dot(tangdir))*adirection > 0.) asense = Standard_False;
164 if (afirstdir.Dot(tangdir) < 0.) asense = Standard_False;
165// Modified by Sergey KHROMOV - Thu Oct 31 14:16:54 2002
166 }
167 }
168// Modified by Sergey KHROMOV - Tue Oct 22 16:35:51 2002 End
169 }
170 return distance;
171}
172
173//===========================================================================
174// calcul de la bissectrice entre deux courbes issue d un point. +
175// +
176// afirstcurve : \ courbes entre lesquelles on veut calculer la +
177// asecondcurve : / bissectrice. +
178// apoint : point par lequel doit passer la bissectrice. +
179// afirstvector : \ vecteurs pour determiner le secteur dans lequel +
180// asecondvector : / la bissectrice doit se trouver. +
181// adirection : indique le cote de la bissectrice a conserver. +
182// tolerance : seuil a partir duquel les bisectrices sont degenerees+
183//===========================================================================
184void Bisector_BisecAna::Perform(const Handle(Geom2d_Curve)& afirstcurve ,
185 const Handle(Geom2d_Curve)& asecondcurve ,
186 const gp_Pnt2d& apoint ,
187 const gp_Vec2d& afirstvector ,
188 const gp_Vec2d& asecondvector ,
189 const Standard_Real adirection ,
190 const Standard_Real tolerance ,
191 const Standard_Boolean oncurve )
192{
193
194 Standard_Boolean ok;
195 Standard_Real distanceptsol,parameter,firstparameter =0.;
196 Standard_Boolean thesense = Standard_False,sense,theSense;
197 Standard_Real distancemini;
198 Standard_Integer nbsolution;
199 Standard_Real PreConf = Precision::Confusion();
200
201 Handle(Standard_Type) type1 = afirstcurve->DynamicType();
202 Handle(Standard_Type) type2 = asecondcurve->DynamicType();
203 Handle(Geom2d_Curve) CurveF;
204 Handle(Geom2d_Curve) CurveE;
205 Handle(GccInt_Bisec) TheSol;
206
207 gp_Vec2d tan1 = afirstcurve->DN(afirstcurve->LastParameter (),1);
208 gp_Vec2d tan2 = asecondcurve->DN(asecondcurve->FirstParameter(),1);
209 tan1.Reverse();
210
211 if (type1 == STANDARD_TYPE(Geom2d_TrimmedCurve))
212 CurveF = Handle(Geom2d_TrimmedCurve)::DownCast(afirstcurve)->BasisCurve();
213 else
214 CurveF = afirstcurve;
215
216 if (type2 == STANDARD_TYPE(Geom2d_TrimmedCurve))
217 CurveE = Handle(Geom2d_TrimmedCurve)::DownCast(asecondcurve)->BasisCurve();
218 else
219 CurveE = asecondcurve;
220
221 type1 = CurveF->DynamicType();
222 type2 = CurveE->DynamicType();
223 Standard_Integer cas =0;
224 gp_Circ2d circle1,circle2;
225 gp_Lin2d line1,line2;
226
227//=============================================================================
228// Determination de la nature des arguments. +
229//=============================================================================
230
231 if (type1 == STANDARD_TYPE(Geom2d_Circle)) {
232 if (type2 == STANDARD_TYPE(Geom2d_Circle)) {
233 cas = 1;
234 Handle(Geom2d_Circle) C1 = Handle(Geom2d_Circle)::DownCast(CurveF);
235 circle1 = C1->Circ2d();
236 Handle(Geom2d_Circle) C2 = Handle(Geom2d_Circle)::DownCast(CurveE);
237 circle2 = C2->Circ2d();
238 }
239 else if (type2 == STANDARD_TYPE(Geom2d_Line)) {
240 cas = 2;
241 Handle(Geom2d_Circle) C1 = Handle(Geom2d_Circle)::DownCast(CurveF);
242 circle1 = C1->Circ2d();
243 Handle(Geom2d_Line) L2 = Handle(Geom2d_Line)::DownCast(CurveE);
244 line2 = L2->Lin2d();
245 }
246 else {
247 cout << "Not yet implemented" << endl;
248 }
249 }
250 else if (type1 == STANDARD_TYPE(Geom2d_Line)) {
251 if (type2 == STANDARD_TYPE(Geom2d_Circle)) {
252 cas = 2;
253 Handle(Geom2d_Circle) C1 = Handle(Geom2d_Circle)::DownCast(CurveE);
254 circle1 = C1->Circ2d();
255 Handle(Geom2d_Line) L2 = Handle(Geom2d_Line)::DownCast(CurveF);
256 line2 = L2->Lin2d();
257 }
258 else if (type2 == STANDARD_TYPE(Geom2d_Line)) {
259 cas = 3;
260 Handle(Geom2d_Line) L1 = Handle(Geom2d_Line)::DownCast(CurveF);
261 line1 = L1->Lin2d();
262 Handle(Geom2d_Line) L2 = Handle(Geom2d_Line)::DownCast(CurveE);
263 line2 = L2->Lin2d();
264 }
265 else {
266 cout << "Not yet implemented" << endl;
267 }
268 }
269 else {
270 cout << "Not yet implemented" << endl;
271 }
272
273 switch(cas) {
274
275//=============================================================================
276// Bissectrice cercle - cercle. +
277//=============================================================================
278
279 case 1 : {
280 Standard_Real radius1 = circle1.Radius();
281 Standard_Real radius2 = circle2.Radius();
282
283 //-----------------------------------------------------
284 // Cas particulier ou les deux cercles sont confondus.
285 //-----------------------------------------------------
286 if (circle1.Location().IsEqual(circle2.Location(),PreConf)&&
287 (Abs(radius1 - radius2) <= PreConf)){
288 gp_Pnt2d P1 = afirstcurve ->Value(afirstcurve ->LastParameter());
289 gp_Pnt2d P2 = asecondcurve->Value(asecondcurve->FirstParameter());
290 gp_Pnt2d PMil;
291 gp_Lin2d line;
292 PMil = gp_Pnt2d((P1.X() + P2.X())/2.,
293 (P1.Y() + P2.Y())/2.);
294// Modified by skv - Fri Jul 1 16:23:32 2005 IDEM(Airbus) Begin
295// line = gp_Lin2d(PMil,
296// gp_Dir2d(circle1.Location().X() - PMil.X(),
297// circle1.Location().Y() - PMil.Y()));
298 if (!circle1.Location().IsEqual(PMil,PreConf)) {
299 // PMil doesn't coinside with the circle location.
300 line = gp_Lin2d(PMil,
301 gp_Dir2d(circle1.Location().X() - PMil.X(),
302 circle1.Location().Y() - PMil.Y()));
303 } else if (radius1 >= PreConf) {
304 // PMil coinsides with the circle location and radius is greater then 0.
305 line = gp_Lin2d(circle1.Location(),
306 gp_Dir2d(P1.Y() - circle1.Location().Y(),
307 circle1.Location().X() - P1.X()));
308 } else {
309 // radius is equal to 0. No matter what direction to chose.
310 line = gp_Lin2d(circle1.Location(), gp_Dir2d(1., 0.));
311 }
312// Modified by skv - Fri Jul 1 16:23:32 2005 IDEM(Airbus) End
313 Handle(GccInt_Bisec) solution = new GccInt_BLine(line);
314 sense = Standard_False;
315// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
316// distanceptsol = Distance(apoint,solution,
317// afirstvector,asecondvector,
318// adirection,parameter,sense,ok);
319 if (oncurve)
320 distanceptsol = Distance(apoint,solution,
321 tan2,tan1,
322 adirection,parameter,sense,ok);
323 else
324 distanceptsol = Distance(apoint,solution,
325 afirstvector,asecondvector,
326 adirection,parameter,sense,ok);
327// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
328 Handle(Geom2d_Curve) bisectorcurve = new Geom2d_Line(line);
329 if (!sense)
330 thebisector =new Geom2d_TrimmedCurve(bisectorcurve,
331 parameter,
332 - Precision::Infinite());
333 else {
334 Standard_Real parameter2;
335 parameter2 = ElCLib::Parameter(line,circle1.Location());
336 parameter2 += 1.e-8;
337 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
338 parameter,
339 parameter2);
340 }
341 break;
342 } //fin cas part cercles confondus.
343
344 if (radius1 < radius2) {
345 gp_Circ2d circle = circle1;
346 circle1 = circle2;
347 circle2 = circle;
348
349 Standard_Real radius = radius1;
350 radius1 = radius2;
351 radius2 = radius;
352 }
353
354 // petit recadrage des cercles. dans le cas ou les cercles
355 // sont OnCurve , si ils sont presque tangents on les rends
356 // tangents.
357 Standard_Real EntreAxe = circle1.Location().Distance(circle2.Location());
358 Standard_Real D1 = 0.5*(radius1 - EntreAxe - radius2);
359 Standard_Boolean CirclesTangent = Standard_False;
360
361// Modified by Sergey KHROMOV - Thu Oct 31 12:42:21 2002 End
362// if ( oncurve && Abs(D1) < PreConf) {
363 if ( oncurve && Abs(D1) < PreConf && tan1.IsParallel(tan2, 1.e-8)) {
364// Modified by Sergey KHROMOV - Thu Oct 31 12:42:22 2002 Begin
365 // C2 inclus dans C1 et tangent.
366 circle1.SetRadius(radius1 - D1);
367 circle2.SetRadius(radius2 + D1);
368 CirclesTangent = Standard_True;
369 }
370 else {
371 D1 = 0.5*(radius1 - EntreAxe + radius2);
372// Modified by Sergey KHROMOV - Thu Oct 31 12:44:24 2002 Begin
373// if (oncurve && Abs(D1) < PreConf) {
374 if (oncurve && Abs(D1) < PreConf && tan1.IsParallel(tan2, 1.e-8)) {
375// Modified by Sergey KHROMOV - Thu Oct 31 12:44:25 2002 End
376 // C2 et C1 tangents et disjoints.
377 circle1.SetRadius(radius1 - D1);
378 circle2.SetRadius(radius2 - D1);
379 CirclesTangent = Standard_True;
380 }
381 } // fin recadrage.
382
383 GccAna_Circ2dBisec Bisector(circle1,circle2);
384
385 distancemini = Precision::Infinite();
386
387 if (Bisector.IsDone()) {
388 nbsolution = Bisector.NbSolutions();
389 for (Standard_Integer i = 1; i <= nbsolution; i++) {
390 Handle(GccInt_Bisec) solution = Bisector.ThisSolution(i);
391 Degenerate(solution,tolerance);
392 sense = Standard_True;
393 if (oncurve) {
394 distanceptsol = Distance(apoint,solution,
395 tan1,tan2,
396 adirection,parameter,sense,ok);
397 }
398 else {ok = Standard_True;}
399
400 theSense = sense;
401 if (ok) {
402 sense = Standard_False;
403// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
404// distanceptsol = Distance(apoint,solution,
405// afirstvector,asecondvector,
406// adirection,parameter,sense,ok);
407 if (oncurve)
408 distanceptsol = Distance(apoint,solution,
409 tan2,tan1,
410 adirection,parameter,sense,ok);
411 else
412 distanceptsol = Distance(apoint,solution,
413 afirstvector,asecondvector,
414 adirection,parameter,sense,ok);
415// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
416 if (distanceptsol <= distancemini) {
417 TheSol = solution;
418 firstparameter = parameter;
419 thesense = sense;
420 distancemini = distanceptsol;
421 }
422 }
423 }
424 if (!TheSol.IsNull()) {
425 Handle(Geom2d_Curve) bisectorcurve;
426 GccInt_IType type = TheSol->ArcType();
427 if (type == GccInt_Lin) {
428 gp_Lin2d gpline = TheSol->Line();
429 bisectorcurve = new Geom2d_Line(gpline);
430
431 Standard_Real secondparameter = Precision::Infinite();
432 if (!thesense) secondparameter = - Precision::Infinite();
433
434 if (oncurve) {
435 // bisectrice droite et oncurve
436 // soit cassure entre deux cercles de meme rayon soit cercles tangent.
437
438 // si tangent plat et que la bissectrice est du cote de la concavite
439 // d un des cercle . la bissectrice est un segment du point commun au
440 // premier des 2 centre de cercle qu elle rencontre.
441 // dan ce cas il est important de mettre un segmnent pour les
442 // intersection dans Tool2d.
443
444 if (CirclesTangent) {
445 // Modified by skv - Tue Apr 13 17:23:31 2004 IDEM(Airbus) Begin
446 // Trying to correct the line if the distance between it
447 // and the reference point is too big.
448 if (distancemini > tolerance) {
449 gp_Pnt2d aPloc = gpline.Location();
450 gp_Dir2d aNewDir(apoint.XY() - aPloc.XY());
451 gp_Lin2d aNewLin(aPloc, aNewDir);
452 gp_Pnt2d aCC2 = circle2.Location();
453 Standard_Real aNewDMin = aNewLin.Distance(apoint);
454 Standard_Real aTolConf = 1.e-3;
455 // Hope, aNewDMin is equal to 0...
456
457 if (aNewLin.Distance(aCC2) <= aTolConf) {
458 distancemini = aNewDMin;
459 firstparameter = ElCLib::Parameter(aNewLin, apoint);
460 bisectorcurve = new Geom2d_Line(aNewLin);
461 }
462 }
463 // Modified by skv - Tue Apr 13 17:23:32 2004 IDEM(Airbus) End
464 if (tan1.Dot(tan2) < 0.) {
465 // plat et nom rebroussement.
466 Standard_Real Par1 = ElCLib::Parameter(gpline, circle1.Location());
467 Standard_Real Par2 = ElCLib::Parameter(gpline, circle2.Location());
468 Standard_Real MinPar = Min(Par1,Par2);
469 Standard_Real MaxPar = Max(Par1,Par2);
470
471 if (!thesense) {
472 if (MaxPar < firstparameter)
473 secondparameter = MaxPar - 1.E-8;
474 else if (MinPar < firstparameter)
475 secondparameter = MinPar - 1.E-8;
476 }
477 else {
478 if (MinPar > firstparameter)
479 secondparameter = MinPar + 1.E-8;
480 else if (MaxPar > firstparameter)
481 secondparameter = MaxPar + 1.E-8;
482 }
483 }
484 }
485 }
486
487 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
488 firstparameter,
489 secondparameter);
490 }
491 else if (type == GccInt_Cir) {
492 bisectorcurve = new Geom2d_Circle(TheSol->Circle());
493 if (!thesense)
494 thebisector = new Geom2d_TrimmedCurve
495 (bisectorcurve,firstparameter-2.0*PI,firstparameter,thesense);
496 else
497 thebisector = new Geom2d_TrimmedCurve
498 (bisectorcurve,firstparameter,firstparameter+2.0*PI,thesense);
499 }
500 else if (type == GccInt_Hpr) {
501 bisectorcurve = new Geom2d_Hyperbola(TheSol->Hyperbola());
502 if (!thesense)
503 thebisector = new Geom2d_TrimmedCurve
504 (bisectorcurve,firstparameter, - Precision::Infinite());
505 else
506 thebisector = new Geom2d_TrimmedCurve
507 (bisectorcurve,firstparameter,Precision::Infinite());
508 }
509 else if (type == GccInt_Ell) {
510 bisectorcurve = new Geom2d_Ellipse(TheSol->Ellipse());
511 if (!thesense)
512 thebisector = new Geom2d_TrimmedCurve
513 (bisectorcurve,firstparameter-2.0*PI,firstparameter,thesense);
514 else
515 thebisector = new Geom2d_TrimmedCurve
516 (bisectorcurve,firstparameter,firstparameter+2.0*PI,thesense);
517 }
518 }
519 }
520 }
521 break;
522
523//=============================================================================
524// Bissectrice cercle - droite. +
525//=============================================================================
526
527 case 2 : {
528 // petit recadrage des cercles. dans le cas OnCurve.
529 // Si le cercle et la droite sont presque tangents on les rends
530 // tangents.
531 if (oncurve) {
532 Standard_Real radius1 = circle1.Radius();
533 Standard_Real D1 = (line2.Distance(circle1.Location()) - radius1);
534// Modified by Sergey KHROMOV - Wed Oct 30 14:48:43 2002 Begin
535// if (Abs(D1) < PreConf) {
536 if (Abs(D1) < PreConf && tan1.IsParallel(tan2, 1.e-8)) {
537// Modified by Sergey KHROMOV - Wed Oct 30 14:48:44 2002 End
538 circle1.SetRadius(radius1+D1);
539 }
540 }
541
542 GccAna_CircLin2dBisec Bisector(circle1,line2);
543
544 distancemini = Precision::Infinite();
545
546 if (Bisector.IsDone()) {
547 nbsolution = Bisector.NbSolutions();
548 for (Standard_Integer i = 1; i <= nbsolution; i++) {
549 Handle(GccInt_Bisec) solution = Bisector.ThisSolution(i);
550 Degenerate(solution,tolerance);
551 sense = Standard_True;
552 distanceptsol = Distance(apoint,solution,tan1,tan2,
553 adirection,parameter,sense,ok);
554 theSense = sense;
555 if (ok || !oncurve) {
556 sense = Standard_False;
557// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
558// distanceptsol = Distance(apoint,solution,
559// afirstvector,asecondvector,
560// adirection,parameter,sense,ok);
561 if (oncurve)
562 distanceptsol = Distance(apoint,solution,
563 tan2,tan1,
564 adirection,parameter,sense,ok);
565 else
566 distanceptsol = Distance(apoint,solution,
567 afirstvector,asecondvector,
568 adirection,parameter,sense,ok);
569// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
570 if (distanceptsol <= distancemini) {
571 TheSol = solution;
572 firstparameter = parameter;
573 thesense = sense;
574 distancemini = distanceptsol+1.e-8;
575 }
576 }
577 }
578 if (!TheSol.IsNull()) {
579 GccInt_IType type = TheSol->ArcType();
580 Handle(Geom2d_Curve) bisectorcurve;
581 if (type == GccInt_Lin) {
582 // -----------------------------------------------------------------
583 // Si la bisectrice est une ligne
584 // => la droite est tangente au cercle.
585 // Si La portion de bisectrice qui nous interresse est du cote
586 // du centre.
587 // => la bisectrice est limitee par le point et le centre du
588 // cercle.
589 // Remarque : Dans ce dernier cas la bisectrice est en fait une
590 // parabole degeneree.
591 // -----------------------------------------------------------------
592 gp_Pnt2d circlecenter;
593 gp_Lin2d gpline;
594 Standard_Real secondparameter;
595
596 circlecenter = circle1.Location();
597 gpline = TheSol->Line();
598 secondparameter = ElCLib::Parameter(gpline, circlecenter);
599 bisectorcurve = new Geom2d_Line(gpline);
600
601 if (!thesense) {
602 if (secondparameter > firstparameter) {
603 secondparameter = - Precision::Infinite();
604 }
605 else {
606 secondparameter = secondparameter - 1.E-8;
607 }
608 }
609 else {
610 if (secondparameter < firstparameter) {
611 secondparameter = Precision::Infinite();
612 }
613 else {
614 secondparameter = secondparameter + 1.E-8;
615 }
616 }
617
618 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
619 firstparameter,
620 secondparameter);
621 }
622 else if (type == GccInt_Par) {
623 bisectorcurve = new Geom2d_Parabola(TheSol->Parabola());
624 if (!thesense)
625 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
626 firstparameter,
627 - Precision::Infinite());
628 else
629 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
630 firstparameter,
631 Precision::Infinite());
632 }
633 }
634 }
635 }
636 break;
637
638//=============================================================================
639// Bissectrice droite - droite. +
640//=============================================================================
641 case 3 : {
642 gp_Dir2d Direc1(line1.Direction());
643 gp_Dir2d Direc2(line2.Direction());
644 gp_Lin2d line;
645 distancemini = Precision::Infinite();
646
647// Modified by Sergey KHROMOV - Tue Sep 10 15:58:43 2002 Begin
648// Change to the same criterion as in MAT2d_Circuit.cxx:
649// method MAT2d_Circuit::InitOpen(..)
650// if (Direc1.IsParallel(Direc2,RealEpsilon())) {
651 if (Direc1.IsParallel(Direc2,1.e-8)) {
652// Modified by Sergey KHROMOV - Tue Sep 10 15:58:45 2002 End
653 if (line1.Distance(line2.Location())/2. <= Precision::Confusion())
654 line = gp_Lin2d(apoint,gp_Dir2d(-line1.Direction().Y(),
655 line1.Direction().X()));
656 else
657 line = gp_Lin2d(apoint,line2.Direction());
658
659 Handle(GccInt_Bisec) solution = new GccInt_BLine(line);
660// Modified by skv - Wed Jul 7 17:21:09 2004 IDEM(Airbus) Begin
661// sense = Standard_True;
662// distanceptsol = Distance(apoint,solution,
663// tan1,tan2,
664// adirection,parameter,sense,ok);
665// theSense = sense;
666// if (ok || !oncurve) {
667 sense = Standard_False;
668// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
669// distanceptsol = Distance(apoint,solution,
670// afirstvector,asecondvector,
671// adirection,parameter,sense,ok);
672 if (oncurve)
673 distanceptsol = Distance(apoint,solution,
674 tan2,tan1,
675 adirection,parameter,sense,ok);
676 else
677 distanceptsol = Distance(apoint,solution,
678 afirstvector,asecondvector,
679 adirection,parameter,sense,ok);
680// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
681// if (distanceptsol <= distancemini) {
682 firstparameter = parameter;
683 Handle(Geom2d_Curve) bisectorcurve;
684 bisectorcurve = new Geom2d_Line(line);
685 if (!sense)
686 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
687 firstparameter,
688 - Precision::Infinite());
689 else
690 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
691 firstparameter,
692 Precision::Infinite());
693// }
694// }
695// Modified by skv - Wed Jul 7 17:21:09 2004 IDEM(Airbus) End
696 }
697 else {
698 gp_Lin2d l(apoint,gp_Dir2d(Direc2.XY()-Direc1.XY()));
699 Handle(GccInt_Bisec) solution = new GccInt_BLine(l);
700 Standard_Boolean ok;
701 sense = Standard_False;
702// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
703// distanceptsol = Distance(apoint,solution,
704// afirstvector,asecondvector,
705// adirection,parameter,sense,ok);
706 if (oncurve)
707 distanceptsol = Distance(apoint,solution,
708 tan2,tan1,
709 adirection,parameter,sense,ok);
710 else
711 distanceptsol = Distance(apoint,solution,
712 afirstvector,asecondvector,
713 adirection,parameter,sense,ok);
714// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
715 if (ok || !oncurve) {
716 thesense = sense;
717 distancemini = distanceptsol;
718 }
719 TheSol = new GccInt_BLine(l);
720 Handle(Geom2d_Curve) bisectorcurve;
721 bisectorcurve = new Geom2d_Line(TheSol->Line());
722 if (!thesense)
723 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
724 0.,- Precision::Infinite());
725 else
726 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
727 0., Precision::Infinite());
728 }
729 }
730 break;
731
732 default :
733 StdFail_NotDone::Raise();
734 break;
735 }
736}
737
738
739//===========================================================================
740// calcul de la bissectrice entre une courbe et un point issue d un point. +
741// +
742// afirstcurve : \ courbe et point entre lesquelles on veut calculer la +
743// asecondpoint : / bissectrice. +
744// apoint : point par lequel doit passer la bissectrice. +
745// afirstvector : \ vecteurs pour determiner le secteur dans lequel +
746// asecondvector : / la bissectrice doit se trouver. +
747// adirection : indique le cote de la bissectrice a conserver. +
748// tolerance : seuil a partir duquel les bisectrices sont degenerees+
749//===========================================================================
750
751void Bisector_BisecAna::Perform(const Handle(Geom2d_Curve)& afirstcurve ,
752 const Handle(Geom2d_Point)& asecondpoint ,
753 const gp_Pnt2d& apoint ,
754 const gp_Vec2d& afirstvector ,
755 const gp_Vec2d& asecondvector,
756 const Standard_Real adirection ,
757 const Standard_Real tolerance ,
758 const Standard_Boolean oncurve )
759{
760 Standard_Boolean ok;
761 Standard_Boolean thesense = Standard_False,sense,theSense;
762 Standard_Real distanceptsol,parameter,firstparameter =0.,secondparameter;
763 Handle(Geom2d_Curve) curve;
764 Handle(GccInt_Bisec) TheSol;
765
766 gp_Circ2d circle;
767 gp_Lin2d line;
768 gp_Pnt2d circlecenter;
769
770 Standard_Integer cas = 0;
771
772 Handle(Standard_Type) type = afirstcurve->DynamicType();
773
774 if (type == STANDARD_TYPE(Geom2d_TrimmedCurve)) {
775 curve = (*(Handle_Geom2d_TrimmedCurve*)&afirstcurve)->BasisCurve();
776 }
777 else {
778 curve = afirstcurve;
779 }
780
781 type = curve->DynamicType();
782#ifdef DEB
783 gp_Pnt2d Point(asecondpoint->Pnt2d());
784#else
785 asecondpoint->Pnt2d();
786#endif
787 if (type == STANDARD_TYPE(Geom2d_Circle)) {
788 cas = 1;
789 Handle(Geom2d_Circle) C1 = Handle(Geom2d_Circle)::DownCast(curve);
790 circle = C1->Circ2d();
791 }
792 else if (type == STANDARD_TYPE(Geom2d_Line)) {
793 cas = 2;
794 Handle(Geom2d_Line) L1 = Handle(Geom2d_Line)::DownCast(curve);
795 line = L1->Lin2d();
796 }
797 else {
798 cout << "Not yet implemented" << endl;
799 }
800
801 switch(cas) {
802
803//=============================================================================
804// Bissectrice point - cercle. +
805//=============================================================================
806 case 1 : {
807 GccAna_CircPnt2dBisec Bisector(circle,asecondpoint->Pnt2d());
808 Standard_Real distancemini = Precision::Infinite();
809 if (Bisector.IsDone()) {
810 Standard_Integer nbsolution = Bisector.NbSolutions();
811 for (Standard_Integer i = 1; i <= nbsolution; i++) {
812 Handle(GccInt_Bisec) solution = Bisector.ThisSolution(i);
813 Degenerate(solution,tolerance);
814 sense = Standard_False;
815 distanceptsol = Distance(apoint,solution,
816 afirstvector,asecondvector,
817 adirection,parameter,sense,ok);
818
819 if (distanceptsol <= distancemini) {
820 TheSol = solution;
821 firstparameter = parameter;
822 thesense = sense;
823 distancemini = distanceptsol;
824 }
825 }
826 if (!TheSol.IsNull()) {
827 GccInt_IType type = TheSol->ArcType();
828 Handle(Geom2d_Curve) bisectorcurve;
829 if (type == GccInt_Lin) {
830
831// ----------------------------------------------------------------------------
832// Si la bisectrice est une ligne
833// => le point est sur le cercle.
834// Si La portion de bisectrice qui nous interresse est du cote du centre.
835// => la bisectrice est limitee par le point et le centre du cercle.
836// Remarque : Dans ce dernier cas la bisectrice est en fait un ellipse de petit
837// axe nul.
838// ----------------------------------------------------------------------------
839
840 circlecenter = circle.Location();
841 line = TheSol->Line();
842 secondparameter = ElCLib::Parameter(line, circlecenter);
843 bisectorcurve = new Geom2d_Line(line);
844
845 if (!thesense) {
846 if (secondparameter > firstparameter) {
847 secondparameter = - Precision::Infinite();
848 }
849 else {
850 secondparameter = secondparameter - 1.E-8;
851 }
852 }
853 else {
854 if (secondparameter < firstparameter) {
855 secondparameter = Precision::Infinite();
856 }
857 else {
858 secondparameter = secondparameter + 1.E-8;
859 }
860 }
861
862 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
863 firstparameter,
864 secondparameter);
865
866 }
867 else if (type == GccInt_Cir) {
868 bisectorcurve = new Geom2d_Circle(TheSol->Circle());
869 if (!thesense)
870 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
871 firstparameter-2.0*PI,
872 firstparameter,
873 thesense);
874 else
875 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
876 firstparameter,
877 firstparameter+2.0*PI,
878 thesense);
879 }
880 else if (type == GccInt_Hpr) {
881 bisectorcurve=new Geom2d_Hyperbola(TheSol->Hyperbola());
882 if (!thesense)
883 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
884 firstparameter,
885 - Precision::Infinite());
886 else
887 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
888 firstparameter,
889 Precision::Infinite());
890 }
891 else if (type == GccInt_Ell) {
892 bisectorcurve = new Geom2d_Ellipse(TheSol->Ellipse());
893 if (!thesense)
894 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
895 firstparameter-2.0*PI,
896 firstparameter,
897 thesense);
898 else
899 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
900 firstparameter,
901 firstparameter+2.0*PI,
902 thesense);
903 }
904 }
905 }
906 }
907 break;
908
909//=============================================================================
910// Bissectrice point - droite. +
911//=============================================================================
912 case 2 : {
913 GccAna_LinPnt2dBisec Bisector(line,asecondpoint->Pnt2d());
914
915 theSense = Standard_True;
916#ifdef DEB
917 gp_Vec2d V(line.Direction());
918#else
919 line.Direction();
920#endif
921 Handle(GccInt_Bisec) solution = Bisector.ThisSolution();
922 Degenerate(solution,tolerance);
923 GccInt_IType type = solution->ArcType();
924 Handle(Geom2d_Curve) bisectorcurve;
925
926 if (type == GccInt_Lin) {
927 bisectorcurve = new Geom2d_Line(solution->Line());
928 }
929 else if (type == GccInt_Par) {
930 bisectorcurve = new Geom2d_Parabola(solution->Parabola());
931 }
932 sense = Standard_False;
933 distanceptsol = Distance(apoint,solution,
934 afirstvector,asecondvector,
935 adirection,parameter,sense,ok);
936
937 if (ok || !oncurve) {
938 firstparameter = parameter;
939 thesense = sense;
940 }
941
942 if (!thesense)
943 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
944 firstparameter,
945 - Precision::Infinite());
946 else
947 thebisector = new Geom2d_TrimmedCurve(bisectorcurve,
948 firstparameter,
949 Precision::Infinite());
950 }
951 break;
952
953 default:
954 {
955 cout << "Not yet implemented" << endl;
956 break;
957 }
958 }
959}
960
961
962//===========================================================================
963// calcul de la bissectrice entre une courbe et un point issue d un point. +
964// +
965// afirstpoint : \ courbes entre lesquelles on veut calculer la +
966// asecondcurve : / bissectrice. +
967// apoint : point par lequel doit passer la bissectrice. +
968// afirstvector : \ vecteurs pour determiner le secteur dans lequel +
969// asecondvector : / la bissectrice doit se trouver. +
970// adirection : indique le cote de la bissectrice a conserver. +
971// tolerance : seuil a partir duquel les bisectrices sont degenerees+
972//===========================================================================
973
974void Bisector_BisecAna::Perform(const Handle(Geom2d_Point)& afirstpoint ,
975 const Handle(Geom2d_Curve)& asecondcurve ,
976 const gp_Pnt2d& apoint ,
977 const gp_Vec2d& afirstvector ,
978 const gp_Vec2d& asecondvector,
979 const Standard_Real adirection ,
980// const Standard_Real tolerance ,
981 const Standard_Real ,
982 const Standard_Boolean oncurve )
983
984{
985 Standard_Real adirectionreverse = - adirection;
986 Perform(asecondcurve ,
987 afirstpoint ,
988 apoint ,
989 asecondvector ,
990 afirstvector ,
991 adirectionreverse ,
992// Modified by skv - Tue Feb 15 17:51:29 2005 Integration Begin
993 0.,
994// Modified by skv - Tue Feb 15 17:51:29 2005 Integration End
995 oncurve );
996}
997
998//===========================================================================
999// calcul de la bissectrice entre deux points issue d un point. +
1000// +
1001// afirstpoint : \ courbes entre lesquelles on veut calculer la +
1002// asecondpoint : / bissectrice. +
1003// apoint : point par lequel doit passer la bissectrice. +
1004// afirstvector : \ vecteurs pour determiner le secteur dans lequel +
1005// asecondvector : / la bissectrice doit se trouver. +
1006// adirection : indique le cote de la bissectrice a conserver. +
1007//===========================================================================
1008
1009void Bisector_BisecAna::Perform(const Handle(Geom2d_Point)& afirstpoint ,
1010 const Handle(Geom2d_Point)& asecondpoint ,
1011 const gp_Pnt2d& apoint ,
1012 const gp_Vec2d& afirstvector ,
1013 const gp_Vec2d& asecondvector,
1014 const Standard_Real adirection ,
1015// const Standard_Real tolerance ,
1016 const Standard_Real ,
1017 const Standard_Boolean oncurve )
1018{
1019 Standard_Boolean sense,ok;
1020 Standard_Real distanceptsol,parameter;
1021
1022 GccAna_Pnt2dBisec bisector(afirstpoint->Pnt2d(),asecondpoint->Pnt2d());
1023 gp_Lin2d line = bisector.ThisSolution();
1024 Handle(GccInt_Bisec) solution = new GccInt_BLine(line);
1025
1026 sense = Standard_False;
1027 distanceptsol = Distance(apoint,solution,
1028 afirstvector,asecondvector,
1029 adirection,parameter,sense,ok);
1030 if (ok || !oncurve) {
1031 Handle(Geom2d_Curve) bisectorcurve = new Geom2d_Line(line);
1032 if (!sense)
1033 thebisector=new Geom2d_TrimmedCurve(bisectorcurve,
1034 parameter,- Precision::Infinite());
1035 else
1036 thebisector =new Geom2d_TrimmedCurve(bisectorcurve,
1037 parameter,Precision::Infinite());
1038 }
1039}
1040
1041//=============================================================================
1042//function : IsExtendAtStart
1043//purpose :
1044//=============================================================================
1045Standard_Boolean Bisector_BisecAna::IsExtendAtStart() const
1046{
1047 return Standard_False;
1048}
1049
1050//=============================================================================
1051//function : IsExtendAtEnd
1052//purpose :
1053//=============================================================================
1054Standard_Boolean Bisector_BisecAna::IsExtendAtEnd() const
1055{
1056 return Standard_False;
1057}
1058
1059//=============================================================================
1060//function : SetTrim
1061//purpose : Restriction de la bissectrice par le domaine de la courbe Cu.
1062// Le domaine de la courbe est l ensemble des points plus pres de la
1063// courbe que de ses extremites.
1064// Pour le calcul le domaine est etendu. Extension de Epsilon1 du
1065// First et du Last parametre de la courbe.
1066//=============================================================================
1067//void Bisector_BisecAna::SetTrim(const Handle(Geom2d_Curve)& Cu)
1068void Bisector_BisecAna::SetTrim(const Handle(Geom2d_Curve)& )
1069{
1070/*
1071 Handle(Standard_Type) Type;
1072 Handle(Geom2d_Curve) TheCurve;
1073 Handle(Geom2d_Circle) CircleCu;
1074 Handle(Geom2d_Line) LineCu;
1075 Handle(Geom2d_Curve) FirstLimit;
1076 Handle(Geom2d_Curve) LastLimit;
1077
1078 gp_Lin2d gpLine;
1079 gp_Pnt2d P, PFirst, PLast, FirstPointBisector, Center;
1080 gp_Vec2d TanFirst, TanLast;
1081
1082 IntRes2d_Domain FirstDomain;
1083 IntRes2d_Domain LastDomain ;
1084
1085 Standard_Real UFirst, ULast, UB1, UB2;
1086 Standard_Real UBisInt1, UBisInt2, Utrim;
1087 Standard_Real Distance;
1088 Standard_Real Radius;
1089
1090 Standard_Real Epsilon1 = 1.E-6; // Epsilon sur le parametre de la courbe.
1091 Standard_Real Tolerance = 1.E-8; // Tolerance pour les intersections.
1092
1093 Type = Cu->DynamicType();
1094
1095 if (Type == STANDARD_TYPE(Geom2d_TrimmedCurve)) {
1096 TheCurve = Handle(Geom2d_TrimmedCurve)::DownCast(Cu)->BasisCurve();
1097 Type = TheCurve->DynamicType();
1098 }
1099 else {
1100 TheCurve = Cu;
1101 }
1102
1103 if (Type == STANDARD_TYPE(Geom2d_Circle)) {
1104 CircleCu = Handle(Geom2d_Circle)::DownCast(TheCurve);
1105 }
1106 else {
1107 LineCu = Handle(Geom2d_Line)::DownCast(TheCurve);
1108 }
1109
1110 // Recuperation de UFirst, ULast.
1111 // -------------------------------
1112 UFirst = Cu->FirstParameter();
1113 ULast = Cu->LastParameter();
1114
1115 // Creation des lignes Limites du domaine si elles existent.
1116 // et Determination de leur domaine d intersection.
1117 // ---------------------------------------------------------
1118 if (Type == STANDARD_TYPE(Geom2d_Circle)) {
1119 CircleCu->D1(UFirst,PFirst,TanFirst);
1120 CircleCu->D1(ULast ,PLast ,TanLast);
1121 Radius = CircleCu->Radius();
1122
1123 if (PFirst.Distance(PLast) > 2.*Epsilon1 && Radius > Epsilon1) {
1124 Center = CircleCu->Location();
1125 P = PFirst.Translated( - (Epsilon1/Radius)*TanFirst );
1126
1127 FirstLimit = new Geom2d_Line(P,
1128 gp_Dir2d(PFirst.X() - Center.X(),
1129 PFirst.Y() - Center.Y()));
1130 P = PLast .Translated( (Epsilon1/Radius)*TanLast );
1131
1132 LastLimit = new Geom2d_Line(P,
1133 gp_Dir2d(PLast.X() - Center.X(),
1134 PLast.Y() - Center.Y()));
1135
1136 Geom2dAdaptor_Curve AFirstLimit(FirstLimit);
1137 Geom2dAdaptor_Curve ALastLimit (LastLimit);
1138 Geom2dInt_GInter Intersect(AFirstLimit , FirstDomain,
1139 ALastLimit , LastDomain ,
1140 Tolerance , Tolerance );
1141
1142 if (Intersect.IsDone() && !Intersect.IsEmpty()) {
1143 if (Intersect.NbPoints() >= 1) {
1144 FirstDomain.SetValues(Intersect.Point(1).Value(),
1145 Intersect.Point(1).ParamOnFirst(),
1146 Tolerance,Standard_True);
1147 LastDomain. SetValues(Intersect.Point(1).Value(),
1148 Intersect.Point(1).ParamOnSecond(),
1149 Tolerance,Standard_True);
1150 }
1151 }
1152 }
1153 }
1154 else if (Type == STANDARD_TYPE(Geom2d_Line)) {
1155 gpLine = LineCu->Lin2d();
1156 if (UFirst > - Precision::Infinite()){
1157 P = LineCu->Value(UFirst - Epsilon1);
1158 FirstLimit = new Geom2d_Line(gpLine.Normal(P)) ;
1159 }
1160 if (ULast < Precision::Infinite()) {
1161 P = LineCu->Value(ULast + Epsilon1);
1162 LastLimit = new Geom2d_Line(gpLine.Normal(P));
1163 }
1164 }
1165 else {
1166 Standard_NotImplemented::Raise();
1167 }
1168
1169 // Determination domaine d intersection de la Bissectrice.
1170 // -------------------------------------------------------
1171 UB1 = thebisector->FirstParameter();
1172 UB2 = thebisector->LastParameter();
1173 if (UB2 > 10000.) {
1174 UB2 = 10000.;
1175 Handle(Geom2d_Curve) BasisCurve = thebisector->BasisCurve();
1176 Handle(Standard_Type) Type1 = BasisCurve->DynamicType();
1177 gp_Parab2d gpParabola;
1178 gp_Hypr2d gpHyperbola;
1179 Standard_Real Focus;
1180 Standard_Real Limit = 50000.;
1181 if (Type1 == STANDARD_TYPE(Geom2d_Parabola)) {
1182 gpParabola = Handle(Geom2d_Parabola)::DownCast(BasisCurve)->Parab2d();
1183 Focus = gpParabola.Focal();
1184 Standard_Real Val1 = Sqrt(Limit*Focus);
1185 Standard_Real Val2 = Sqrt(Limit*Limit);
1186 UB2 = (Val1 <= Val2 ? Val1:Val2);
1187 }
1188 else if (Type1 == STANDARD_TYPE(Geom2d_Hyperbola)) {
1189 gpHyperbola = Handle(Geom2d_Hyperbola)::DownCast(BasisCurve)->Hypr2d();
1190 Standard_Real Majr = gpHyperbola.MajorRadius();
1191 Standard_Real Minr = gpHyperbola.MinorRadius();
1192 Standard_Real Valu1 = Limit/Majr;
1193 Standard_Real Valu2 = Limit/Minr;
1194 Standard_Real Val1 = Log(Valu1+Sqrt(Valu1*Valu1-1));
1195 Standard_Real Val2 = Log(Valu2+Sqrt(Valu2*Valu2+1));
1196 UB2 = (Val1 <= Val2 ? Val1:Val2);
1197 }
1198 }
1199
1200 IntRes2d_Domain DomainBisector(thebisector->Value(UB1), UB1, Tolerance,
1201 thebisector->Value(UB2), UB2, Tolerance);
1202
1203 if (thebisector->BasisCurve()->IsPeriodic()) {
1204 DomainBisector.SetEquivalentParameters(0.0,2.*PI);
1205 }
1206 FirstPointBisector = thebisector->Value(UB1);
1207
1208
1209 // Intersection Bisectrice avec FirstLimit => UBisInt1.
1210 // ----------------------------------------------------
1211 UBisInt1 = Precision::Infinite();
1212 if (!FirstLimit.IsNull()) {
1213 Geom2dAdaptor_Curve AdapBis (thebisector);
1214 Geom2dAdaptor_Curve AFirstLimit(FirstLimit);
1215 Geom2dInt_GInter Intersect(AFirstLimit , FirstDomain,
1216 AdapBis , DomainBisector,
1217 Tolerance , Tolerance );
1218
1219 if (Intersect.IsDone() && !Intersect.IsEmpty()) {
1220 for (Standard_Integer i=1; i<=Intersect.NbPoints(); i++) {
1221 Distance = FirstPointBisector.Distance(Intersect.Point(i).Value());
1222 if (Distance > 2.*Tolerance) {
1223 UBisInt1 = Intersect.Point(i).ParamOnSecond();
1224 break;
1225 }
1226 }
1227 }
1228 }
1229 // Intersection Bisectrice avec LastLimit => UBisInt2.
1230 // ---------------------------------------------------
1231 UBisInt2 = Precision::Infinite();
1232 if (!LastLimit.IsNull()) {
1233 Geom2dAdaptor_Curve AdapBis (thebisector);
1234 Geom2dAdaptor_Curve ALastLimit (LastLimit);
1235 Geom2dInt_GInter Intersect(ALastLimit , LastDomain ,
1236 AdapBis , DomainBisector,
1237 Tolerance , Tolerance );
1238
1239 if (Intersect.IsDone() && !Intersect.IsEmpty()) {
1240 for (Standard_Integer i=1; i<=Intersect.NbPoints(); i++) {
1241 Distance = FirstPointBisector.Distance(Intersect.Point(i).Value());
1242 if (Distance > 2.*Tolerance) {
1243 UBisInt2 = Intersect.Point(i).ParamOnSecond();
1244 break;
1245 }
1246 }
1247 }
1248 }
1249 // Restriction de la Bissectrice par le point d intersection de plus petit
1250 // parametre.
1251 //------------------------------------------------------------------------
1252 Utrim = (UBisInt1 < UBisInt2) ? UBisInt1 : UBisInt2;
1253
1254 if (Utrim < UB2 && Utrim > UB1) thebisector->SetTrim(UB1,Utrim);
1255*/
1256}
1257
1258void Bisector_BisecAna::SetTrim(const Standard_Real uf, const Standard_Real ul)
1259{
1260 thebisector->SetTrim(uf, ul);
1261}
1262//=============================================================================
1263//function : Reverse
1264//purpose :
1265//=============================================================================
1266void Bisector_BisecAna::Reverse()
1267{
1268 thebisector->Reverse();
1269}
1270
1271//=============================================================================
1272//function : ReversedParameter
1273//purpose :
1274//=============================================================================
1275Standard_Real Bisector_BisecAna::ReversedParameter(const Standard_Real U) const
1276{
1277 return thebisector->ReversedParameter(U);
1278}
1279
1280//=============================================================================
1281//function : IsCN
1282//purpose :
1283//=============================================================================
1284Standard_Boolean Bisector_BisecAna::IsCN(const Standard_Integer N) const
1285{
1286 return thebisector->IsCN(N);
1287}
1288
1289//=============================================================================
1290//function : Copy
1291//purpose :
1292//=============================================================================
1293Handle(Geom2d_Geometry) Bisector_BisecAna::Copy() const
1294{
1295 Handle(Bisector_BisecAna) C = new Bisector_BisecAna();
1296 C->Init (Handle(Geom2d_TrimmedCurve)::DownCast(thebisector->Copy()));
1297 return C;
1298}
1299
1300//=============================================================================
1301//function : Transform
1302//purpose :
1303//=============================================================================
1304void Bisector_BisecAna::Transform(const gp_Trsf2d& T)
1305{
1306 thebisector->Transform(T);
1307}
1308
1309//=============================================================================
1310//function : FirstParameter
1311//purpose :
1312//=============================================================================
1313Standard_Real Bisector_BisecAna::FirstParameter() const
1314{
1315// modified by NIZHNY-EAP Thu Feb 3 17:23:42 2000 ___BEGIN___
1316// return thebisector->BasisCurve()->FirstParameter();
1317 return thebisector->FirstParameter();
1318// modified by NIZHNY-EAP Thu Feb 3 17:23:48 2000 ___END___
1319}
1320
1321//=============================================================================
1322//function : LastParameter
1323//purpose :
1324//=============================================================================
1325Standard_Real Bisector_BisecAna::LastParameter() const
1326{
1327 return thebisector->LastParameter();
1328}
1329
1330//=============================================================================
1331//function : IsClosed
1332//purpose :
1333//=============================================================================
1334Standard_Boolean Bisector_BisecAna::IsClosed() const
1335{
1336 return thebisector->BasisCurve()->IsClosed();
1337}
1338
1339//=============================================================================
1340//function : IsPeriodic
1341//purpose :
1342//=============================================================================
1343Standard_Boolean Bisector_BisecAna::IsPeriodic() const
1344{
1345 return thebisector->BasisCurve()->IsPeriodic();
1346}
1347
1348//=============================================================================
1349//function : Continuity
1350//purpose :
1351//=============================================================================
1352GeomAbs_Shape Bisector_BisecAna::Continuity() const
1353{
1354 return thebisector->Continuity();
1355}
1356
1357//=============================================================================
1358//function : D0
1359//purpose :
1360//=============================================================================
1361void Bisector_BisecAna::D0(const Standard_Real U, gp_Pnt2d& P) const
1362{
1363 thebisector->BasisCurve()->D0(U,P);
1364}
1365
1366//=============================================================================
1367//function : D1
1368//purpose :
1369//=============================================================================
1370void Bisector_BisecAna::D1(const Standard_Real U, gp_Pnt2d& P, gp_Vec2d& V1) const
1371{
1372 thebisector->BasisCurve()->D1(U,P,V1);
1373}
1374//=============================================================================
1375//function : D2
1376//purpose :
1377//=============================================================================
1378void Bisector_BisecAna::D2(const Standard_Real U,
1379 gp_Pnt2d& P,
1380 gp_Vec2d& V1,
1381 gp_Vec2d& V2) const
1382{
1383 thebisector->BasisCurve()->D2(U,P,V1,V2);
1384}
1385//=============================================================================
1386//function : D3
1387//purpose :
1388//=============================================================================
1389void Bisector_BisecAna::D3(const Standard_Real U,
1390 gp_Pnt2d& P,
1391 gp_Vec2d& V1,
1392 gp_Vec2d& V2,
1393 gp_Vec2d& V3) const
1394{
1395 thebisector->BasisCurve()->D3(U,P,V1,V2,V3);
1396}
1397//=============================================================================
1398//function : DN
1399//purpose :
1400//=============================================================================
1401gp_Vec2d Bisector_BisecAna::DN(const Standard_Real U, const Standard_Integer N) const
1402{
1403 return thebisector->BasisCurve()->DN (U, N);
1404}
1405
1406//=============================================================================
1407//function : Geom2dCurve
1408//purpose :
1409//=============================================================================
1410Handle(Geom2d_Curve) Bisector_BisecAna::Geom2dCurve() const
1411{
1412 return thebisector->BasisCurve();
1413}
1414
1415//==========================================================================
1416//function : ParameterOfStartPoint
1417//purpose :
1418//==========================================================================
1419Standard_Real Bisector_BisecAna::ParameterOfStartPoint() const
1420{
1421 return thebisector->FirstParameter();
1422}
1423
1424//==========================================================================
1425//function : ParameterOfEndPoint
1426//purpose :
1427//==========================================================================
1428Standard_Real Bisector_BisecAna::ParameterOfEndPoint() const
1429{
1430 return thebisector->LastParameter();
1431}
1432
1433//==========================================================================
1434//function : Parameter
1435//purpose :
1436//==========================================================================
1437Standard_Real Bisector_BisecAna::Parameter(const gp_Pnt2d& P) const
1438{
1439 gp_Hypr2d gphyperbola;
1440 gp_Parab2d gpparabola ;
1441 gp_Elips2d gpellipse ;
1442 gp_Circ2d gpcircle ;
1443 gp_Lin2d gpline ;
1444
1445 Handle(Geom2d_Curve) BasisCurve = thebisector->BasisCurve();
1446 Handle(Standard_Type) Type = BasisCurve ->DynamicType();
1447
1448 if (Type == STANDARD_TYPE(Geom2d_Line)) {
1449 gpline = Handle(Geom2d_Line)::DownCast(BasisCurve)->Lin2d();
1450 return ElCLib::Parameter(gpline,P);
1451 }
1452 else if (Type == STANDARD_TYPE(Geom2d_Circle)) {
1453 gpcircle = Handle(Geom2d_Circle)::DownCast(BasisCurve)->Circ2d();
1454 return ElCLib::Parameter(gpcircle,P);
1455 }
1456 else if (Type == STANDARD_TYPE(Geom2d_Hyperbola)) {
1457 gphyperbola = Handle(Geom2d_Hyperbola)::DownCast(BasisCurve)->Hypr2d();
1458 return ElCLib::Parameter(gphyperbola,P);
1459 }
1460 else if (Type == STANDARD_TYPE(Geom2d_Parabola)) {
1461 gpparabola = Handle(Geom2d_Parabola)::DownCast(BasisCurve)->Parab2d();
1462 return ElCLib::Parameter(gpparabola,P);
1463 }
1464 else if (Type == STANDARD_TYPE(Geom2d_Ellipse)) {
1465 gpellipse = Handle(Geom2d_Ellipse)::DownCast(BasisCurve)->Elips2d();
1466 return ElCLib::Parameter(gpellipse,P);
1467 }
1468 return 0.;
1469}
1470
1471//=============================================================================
1472//function : NbIntervals
1473//purpose :
1474//=============================================================================
1475Standard_Integer Bisector_BisecAna::NbIntervals() const
1476{
1477 return 1;
1478}
1479
1480//=============================================================================
1481//function : IntervalFirst
1482//purpose :
1483//=============================================================================
1484Standard_Real Bisector_BisecAna::IntervalFirst(const Standard_Integer I) const
1485{
1486 if (I != 1) Standard_OutOfRange::Raise();
1487 return FirstParameter();
1488}
1489
1490//=============================================================================
1491//function : IntervalLast
1492//purpose :
1493//=============================================================================
1494Standard_Real Bisector_BisecAna::IntervalLast(const Standard_Integer I) const
1495{
1496 if (I != 1) Standard_OutOfRange::Raise();
1497 return LastParameter();
1498}
1499
1500//=============================================================================
1501//function :
1502//=============================================================================
1503void Bisector_BisecAna::Init(const Handle(Geom2d_TrimmedCurve)& Bis)
1504{
1505 thebisector = Bis;
1506}
1507
1508//=============================================================================
1509//function : Degenerate
1510//purpose : Remplace la bisectrice par une droite,
1511// si la bisectrice est une ellipse, une parabole ou une ellipse
1512// degenere.
1513//=============================================================================
1514Standard_Boolean Degenerate(Handle(GccInt_Bisec)& aBisector,
1515 const Standard_Real Tolerance)
1516{
1517 Standard_Boolean Degeneree = Standard_False;
1518
1519 gp_Hypr2d gphyperbola;
1520 gp_Parab2d gpparabola ;
1521 gp_Elips2d gpellipse ;
1522 //gp_Circ2d gpcircle ;
1523
1524 Handle(GccInt_Bisec) NewBisector;
1525
1526 GccInt_IType type = aBisector->ArcType();
1527
1528 if (type == GccInt_Hpr) {
1529 gphyperbola = aBisector->Hyperbola();
1530
1531 // Si l Hyperbole est degeneree, elle est remplacee par la droite
1532 // de direction l axe de symetrie.
1533
1534 if (gphyperbola.MajorRadius() < Tolerance) {
1535 gp_Lin2d gpline(gphyperbola.YAxis());
1536 NewBisector = new GccInt_BLine(gpline);
1537 aBisector = NewBisector;
1538 Degeneree = Standard_True;
1539 }
1540 if (gphyperbola.MinorRadius() < Tolerance) {
1541 gp_Lin2d gpline(gphyperbola.XAxis());
1542 NewBisector = new GccInt_BLine(gpline);
1543 aBisector = NewBisector;
1544 Degeneree = Standard_True;
1545 }
1546 }
1547 else if (type == GccInt_Par) {
1548 gpparabola = aBisector->Parabola();
1549
1550 // Si la parabole est degeneree, elle est remplacee par la droite
1551 // issue du Sommet et de direction l axe de symetrie.
1552
1553 if (gpparabola.Focal() < Tolerance) {
1554 gp_Lin2d gpline(gpparabola.MirrorAxis());
1555 NewBisector = new GccInt_BLine(gpline);
1556 aBisector = NewBisector;
1557 Degeneree = Standard_True;
1558 }
1559 }
1560 else if (type == GccInt_Ell) {
1561 gpellipse = aBisector->Ellipse();
1562
1563 // Si l ellipse est degeneree, elle est remplacee par la droite
1564 // definie par le grand axe.
1565
1566 if (gpellipse.MinorRadius() < Tolerance) {
1567 gp_Lin2d gpline(gpellipse.XAxis());
1568 NewBisector = new GccInt_BLine(gpline);
1569 aBisector = NewBisector;
1570 Degeneree = Standard_True;
1571 }
1572 }
1573 return Degeneree;
1574}
1575
1576static void Indent (const Standard_Integer Offset) {
1577 if (Offset > 0) {
1578 for (Standard_Integer i = 0; i < Offset; i++) { cout << " "; }
1579 }
1580}
1581
1582//=============================================================================
1583//function : Dump
1584// purpose :
1585//=============================================================================
1586//void Bisector_BisecAna::Dump(const Standard_Integer Deep,
1587void Bisector_BisecAna::Dump(const Standard_Integer ,
1588 const Standard_Integer Offset) const
1589{
1590 Indent (Offset);
1591 cout<<"Bisector_BisecAna"<<endl;
1592 Indent (Offset);
1593// thebisector->Dump();
1594}