0023603: Boolean operation between two edges fails
[occt.git] / src / IntTools / IntTools_EdgeEdge_1.cxx
CommitLineData
e145f8c1 1// Created on: 2012-11-29
2// Created by: Peter KURNEV
3// Copyright (c) 2012 OPEN CASCADE SAS
4//
5// The content of this file is subject to the Open CASCADE Technology Public
6// License Version 6.5 (the "License"). You may not use the content of this file
7// except in compliance with the License. Please obtain a copy of the License
8// at http://www.opencascade.org and read it completely before using this file.
9//
10// The Initial Developer of the Original Code is Open CASCADE S.A.S., having its
11// main offices at: 1, place des Freres Montgolfier, 78280 Guyancourt, France.
12//
13// The Original Code and all software distributed under the License is
14// distributed on an "AS IS" basis, without warranty of any kind, and the
15// Initial Developer hereby disclaims all such warranties, including without
16// limitation, any warranties of merchantability, fitness for a particular
17// purpose or non-infringement. Please see the License for the specific terms
18// and conditions governing the rights and limitations under the License.
19
20
21#include <IntTools_EdgeEdge.ixx>
22
23#include <gp_Elips.hxx>
24#include <gp_Ax1.hxx>
25#include <gp_Dir.hxx>
26#include <gp_XYZ.hxx>
27#include <gp_Ax2.hxx>
28#include <gp_Pnt.hxx>
29//
30#include <Geom_Curve.hxx>
31#include <Geom_Line.hxx>
32#include <Geom_Circle.hxx>
33#include <Geom_Ellipse.hxx>
34#include <Geom_Parabola.hxx>
35#include <Geom_Hyperbola.hxx>
36#include <Geom_BezierCurve.hxx>
37#include <Geom_BSplineCurve.hxx>
38#include <Geom_TrimmedCurve.hxx>
39#include <Geom_OffsetCurve.hxx>
40//
41#include <BRep_Tool.hxx>
42#include <BRepAdaptor_Curve.hxx>
43
44//=======================================================================
45//class : IntTools_ComparatorCurve
46//purpose :
47//=======================================================================
48class IntTools_ComparatorCurve {
49 public:
50 IntTools_ComparatorCurve() {
51 myT11=0.;
52 myT12=0.;
53 myT21=0.;
54 myT22=0.;
55 myIsSame=Standard_False;
56 };
57 //
58 virtual ~IntTools_ComparatorCurve(){
59 };
60 //
61 void SetCurve1(const BRepAdaptor_Curve& aBC3D) {
62 myBC1=aBC3D;
63 };
64 //
65 const BRepAdaptor_Curve& Curve1()const {
66 return myBC1;
67 };
68 //
69 void SetRange1(const Standard_Real aT1,
70 const Standard_Real aT2) {
71 myT11=aT1;
72 myT12=aT2;
73 };
74 //
75 void Range1(Standard_Real& aT1, Standard_Real& aT2)const {
76 aT1=myT11;
77 aT2=myT12;
78 };
79 //
80 void SetCurve2(const BRepAdaptor_Curve& aBC3D){
81 myBC2=aBC3D;
82 };
83 //
84 const BRepAdaptor_Curve& Curve2()const{
85 return myBC2;
86 };
87 //
88 void SetRange2(const Standard_Real aT1,
89 const Standard_Real aT2){
90 myT21=aT1;
91 myT22=aT2;
92 };
93 //
94 void Range2(Standard_Real& aT1,
95 Standard_Real& aT2)const {
96 aT1=myT21;
97 aT2=myT22;
98 };
99 //
100 Standard_Boolean IsSame()const {
101 return myIsSame;
102 };
103 //
104 void Perform();
105 //
106 //--------------------------------------
107 protected:
108 //
109 void IsSameElipse();
110 //
111 void IsSameBSplineCurve();
112 //
113 static
114 Standard_Boolean
115 IsSameReal(const Standard_Real aR1,
116 const Standard_Real aR2);
117 //
118 static
119 Standard_Boolean
120 IsSameAx2(const gp_Ax2& aAx21,
121 const gp_Ax2& aAx22);
122 //
123 static
124 Standard_Boolean
125 IsSameAx1(const gp_Ax1& aAx1,
126 const gp_Ax1& aAx2);
127 //
128 static
129 Standard_Boolean
130 IsSamePnt(const gp_Pnt& aP1,
131 const gp_Pnt& aP2);
132 static
133 Standard_Boolean
134 IsSameDir(const gp_Dir& aDir1,
135 const gp_Dir& aDir2);
136 //
137 static
138 Standard_Boolean
139 IsSameXYZ(const gp_XYZ& aXYZ1,
140 const gp_XYZ& aXYZ2);
141 //
142 static
143 void GetCurveBase(const Handle(Geom_Curve)& aC3D,
144 GeomAbs_CurveType& aTypeBase,
145 Handle(Geom_Curve)& aCurveBase);
146 //
147 static
148 Standard_Boolean
149 IsTypeBase(const Handle(Geom_Curve)& aC,
150 GeomAbs_CurveType& aTypeB);
151 //
152 protected:
153 BRepAdaptor_Curve myBC1;
154 Standard_Real myT11;
155 Standard_Real myT12;
156 //
157 BRepAdaptor_Curve myBC2;
158 Standard_Real myT21;
159 Standard_Real myT22;
160 //
161 Standard_Boolean myIsSame;
162};
163//=======================================================================
164//function : Perform
165//purpose :
166//=======================================================================
167void IntTools_ComparatorCurve::Perform()
168{
169 GeomAbs_CurveType aCurveType1, aCurveType2;
170 //
171 myIsSame=Standard_False;
172 //
173 aCurveType1=myBC1.GetType();
174 aCurveType2=myBC2.GetType();
175 //
176 myIsSame=(aCurveType1==aCurveType2);
177 if (!myIsSame) {
178 return;
179 }
180 //
181 myIsSame=IsSameReal(myT11, myT21);
182 if (!myIsSame) {
183 return;
184 }
185 //
186 myIsSame=IsSameReal(myT12, myT22);
187 if (!myIsSame) {
188 return;
189 }
190 //
191 if (aCurveType1==GeomAbs_Ellipse) {
192 IsSameElipse();
193 return;
194 }
195 else if (aCurveType1==GeomAbs_BSplineCurve) {
196 IsSameBSplineCurve();
197 return ;
198 }
199 else {
200 myIsSame=Standard_False;
201 return;
202 }
203}
204//=======================================================================
205//function : IsSameBSplineCurve
206//purpose :
207//=======================================================================
208void IntTools_ComparatorCurve::IsSameBSplineCurve()
209{
210 Standard_Boolean bIsRational, bIsPreiodic;
211 Standard_Integer iNbPoles, iNbKnots, iDegree;
212 //
213 bIsRational=myBC1.IsRational();
214 myIsSame=(bIsRational==myBC2.IsRational());
215 if (!myIsSame) {
216 return;
217 }
218 //
219 iNbPoles=myBC1.NbPoles();
220 myIsSame=(iNbPoles==myBC2.NbPoles());
221 if (!myIsSame) {
222 return;
223 }
224 //
225 iNbKnots=myBC1.NbKnots();
226 myIsSame=(iNbKnots==myBC2.NbKnots());
227 if (!myIsSame) {
228 return;
229 }
230 //
231 iDegree=myBC1.Degree();
232 myIsSame=(iDegree==myBC2.Degree());
233 if (!myIsSame) {
234 return;
235 }
236 //
237 bIsPreiodic=myBC1.IsPeriodic();
238 myIsSame=(bIsPreiodic==myBC2.IsPeriodic());
239 if (!myIsSame) {
240 return;
241 }
242
243 //-------------------------------------------
244 Standard_Integer i, j, aM[2];
245 Standard_Real aT1, aT2, aX0[4], aX1[4];
246 GeomAbs_CurveType aTypeBase;
247 gp_Pnt aP;
248 Handle(Geom_Curve) aC;
249 Handle(Geom_BSplineCurve) aBSp[2];
250 TopoDS_Edge aE1, aE2;
251 //
252 aE1=myBC1.Edge();
253 aE2=myBC2.Edge();
254 //
255 aC=BRep_Tool::Curve (aE1, aT1, aT2);
256 GetCurveBase(aC, aTypeBase, aBSp[0]);
257 //
258 aC=BRep_Tool::Curve (aE2, aT1, aT2);
259 GetCurveBase(aC, aTypeBase, aBSp[1]);
260 //
261 // Poles / Weights
262 for(i=1; i<=iNbPoles; ++i) {
263 aP=aBSp[0]->Pole(i);
264 aP.Coord(aX0[0], aX0[1], aX0[2]);
265 aX0[3]=aBSp[0]->Weight(i);
266 //
267 aP=aBSp[1]->Pole(i);
268 aP.Coord(aX1[0], aX1[1], aX1[2]);
269 aX1[3]=aBSp[1]->Weight(i);
270 //
271 for (j=0; j<4; ++j) {
272 myIsSame=IsSameReal(aX0[j], aX1[j]);
273 if(!myIsSame) {
274 return;
275 }
276 }
277 }//for(i=1; i<iNbPoles; ++i) {
278 //
279 // Knots / Multiplicities
280 for(i=1; i<=iNbKnots; ++i) {
281 aX0[0]=aBSp[0]->Knot(i);
282 aX0[1]=aBSp[1]->Knot(i);
283 myIsSame=IsSameReal(aX0[0], aX0[1]);
284 if(!myIsSame) {
285 return;
286 }
287 //
288 aM[0]=aBSp[0]->Multiplicity(i);
289 aM[1]=aBSp[1]->Multiplicity(i);
290 myIsSame=(aM[0]==aM[1]);
291 if(!myIsSame) {
292 return;
293 }
294 }
295}
296//=======================================================================
297//function : GetCurveBase
298//purpose :
299//=======================================================================
300void IntTools_ComparatorCurve::GetCurveBase(const Handle(Geom_Curve)& aC3D,
301 GeomAbs_CurveType& aTypeBase,
302 Handle(Geom_Curve)& aCurveBase)
303{
304 Standard_Boolean bIsTypeBase;
305 Standard_Integer iTrimmed, iOffset;
306 Standard_Real aOffsetBase;
307 GeomAbs_CurveType aTypeB;
308 Handle(Geom_Curve) aC3DB;
309 Handle(Geom_TrimmedCurve) aCT3D;
310 Handle(Geom_OffsetCurve) aCF3D;
311 //
312 aTypeBase=GeomAbs_OtherCurve;
313 aOffsetBase=0.;
314 //
315 aC3DB=aC3D;
316 bIsTypeBase=IsTypeBase(aC3DB, aTypeB);
317 if (bIsTypeBase) {
318 aTypeBase=aTypeB;
319 aCurveBase=aC3D;
320 return;
321 }
322 //
323 while(1) {
324 iTrimmed=0;
325 iOffset=0;
326 aCT3D=Handle(Geom_TrimmedCurve)::DownCast(aC3DB);
327 if (!aCT3D.IsNull()) {
328 aC3DB=aCT3D->BasisCurve();
329 ++iTrimmed;
330 }
331 //
332 aCF3D=Handle(Geom_OffsetCurve)::DownCast(aC3DB);
333 if (!aCF3D.IsNull()) {
334 Standard_Real aOffset;
335 //
336 aOffset=aCF3D->Offset();
337 aOffsetBase=aOffsetBase+aOffset;
338 //
339 aC3DB=aCF3D->BasisCurve();
340 ++iOffset;
341 }
342 //
343 if (!(iTrimmed || iOffset)) {
344 break;
345 }
346 //
347 bIsTypeBase=IsTypeBase(aC3DB, aTypeB);
348 if (bIsTypeBase) {
349 aTypeBase=aTypeB;
350 aCurveBase=aC3DB;
351 return;
352 }
353 }
354}
355//=======================================================================
356//function : IsTypeBase
357//purpose :
358//=======================================================================
359Standard_Boolean
360 IntTools_ComparatorCurve::IsTypeBase(const Handle(Geom_Curve)& aC,
361 GeomAbs_CurveType& aTypeB)
362{
363 Standard_Boolean bRet;
364 Handle(Standard_Type) aType;
365 //
366 bRet=Standard_True;
367 //
368 aType=aC->DynamicType();
369 if (aType==STANDARD_TYPE(Geom_Line)) {
370 aTypeB=GeomAbs_Line;
371 }
372 else if (aType==STANDARD_TYPE(Geom_Circle)) {
373 aTypeB=GeomAbs_Circle;
374 }
375 else if (aType==STANDARD_TYPE(Geom_Ellipse)) {
376 aTypeB=GeomAbs_Ellipse;
377 }
378 else if (aType==STANDARD_TYPE(Geom_Parabola)) {
379 aTypeB=GeomAbs_Parabola;
380 }
381 else if (aType==STANDARD_TYPE(Geom_Hyperbola)) {
382 aTypeB=GeomAbs_Hyperbola;
383 }
384 else if (aType==STANDARD_TYPE(Geom_BezierCurve)) {
385 aTypeB=GeomAbs_BezierCurve;
386 }
387 else if (aType==STANDARD_TYPE(Geom_BSplineCurve)) {
388 aTypeB=GeomAbs_BSplineCurve;
389 }
390 else {
391 aTypeB=GeomAbs_OtherCurve;
392 bRet=!bRet;
393 }
394 return bRet;
395}
396//=======================================================================
397//function : IsSameElipse
398//purpose :
399//=======================================================================
400void IntTools_ComparatorCurve::IsSameElipse()
401{
402 Standard_Real aR1, aR2;
403 gp_Elips aElips1, aElips2;
404 //
405 myIsSame=Standard_False;
406 //
407 aElips1=myBC1.Ellipse();
408 aElips2=myBC2.Ellipse();
409 //
410 aR1=aElips1.MajorRadius();
411 aR2=aElips2.MajorRadius();
412 myIsSame=IsSameReal(aR1, aR2);
413 if (!myIsSame) {
414 return;
415 }
416 //
417 aR1=aElips1.MinorRadius();
418 aR2=aElips2.MinorRadius();
419 myIsSame=IsSameReal(aR1, aR2);
420 if (!myIsSame) {
421 return;
422 }
423 //
424 const gp_Ax2& aAx21=aElips1.Position();
425 const gp_Ax2& aAx22=aElips2.Position();
426 myIsSame=IsSameAx2(aAx21, aAx22);
427}
428//=======================================================================
429//function : IsSameAx2
430//purpose :
431//=======================================================================
432Standard_Boolean
433 IntTools_ComparatorCurve::IsSameAx2(const gp_Ax2& aAx21,
434 const gp_Ax2& aAx22)
435{
436 Standard_Boolean bRet;
437 //
438 const gp_Ax1& aAx1=aAx21.Axis();
439 const gp_Ax1& aAx2=aAx22.Axis();
440 //
441 bRet=IsSameAx1(aAx1, aAx2);
442 if (!bRet) {
443 return bRet;
444 }
445 //
446 const gp_Dir& aDirX1=aAx21.XDirection();
447 const gp_Dir& aDirX2=aAx22.XDirection();
448 //
449 bRet=IsSameDir(aDirX1, aDirX2);
450 if (!bRet) {
451 return bRet;
452 }
453 //
454 //
455 const gp_Dir& aDirY1=aAx21.YDirection();
456 const gp_Dir& aDirY2=aAx22.YDirection();
457 //
458 bRet=IsSameDir(aDirY1, aDirY2);
459 //
460 return bRet;
461}
462//=======================================================================
463//function : IsSamePnt
464//purpose :
465//=======================================================================
466Standard_Boolean
467 IntTools_ComparatorCurve::IsSamePnt(const gp_Pnt& aP1,
468 const gp_Pnt& aP2)
469{
470 const gp_XYZ& aXYZ1=aP1.XYZ();
471 const gp_XYZ& aXYZ2=aP2.XYZ();
472 return IsSameXYZ(aXYZ1, aXYZ2);
473}
474//=======================================================================
475//function : IsSameAx1
476//purpose :
477//=======================================================================
478Standard_Boolean
479 IntTools_ComparatorCurve::IsSameAx1(const gp_Ax1& aAx1,
480 const gp_Ax1& aAx2)
481{
482 Standard_Boolean bRet;
483 //
484 const gp_Pnt& aP1=aAx1.Location();
485 const gp_Pnt& aP2=aAx2.Location();
486 //
487 bRet=IsSamePnt(aP1, aP2);
488 if (!bRet) {
489 return bRet;
490 }
491 //
492 const gp_Dir& aDir1=aAx1.Direction();
493 const gp_Dir& aDir2=aAx2.Direction();
494 //
495 bRet=IsSameDir(aDir1, aDir2);
496 return bRet;
497}
498//=======================================================================
499//function : IsSameDir
500//purpose :
501//=======================================================================
502Standard_Boolean
503 IntTools_ComparatorCurve::IsSameDir(const gp_Dir& aDir1,
504 const gp_Dir& aDir2)
505{
506 const gp_XYZ& aXYZ1=aDir1.XYZ();
507 const gp_XYZ& aXYZ2=aDir2.XYZ();
508 return IsSameXYZ(aXYZ1, aXYZ2);
509}
510//=======================================================================
511//function : IsSameXYZ
512//purpose :
513//=======================================================================
514Standard_Boolean
515 IntTools_ComparatorCurve::IsSameXYZ(const gp_XYZ& aXYZ1,
516 const gp_XYZ& aXYZ2)
517{
518 Standard_Boolean bRet;
519 Standard_Integer i;
520 Standard_Real aX1[3], aX2[3];
521
522 aXYZ1.Coord(aX1[0], aX1[1], aX1[2]);
523 aXYZ2.Coord(aX2[0], aX2[1], aX2[2]);
524 //
525 for (i=0; i<3; ++i) {
526 bRet=IsSameReal(aX1[i], aX2[i]);
527 if(!bRet) {
528 break;
529 }
530 }
531 return bRet;
532}
533//=======================================================================
534//function : IsSameReal
535//purpose :
536//=======================================================================
537Standard_Boolean
538 IntTools_ComparatorCurve::IsSameReal(const Standard_Real aR1,
539 const Standard_Real aR2)
540{
541 Standard_Boolean bRet;
542 Standard_Real aEpsilon;
543 //
544 aEpsilon=Epsilon(aR1);
545 bRet=(fabs(aR1-aR2)<aEpsilon);
546 return bRet;
547}
548//=======================================================================
549//function : IsSameCurves
550//purpose :
551//=======================================================================
552Standard_Boolean IntTools_EdgeEdge::IsSameCurves()
553{
554 Standard_Boolean bRet;
555 IntTools_ComparatorCurve aICC;
556 //
557 aICC.SetCurve1(myCFrom);
558 aICC.SetRange1(myTminFrom, myTmaxFrom);
559 //
560 aICC.SetCurve2(myCTo);
561 aICC.SetRange2(myTminTo, myTmaxTo);
562 //
563 aICC.Perform();
564 bRet=aICC.IsSame();
565 //
566 return bRet;
567}