0024750: Replace instantiations of TCollection generic classes by NCollection templat...
[occt.git] / src / Bnd / Bnd_Box.cxx
CommitLineData
b311480e 1// Created on: 1991-03-08
2// Created by: Christophe MARION
3// Copyright (c) 1991-1999 Matra Datavision
973c2be1 4// Copyright (c) 1999-2014 OPEN CASCADE SAS
aa396061 5//
973c2be1 6// This file is part of Open CASCADE Technology software library.
b311480e 7//
d5f74e42 8// This library is free software; you can redistribute it and/or modify it under
9// the terms of the GNU Lesser General Public License version 2.1 as published
973c2be1 10// by the Free Software Foundation, with special exception defined in the file
11// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12// distribution for complete text of the license and disclaimer of any warranty.
b311480e 13//
973c2be1 14// Alternatively, this file may be used under the terms of Open CASCADE
15// commercial license or contractual agreement.
b311480e 16
7fd59977 17#include <Bnd_Box.ixx>
18
19#define VoidMask 0x01
20#define XminMask 0x02
21#define XmaxMask 0x04
22#define YminMask 0x08
23#define YmaxMask 0x10
24#define ZminMask 0x20
25#define ZmaxMask 0x40
26#define WholeMask 0x7e
27
28// Standard_True if the flag is one
29#define VoidFlag() ( Flags & VoidMask )
30#define XminFlag() ( Flags & XminMask )
31#define XmaxFlag() ( Flags & XmaxMask )
32#define YminFlag() ( Flags & YminMask )
33#define YmaxFlag() ( Flags & YmaxMask )
34#define ZminFlag() ( Flags & ZminMask )
35#define ZmaxFlag() ( Flags & ZmaxMask )
36#define WholeFlag() ( (Flags & WholeMask) == WholeMask )
37
38// set the flag to one
39#define SetVoidFlag() ( Flags = VoidMask )
40#define SetXminFlag() ( Flags |= XminMask )
41#define SetXmaxFlag() ( Flags |= XmaxMask )
42#define SetYminFlag() ( Flags |= YminMask )
43#define SetYmaxFlag() ( Flags |= YmaxMask )
44#define SetZminFlag() ( Flags |= ZminMask )
45#define SetZmaxFlag() ( Flags |= ZmaxMask )
46#define SetWholeFlag() ( Flags = WholeMask )
47
48#define ClearVoidFlag() ( Flags &= ~VoidMask )
49
50#include <Standard_Stream.hxx>
51#include <gp.hxx>
52// #include <Precision.hxx>
53#define Bnd_Precision_Infinite 1e+100
54
55//=======================================================================
56//function : Bnd_Box
57//purpose :
58//=======================================================================
59
60Bnd_Box::Bnd_Box()
61 : Xmin(0.), Xmax(0.), Ymin(0.), Ymax(0.), Zmin(0.), Zmax(0.), Gap(0.)
62{
63 SetVoid();
64}
65
66//=======================================================================
67//function : SetWhole
68//purpose :
69//=======================================================================
70
71void Bnd_Box::SetWhole ()
72{
73 SetWholeFlag();
74}
75
76//=======================================================================
77//function : SetVoid
78//purpose :
79//=======================================================================
80
81void Bnd_Box::SetVoid ()
82{
83 SetVoidFlag();
84 Gap=0.;
85}
86
87//=======================================================================
88//function : Set
89//purpose :
90//=======================================================================
91
92void Bnd_Box::Set(const gp_Pnt& P)
93{
94 SetVoid();
95 Add(P);
96}
97
98//=======================================================================
99//function : Set
100//purpose :
101//=======================================================================
102
103void Bnd_Box::Set(const gp_Pnt& P, const gp_Dir& D)
104{
105 SetVoid();
106 Add(P,D);
107}
108
109
110//=======================================================================
111//function : Update
112//purpose :
113//=======================================================================
114
115void Bnd_Box::Update (const Standard_Real x,
116 const Standard_Real y,
117 const Standard_Real z,
118 const Standard_Real X,
119 const Standard_Real Y,
120 const Standard_Real Z)
121{
122 if (VoidFlag()) {
123 Xmin = x;
124 Ymin = y;
125 Zmin = z;
126 Xmax = X;
127 Ymax = Y;
128 Zmax = Z;
129 ClearVoidFlag();
130 }
131 else {
132 if (!XminFlag() && (x < Xmin)) Xmin = x;
133 if (!XmaxFlag() && (X > Xmax)) Xmax = X;
134 if (!YminFlag() && (y < Ymin)) Ymin = y;
135 if (!YmaxFlag() && (Y > Ymax)) Ymax = Y;
136 if (!ZminFlag() && (z < Zmin)) Zmin = z;
137 if (!ZmaxFlag() && (Z > Zmax)) Zmax = Z;
138 }
139}
140
141//=======================================================================
142//function : Update
143//purpose :
144//=======================================================================
145
146void Bnd_Box::Update (const Standard_Real X,
147 const Standard_Real Y,
148 const Standard_Real Z)
149{
150 if (VoidFlag()) {
151 Xmin = X;
152 Ymin = Y;
153 Zmin = Z;
154 Xmax = X;
155 Ymax = Y;
156 Zmax = Z;
157 ClearVoidFlag();
158 }
159 else {
160 if (!XminFlag() && (X < Xmin)) Xmin = X;
161 else if (!XmaxFlag() && (X > Xmax)) Xmax = X;
162 if (!YminFlag() && (Y < Ymin)) Ymin = Y;
163 else if (!YmaxFlag() && (Y > Ymax)) Ymax = Y;
164 if (!ZminFlag() && (Z < Zmin)) Zmin = Z;
165 else if (!ZmaxFlag() && (Z > Zmax)) Zmax = Z;
166 }
167}
168
169//=======================================================================
170//function : GetGap
171//purpose :
172//=======================================================================
173
174Standard_Real Bnd_Box::GetGap () const
175{
176 return Gap;
177}
178
179//=======================================================================
180//function : SetGap
181//purpose :
182//=======================================================================
183
184void Bnd_Box::SetGap (const Standard_Real Tol)
185{
186 Gap = Tol;
187}
188
189//=======================================================================
190//function : Enlarge
191//purpose :
192//=======================================================================
193
194void Bnd_Box::Enlarge (const Standard_Real Tol)
195{
196 Gap=Max(Gap, Abs(Tol));
197}
198
199//=======================================================================
200//function : Get
201//purpose :
202//=======================================================================
203
ed063270 204void Bnd_Box::Get (Standard_Real& theXmin,
205 Standard_Real& theYmin,
206 Standard_Real& theZmin,
207 Standard_Real& theXmax,
208 Standard_Real& theYmax,
209 Standard_Real& theZmax) const
7fd59977 210{
ed063270 211 if (VoidFlag())
212 {
213 Standard_ConstructionError::Raise ("Bnd_Box is void");
214 }
215
216 if (XminFlag()) theXmin = -Bnd_Precision_Infinite;
217 else theXmin = Xmin - Gap;
218 if (XmaxFlag()) theXmax = Bnd_Precision_Infinite;
219 else theXmax = Xmax + Gap;
220 if (YminFlag()) theYmin = -Bnd_Precision_Infinite;
221 else theYmin = Ymin - Gap;
222 if (YmaxFlag()) theYmax = Bnd_Precision_Infinite;
223 else theYmax = Ymax + Gap;
224 if (ZminFlag()) theZmin = -Bnd_Precision_Infinite;
225 else theZmin = Zmin - Gap;
226 if (ZmaxFlag()) theZmax = Bnd_Precision_Infinite;
227 else theZmax = Zmax + Gap;
228}
229
230//=======================================================================
231//function : CornerMin
232//purpose :
233//=======================================================================
234
235gp_Pnt Bnd_Box::CornerMin() const
236{
237 gp_Pnt aCornerMin;
238 if (VoidFlag())
239 {
240 Standard_ConstructionError::Raise ("Bnd_Box is void");
241 return aCornerMin;
242 }
243 if (XminFlag()) aCornerMin.SetX (-Bnd_Precision_Infinite);
244 else aCornerMin.SetX (Xmin - Gap);
245 if (YminFlag()) aCornerMin.SetY (-Bnd_Precision_Infinite);
246 else aCornerMin.SetY (Ymin - Gap);
247 if (ZminFlag()) aCornerMin.SetZ (-Bnd_Precision_Infinite);
248 else aCornerMin.SetZ (Zmin - Gap);
249 return aCornerMin;
250}
251
252//=======================================================================
253//function : CornerMax
254//purpose :
255//=======================================================================
256
257gp_Pnt Bnd_Box::CornerMax() const
258{
259 gp_Pnt aCornerMax;
7fd59977 260 if(VoidFlag())
ed063270 261 {
262 Standard_ConstructionError::Raise ("Bnd_Box is void");
263 return aCornerMax;
264 }
265 if (XmaxFlag()) aCornerMax.SetX (Bnd_Precision_Infinite);
266 else aCornerMax.SetX (Xmax + Gap);
267 if (YminFlag()) aCornerMax.SetY (Bnd_Precision_Infinite);
268 else aCornerMax.SetY (Ymax + Gap);
269 if (ZminFlag()) aCornerMax.SetZ (Bnd_Precision_Infinite);
270 else aCornerMax.SetZ (Zmax + Gap);
271 return aCornerMax;
7fd59977 272}
273
274//=======================================================================
275//function : OpenXmin
276//purpose :
277//=======================================================================
278
279void Bnd_Box::OpenXmin ()
280{
281 SetXminFlag();
282}
283
284//=======================================================================
285//function : OpenXmax
286//purpose :
287//=======================================================================
288
289void Bnd_Box::OpenXmax ()
290{
291 SetXmaxFlag();
292}
293
294//=======================================================================
295//function : OpenYmin
296//purpose :
297//=======================================================================
298
299void Bnd_Box::OpenYmin ()
300{
301 SetYminFlag();
302}
303
304//=======================================================================
305//function : OpenYmax
306//purpose :
307//=======================================================================
308
309void Bnd_Box::OpenYmax ()
310{
311 SetYmaxFlag();
312}
313
314//=======================================================================
315//function : OpenZmin
316//purpose :
317//=======================================================================
318
319void Bnd_Box::OpenZmin ()
320{
321 SetZminFlag();
322}
323
324//=======================================================================
325//function : OpenZmax
326//purpose :
327//=======================================================================
328
329void Bnd_Box::OpenZmax ()
330{
331 SetZmaxFlag();
332}
333
334//=======================================================================
335//function : IsOpenXmin
336//purpose :
337//=======================================================================
338
339Standard_Boolean Bnd_Box::IsOpenXmin () const
340{
341 return XminFlag();
342}
343
344//=======================================================================
345//function : IsOpenXmax
346//purpose :
347//=======================================================================
348
349Standard_Boolean Bnd_Box::IsOpenXmax () const
350{
351 return XmaxFlag();
352}
353
354//=======================================================================
355//function : IsOpenYmin
356//purpose :
357//=======================================================================
358
359Standard_Boolean Bnd_Box::IsOpenYmin () const
360{
361 return YminFlag();
362}
363
364//=======================================================================
365//function : IsOpenYmax
366//purpose :
367//=======================================================================
368
369Standard_Boolean Bnd_Box::IsOpenYmax () const
370{
371 return YmaxFlag();
372}
373
374//=======================================================================
375//function : IsOpenZmin
376//purpose :
377//=======================================================================
378
379Standard_Boolean Bnd_Box::IsOpenZmin () const
380{
381 return ZminFlag();
382}
383
384//=======================================================================
385//function : IsOpenZmax
386//purpose :
387//=======================================================================
388
389Standard_Boolean Bnd_Box::IsOpenZmax () const
390{
391 return ZmaxFlag();
392}
393
394//=======================================================================
395//function : IsWhole
396//purpose :
397//=======================================================================
398
399Standard_Boolean Bnd_Box::IsWhole () const
400{
401 return WholeFlag();
402}
403
404//=======================================================================
405//function : IsVoid
406//purpose :
407//=======================================================================
408
409Standard_Boolean Bnd_Box::IsVoid () const
410{
411 return VoidFlag();
412}
413
414//=======================================================================
415//function : IsXThin
416//purpose :
417//=======================================================================
418
419Standard_Boolean Bnd_Box::IsXThin (const Standard_Real tol) const
420{
421 if (IsWhole()) return Standard_False;
422 if (IsVoid()) return Standard_True;
423 if (XminFlag()) return Standard_False;
424 if (XmaxFlag()) return Standard_False;
425 if (Xmax-Xmin < tol) return Standard_True;
426 return Standard_False;
427}
428
429//=======================================================================
430//function : IsYThin
431//purpose :
432//=======================================================================
433
434Standard_Boolean Bnd_Box::IsYThin (const Standard_Real tol) const
435{
436 if (IsWhole()) return Standard_False;
437 if (IsVoid()) return Standard_True;
438 if (YminFlag()) return Standard_False;
439 if (YmaxFlag()) return Standard_False;
440 if (Ymax-Ymin < tol) return Standard_True;
441 return Standard_False;
442}
443
444//=======================================================================
445//function : IsZThin
446//purpose :
447//=======================================================================
448
449Standard_Boolean Bnd_Box::IsZThin (const Standard_Real tol) const
450{
451 if (IsWhole()) return Standard_False;
452 if (IsVoid()) return Standard_True;
453 if (ZminFlag()) return Standard_False;
454 if (ZmaxFlag()) return Standard_False;
455 if (Zmax-Zmin < tol) return Standard_True;
456 return Standard_False;
457}
458
459//=======================================================================
460//function : IsThin
461//purpose :
462//=======================================================================
463
464Standard_Boolean Bnd_Box::IsThin (const Standard_Real tol) const
465{
466 if (!IsXThin(tol)) return Standard_False;
467 if (!IsYThin(tol)) return Standard_False;
468 if (!IsZThin(tol)) return Standard_False;
469 return Standard_True;
470}
471
472//=======================================================================
473//function : Transformed
474//purpose :
475//=======================================================================
476
477Bnd_Box Bnd_Box::Transformed (const gp_Trsf& T) const
478{
479 gp_TrsfForm F = T.Form();
480 Bnd_Box newb(*this);
481 if ( IsVoid() ) return newb;
482
483 if (F == gp_Identity) {}
484 else if (F == gp_Translation) {
485 Standard_Real DX,DY,DZ;
486 (T.TranslationPart()).Coord(DX,DY,DZ);
487 if (!XminFlag()) newb.Xmin += DX;
488 if (!XmaxFlag()) newb.Xmax += DX;
489 if (!YminFlag()) newb.Ymin += DY;
490 if (!YmaxFlag()) newb.Ymax += DY;
491 if (!ZminFlag()) newb.Zmin += DZ;
492 if (!ZmaxFlag()) newb.Zmax += DZ;
493 }
494 else {
495 gp_Pnt P[8];
496 Standard_Boolean Vertex[8];
497 Standard_Integer i;
498 for (i=0;i<8;i++) Vertex[i] = Standard_True;
499 gp_Dir D[6];
500// Standard_Integer vertices = 0;
501 Standard_Integer directions = 0;
502
503 if (XminFlag()) {
504 directions++;
505 D[directions-1].SetCoord(-1., 0., 0.);
506 Vertex[0] = Vertex[2] = Vertex[4] = Vertex[6] = Standard_False;
507 }
508 if (XmaxFlag()) {
509 directions++;
510 D[directions-1].SetCoord( 1., 0., 0.);
511 Vertex[1] = Vertex[3] = Vertex[5] = Vertex[7] = Standard_False;
512 }
513 if (YminFlag()) {
514 directions++;
515 D[directions-1].SetCoord( 0.,-1., 0.);
516 Vertex[0] = Vertex[1] = Vertex[4] = Vertex[5] = Standard_False;
517 }
518 if (YmaxFlag()) {
519 directions++;
520 D[directions-1].SetCoord( 0., 1., 0.);
521 Vertex[2] = Vertex[3] = Vertex[6] = Vertex[7] = Standard_False;
522 }
523 if (ZminFlag()) {
524 directions++;
525 D[directions-1].SetCoord( 0., 0.,-1.);
526 Vertex[0] = Vertex[1] = Vertex[2] = Vertex[3] = Standard_False;
527 }
528 if (ZmaxFlag()) {
529 directions++;
530 D[directions-1].SetCoord( 0., 0., 1.);
531 Vertex[4] = Vertex[5] = Vertex[6] = Vertex[7] = Standard_False;
532 }
533
534 newb.SetVoid();
535 for (i=0;i<directions;i++) {
536 D[i].Transform(T);
537 newb.Add(D[i]);
538 }
539 P[0].SetCoord(Xmin,Ymin,Zmin);
540 P[1].SetCoord(Xmax,Ymin,Zmin);
541 P[2].SetCoord(Xmin,Ymax,Zmin);
542 P[3].SetCoord(Xmax,Ymax,Zmin);
543 P[4].SetCoord(Xmin,Ymin,Zmax);
544 P[5].SetCoord(Xmax,Ymin,Zmax);
545 P[6].SetCoord(Xmin,Ymax,Zmax);
546 P[7].SetCoord(Xmax,Ymax,Zmax);
547 for (i=0;i<8;i++) {
548 if (Vertex[i]) {
549 P[i].Transform(T);
550 newb.Add(P[i]);
551 }
552 }
553 newb.Gap=Gap;
554 }
555 return newb;
556}
557
558//=======================================================================
559//function : Add
560//purpose :
561//=======================================================================
562
563void Bnd_Box::Add (const Bnd_Box& Other)
564{
565 if (IsWhole()) return;
566 else if (Other.IsVoid()) return;
567 else if (Other.IsWhole()) SetWhole();
568 else if (IsVoid()) (*this) = Other;
569 else
570 {
571 if ( ! IsOpenXmin() )
572 {
573 if (Other.IsOpenXmin()) OpenXmin();
574 else if (Xmin > Other.Xmin) Xmin = Other.Xmin;
575 }
576 if ( ! IsOpenXmax() )
577 {
578 if (Other.IsOpenXmax()) OpenXmax();
579 else if (Xmax < Other.Xmax) Xmax = Other.Xmax;
580 }
581 if ( ! IsOpenYmin() )
582 {
583 if (Other.IsOpenYmin()) OpenYmin();
584 else if (Ymin > Other.Ymin) Ymin = Other.Ymin;
585 }
586 if ( ! IsOpenYmax() )
587 {
588 if (Other.IsOpenYmax()) OpenYmax();
589 else if (Ymax < Other.Ymax) Ymax = Other.Ymax;
590 }
591 if ( ! IsOpenZmin() )
592 {
593 if (Other.IsOpenZmin()) OpenZmin();
594 else if (Zmin > Other.Zmin) Zmin = Other.Zmin;
595 }
596 if ( ! IsOpenZmax() )
597 {
598 if (Other.IsOpenZmax()) OpenZmax();
599 else if (Zmax < Other.Zmax) Zmax = Other.Zmax;
600 }
601 Gap = Max (Gap, Other.Gap);
602 }
603}
604
605//=======================================================================
606//function : Add
607//purpose :
608//=======================================================================
609
610void Bnd_Box::Add (const gp_Pnt& P)
611{
612 Standard_Real X,Y,Z;
613 P.Coord(X,Y,Z);
614 Update(X,Y,Z);
615}
616
617//=======================================================================
618//function : Add
619//purpose :
620//=======================================================================
621
622void Bnd_Box::Add (const gp_Pnt& P, const gp_Dir& D)
623{
624 Add(P);
625 Add(D);
626}
627
628
629//=======================================================================
630//function : Add
631//purpose :
632//=======================================================================
633
634void Bnd_Box::Add (const gp_Dir& D)
635{
636 Standard_Real DX,DY,DZ;
637 D.Coord(DX,DY,DZ);
44d9ae89
A
638
639 if (DX < -RealEpsilon())
640 OpenXmin();
641 else if (DX > RealEpsilon())
642 OpenXmax();
643
644 if (DY < -RealEpsilon())
645 OpenYmin();
646 else if (DY > RealEpsilon())
647 OpenYmax();
648
649 if (DZ < -RealEpsilon())
650 OpenZmin();
651 else if (DZ > RealEpsilon())
652 OpenZmax();
7fd59977 653}
654
655//=======================================================================
656//function : IsOut
657//purpose :
658//=======================================================================
659
660Standard_Boolean Bnd_Box::IsOut (const gp_Pnt& P) const
661{
662 if (IsWhole()) return Standard_False;
663 else if (IsVoid()) return Standard_True;
664 else {
665 Standard_Real X,Y,Z;
666 P.Coord(X,Y,Z);
667 if (!XminFlag() && (X < (Xmin-Gap))) return Standard_True;
668 else if (!XmaxFlag() && (X > (Xmax+Gap))) return Standard_True;
669 else if (!YminFlag() && (Y < (Ymin-Gap))) return Standard_True;
670 else if (!YmaxFlag() && (Y > (Ymax+Gap))) return Standard_True;
671 else if (!ZminFlag() && (Z < (Zmin-Gap))) return Standard_True;
672 else if (!ZmaxFlag() && (Z > (Zmax+Gap))) return Standard_True;
673 else return Standard_False;
674 }
675}
676
677
678//=======================================================================
679//function : IsOut
680//purpose :
681//=======================================================================
682
683Standard_Boolean Bnd_Box::IsOut (const gp_Pln& P) const
684{
685 if (IsWhole()) return Standard_False;
686 else if (IsVoid()) return Standard_True;
687 else {
688 Standard_Real A,B,C,D;
689 P.Coefficients (A, B ,C ,D);
690 Standard_Real d = A * (Xmin-Gap) + B * (Ymin-Gap) + C * (Zmin-Gap) + D;
691// Standard_Boolean plus = d > 0;
692 Standard_Integer plus = d > 0;
693 if (plus != ((A*(Xmin-Gap) + B*(Ymin-Gap) + C*(Zmax+Gap) + D) > 0))
694 return Standard_False;
695 if (plus != ((A*(Xmin-Gap) + B*(Ymax+Gap) + C*(Zmin-Gap) + D) > 0))
696 return Standard_False;
697 if (plus != ((A*(Xmin-Gap) + B*(Ymax+Gap) + C*(Zmax+Gap) + D) > 0))
698 return Standard_False;
699 if (plus != ((A*(Xmax+Gap) + B*(Ymin-Gap) + C*(Zmin-Gap) + D) > 0))
700 return Standard_False;
701 if (plus != ((A*(Xmax+Gap) + B*(Ymin-Gap) + C*(Zmax+Gap) + D) > 0))
702 return Standard_False;
703 if (plus != ((A*(Xmax+Gap) + B*(Ymax+Gap) + C*(Zmin-Gap) + D) > 0))
704 return Standard_False;
705 if (plus != ((A*(Xmax+Gap) + B*(Ymax+Gap) + C*(Zmax+Gap) + D) > 0))
706 return Standard_False;
707 else return Standard_True;
708 }
709}
710
711//=======================================================================
712//function : IsOut
713//purpose :
714//=======================================================================
715
716Standard_Boolean Bnd_Box::IsOut (const gp_Lin& L) const
717{
718 if (IsWhole()) return Standard_False;
719 else if (IsVoid()) return Standard_True;
720 else {
721 Standard_Real xmin = 0, xmax = 0, ymin = 0, ymax = 0, zmin, zmax;
722 Standard_Real parmin, parmax, par1, par2;
723 Standard_Boolean xToSet, yToSet;
724 Standard_Real myXmin, myYmin, myZmin, myXmax, myYmax, myZmax;
725 Get (myXmin, myYmin, myZmin, myXmax, myYmax, myZmax);
726
727 if (Abs(L.Direction().XYZ().X())>0.) {
728 par1=(myXmin-L.Location().XYZ().X())/L.Direction().XYZ().X();
729 par2=(myXmax-L.Location().XYZ().X())/L.Direction().XYZ().X();
730 parmin=Min(par1, par2);
731 parmax=Max(par1, par2);
732 xToSet=Standard_True;
733 }
734 else {
735 if (L.Location().XYZ().X()<myXmin || myXmax<L.Location().XYZ().X()) {
736 return Standard_True;
737 }
738 xmin=L.Location().XYZ().X();
739 xmax=L.Location().XYZ().X();
740 parmin=-Bnd_Precision_Infinite;
741 parmax=Bnd_Precision_Infinite;
742 xToSet=Standard_False;
743 }
744
745 if (Abs(L.Direction().XYZ().Y())>0.) {
746 par1=(myYmin-L.Location().XYZ().Y())/L.Direction().XYZ().Y();
747 par2=(myYmax-L.Location().XYZ().Y())/L.Direction().XYZ().Y();
748 //=================DET change 06/03/01====================
749 if(parmax < Min(par1,par2) || parmin > Max(par1,par2))
750 return Standard_True;
751 //========================================================
752 parmin=Max(parmin, Min(par1,par2));
753 parmax=Min(parmax, Max(par1,par2));
754 yToSet=Standard_True;
755 }
756 else {
757 if (L.Location().XYZ().Y()<myYmin || myYmax<L.Location().XYZ().Y()) {
758 return Standard_True;
759 }
760 ymin=L.Location().XYZ().Y();
761 ymax=L.Location().XYZ().Y();
762 yToSet=Standard_False;
763 }
764
765 if (Abs(L.Direction().XYZ().Z())>0.) {
766 par1=(myZmin-L.Location().XYZ().Z())/L.Direction().XYZ().Z();
767 par2=(myZmax-L.Location().XYZ().Z())/L.Direction().XYZ().Z();
768 //=================DET change 06/03/01====================
769 if(parmax < Min(par1,par2) || parmin > Max(par1,par2))
770 return Standard_True;
771 //========================================================
772 parmin=Max(parmin, Min(par1,par2));
773 parmax=Min(parmax, Max(par1,par2));
774 par1=L.Location().XYZ().Z()+parmin*L.Direction().XYZ().Z();
775 par2=L.Location().XYZ().Z()+parmax*L.Direction().XYZ().Z();
776 zmin=Min(par1, par2);
777 zmax=Max(par1, par2);
778 }
779 else {
780 if (L.Location().XYZ().Z()<myZmin || myZmax<L.Location().XYZ().Z())
781 return Standard_True;
782 zmin=L.Location().XYZ().Z();
783 zmax=L.Location().XYZ().Z();
784 }
785 if (zmax<myZmin || myZmax<zmin) return Standard_True;
786
787 if (xToSet) {
788 par1=L.Location().XYZ().X()+parmin*L.Direction().XYZ().X();
789 par2=L.Location().XYZ().X()+parmax*L.Direction().XYZ().X();
790 xmin=Min(par1, par2);
791 xmax=Max(par1, par2);
792 }
793 if (xmax<myXmin || myXmax<xmin) return Standard_True;
794
795 if (yToSet) {
796 par1=L.Location().XYZ().Y()+parmin*L.Direction().XYZ().Y();
797 par2=L.Location().XYZ().Y()+parmax*L.Direction().XYZ().Y();
798 ymin=Min(par1, par2);
799 ymax=Max(par1, par2);
800 }
801 if (ymax<myYmin || myYmax<ymin) return Standard_True;
802 }
803 return Standard_False;
804}
805
806//=======================================================================
807//function : IsOut
808//purpose :
809//=======================================================================
810
811Standard_Boolean Bnd_Box::IsOut (const Bnd_Box& Other) const
aa396061
P
812{
813 //modified by NIZNHY-PKV Fri Jul 08 11:03:43 2011f
814 if (!Flags && !Other.Flags) {
815 Standard_Boolean bRet;
816 Standard_Real delta;
817 //
818 delta = Other.Gap + Gap;
819 bRet=((Xmin - Other.Xmax > delta) ||
820 (Other.Xmin - Xmax > delta) ||
821 (Ymin - Other.Ymax > delta) ||
822 (Other.Ymin - Ymax > delta) ||
823 (Zmin - Other.Zmax > delta) ||
824 (Other.Zmin - Zmax > delta));
825 return bRet;
826 }
827 //modified by NIZNHY-PKV Fri Jul 08 11:03:46 2011t
7fd59977 828 if (IsVoid()) return Standard_True;
829 if (Other.IsVoid()) return Standard_True;
830 if (IsWhole()) return Standard_False;
831 if (Other.IsWhole()) return Standard_False;
832
833 Standard_Real delta = Other.Gap + Gap;
834
835 if (!XminFlag() && !Other.IsOpenXmax())
836 if (Xmin - Other.Xmax > delta) return Standard_True;
837 if (!XmaxFlag() && !Other.IsOpenXmin())
838 if (Other.Xmin - Xmax > delta) return Standard_True;
839
840 if (!YminFlag() && !Other.IsOpenYmax())
841 if (Ymin - Other.Ymax > delta) return Standard_True;
842 if (!YmaxFlag() && !Other.IsOpenYmin())
843 if (Other.Ymin - Ymax > delta) return Standard_True;
844
845 if (!ZminFlag() && !Other.IsOpenZmax())
846 if (Zmin - Other.Zmax > delta) return Standard_True;
847 if (!ZmaxFlag() && !Other.IsOpenZmin())
848 if (Other.Zmin - Zmax > delta) return Standard_True;
849
850 return Standard_False;
851}
852
853//=======================================================================
854//function : IsOut
855//purpose :
856//=======================================================================
857
858Standard_Boolean Bnd_Box::IsOut (const Bnd_Box& Other,
859 const gp_Trsf& T) const
860{
861 return IsOut(Other.Transformed(T));
862}
863
864//=======================================================================
865//function : IsOut
866//purpose :
867//=======================================================================
868
869Standard_Boolean Bnd_Box::IsOut (const gp_Trsf& T1,
870 const Bnd_Box& Other,
871 const gp_Trsf& T2) const
872{
873 return Transformed(T1).IsOut(Other.Transformed(T2));
874}
875
876
877//=======================================================================
0ebaa4db 878//function : IsSegmentOut
7fd59977 879//purpose :
880//=======================================================================
881
882static Standard_Boolean IsSegmentOut(Standard_Real x1,Standard_Real y1,
883 Standard_Real x2,Standard_Real y2,
884 Standard_Real xs1,Standard_Real ys1,
885 Standard_Real xs2,Standard_Real ys2)
886{
887 Standard_Real eps = RealSmall();
888 Standard_Real xsmin = Min (xs1, xs2);
889 Standard_Real xsmax = Max (xs1, xs2);
890 Standard_Real ysmin = Min (ys1, ys2);
891 Standard_Real ysmax = Max (ys1, ys2);
892
893 if (ysmax-ysmin < eps && (y1-ys1 < eps && ys1-y2 < eps) &&
0ebaa4db 894 ((xsmin-x1 < eps && x1-xsmax < eps) ||
895 (xsmin-x2 < eps && x2-xsmax < eps) ||
896 (x1-xs1 < eps && xs1-x2 < eps)))
7fd59977 897 return Standard_False;
898 if (xsmax-xsmin < eps && (x1-xs1 < eps && xs1-x2 < eps) &&
0ebaa4db 899 ((ysmin-y1 < eps && y1-ysmax < eps) ||
900 (ysmin-y2 < eps && y2-ysmax < eps) ||
901 (y1-ys1 < eps && ys1-y2 < eps)))
7fd59977 902 return Standard_False;
903
904 if ((xs1 < x1 && xs2 < x1) || (xs1 > x2 && xs2 > x2) ||
905 (ys1 < y1 && ys2 < y1) || (ys1 > y2 && ys2 > y2) )
906 return Standard_True;
907
908 if (Abs(xs2-xs1) > eps)
909 {
910 Standard_Real ya = ( Min(x1, x2) - xs1 ) * ( ys2 - ys1 ) / ( xs2 - xs1 ) + ys1;
911 Standard_Real yb = ( Max(x1, x2) - xs1 ) * ( ys2 - ys1 ) / ( xs2 - xs1 ) + ys1;
912 if ( (ya < y1 && yb < y1) || (ya > y2 && yb > y2) ) return Standard_True;
913 }
914 else if (Abs(ys2-ys1) > eps)
915 {
916 Standard_Real xa = ( Min(y1, y2) - ys1 ) * ( xs2 - xs1 ) / ( ys2 - ys1 ) + xs1;
917 Standard_Real xb = ( Max(y1, y2) - ys1 ) * ( xs2 - xs1 ) / ( ys2 - ys1 ) + xs1;
918 if ( (xa < x1 && xb < x1) || (xa > x2 && xb > x2) ) return Standard_True;
919 }
920 else
921 return Standard_True;
922
923 return Standard_False;
924}
925
926Standard_Boolean Bnd_Box::IsOut(const gp_Pnt& P1, const gp_Pnt& P2, const gp_Dir& D) const
927{
928
929 if (IsWhole()) return Standard_False;
930 else if (IsVoid()) return Standard_True;
931
932 Standard_Real eps = RealSmall();
933 Standard_Real myXmin, myYmin, myZmin, myXmax, myYmax, myZmax;
934 Get (myXmin, myYmin, myZmin, myXmax, myYmax, myZmax);
935
936 if(Abs(D.X()) < eps && Abs(D.Y()) < eps)
937 return IsSegmentOut(myXmin, myYmin, myXmax, myYmax, P1.X(), P1.Y(), P2.X(), P2.Y());
938
939 if(Abs(D.X()) < eps && Abs(D.Z()) < eps)
940 return IsSegmentOut(myXmin, myZmin, myXmax, myZmax, P1.X(), P1.Z(), P2.X(), P2.Z());
941
942 if(Abs(D.Y()) < eps && Abs(D.Z()) < eps)
943 return IsSegmentOut(myYmin, myZmin, myYmax, myZmax, P1.Y(), P1.Z(), P2.Y(), P2.Z());
944
945 if(Abs(D.X()) < eps)
946 {
947 if(!IsSegmentOut(myXmin, myZmin, myXmax, myZmax,
948 P1.X(),(myYmin-P1.Y())*D.Z()/D.Y()+P1.Z(),
949 P2.X(),(myYmin-P2.Y())*D.Z()/D.Y()+P2.Z()))
950 return Standard_False;
951
952 if(!IsSegmentOut(myXmin, myZmin, myXmax, myZmax,
953 P1.X(),(myYmax-P1.Y())*D.Z()/D.Y()+P1.Z(),
954 P2.X(),(myYmax-P2.Y())*D.Z()/D.Y()+P2.Z()))
955 return Standard_False;
956
957 if(!IsSegmentOut(myXmin, myYmin, myXmax, myYmax,
958 P1.X(),(myZmin-P1.Z())*D.Y()/D.Z()+P1.Y(),
959 P2.X(),(myZmin-P2.Z())*D.Y()/D.Z()+P2.Y()))
960 return Standard_False;
961
962 if(!IsSegmentOut(myXmin, myYmin, myXmax, myYmax,
963 P1.X(),(myZmax-P1.Z())*D.Y()/D.Z()+P1.Y(),
964 P2.X(),(myZmax-P2.Z())*D.Y()/D.Z()+P2.Y()))
965 return Standard_False;
966
967 return Standard_True;
968 }//if(D.X() == 0)
969
970 if(Abs(D.Y()) < eps)
971 {
972 if(!IsSegmentOut(myYmin, myZmin, myYmax, myZmax,
973 P1.Y(),(myXmin-P1.X())*D.Z()/D.X()+P1.Z(),
974 P2.Y(),(myXmin-P2.X())*D.Z()/D.X()+P2.Z()))
975 return Standard_False;
976
977 if(!IsSegmentOut(myYmin, myZmin, myYmax, myZmax,
978 P1.Y(),(myXmax-P1.X())*D.Z()/D.X()+P1.Z(),
979 P2.Y(),(myXmax-P2.X())*D.Z()/D.X()+P2.Z()))
980 return Standard_False;
981
982 if(!IsSegmentOut(myYmin, myXmin, myYmax, myXmax,
983 P1.Y(),(myZmin-P1.Z())*D.X()/D.Z()+P1.X(),
984 P2.Y(),(myZmin-P2.Z())*D.X()/D.Z()+P2.X()))
985 return Standard_False;
986
987 if(!IsSegmentOut(myYmin, myXmin, myYmax, myXmax,
988 P1.Y(),(myZmax-P1.Z())*D.X()/D.Z()+P1.X(),
989 P2.Y(),(myZmax-P2.Z())*D.X()/D.Z()+P2.X()))
990 return Standard_False;
991
992 return Standard_True;
993 }//if(D.Y() == 0)
994
995 if(Abs(D.Z()) < eps)
996 {
997 if(!IsSegmentOut(myZmin, myXmin, myZmax, myXmax,
998 P1.Z(),(myYmax-P1.Y())*D.X()/D.Y()+P1.X(),
999 P2.Z(),(myYmax-P2.Y())*D.X()/D.Y()+P2.X()))
1000 return Standard_False;
1001
1002 if(!IsSegmentOut(myZmin, myXmin, myZmax, myXmax,
1003 P1.Z(),(myYmin-P1.Y())*D.X()/D.Y()+P1.X(),
1004 P2.Z(),(myYmin-P2.Y())*D.X()/D.Y()+P2.X()))
1005 return Standard_False;
1006
1007 if(!IsSegmentOut(myZmin, myYmin, myZmax, myYmax,
1008 P1.Z(),(myXmax-P1.X())*D.Y()/D.X()+P1.Y(),
1009 P2.Z(),(myXmax-P2.X())*D.Y()/D.X()+P2.Y()))
1010 return Standard_False;
1011
1012 if(!IsSegmentOut(myZmin, myYmin, myZmax, myYmax,
1013 P1.Z(),(myXmin-P1.X())*D.Y()/D.X()+P1.Y(),
1014 P2.Z(),(myXmin-P2.X())*D.Y()/D.X()+P2.Y()))
1015 return Standard_False;
1016
1017 return Standard_True;
1018 }//if(D.Z() == 0)
1019
1020 if(!IsSegmentOut(myXmin,myZmin,myXmax,myZmax,
1021 (myYmin - P1.Y())/D.Y()*D.X() + P1.X(),
1022 (myYmin - P1.Y())/D.Y()*D.Z() + P1.Z(),
1023 (myYmin - P2.Y())/D.Y()*D.X() + P2.X(),
1024 (myYmin - P2.Y())/D.Y()*D.Z() + P2.Z()))
1025 return Standard_False;
1026
1027 if(!IsSegmentOut(myXmin,myZmin,myXmax,myZmax,
1028 (myYmax - P1.Y())/D.Y()*D.X() + P1.X(),
1029 (myYmax - P1.Y())/D.Y()*D.Z() + P1.Z(),
1030 (myYmax - P2.Y())/D.Y()*D.X() + P2.X(),
1031 (myYmax - P2.Y())/D.Y()*D.Z() + P2.Z()))
1032 return Standard_False;
1033
1034 if(!IsSegmentOut(myXmin,myYmin,myXmax,myYmax,
1035 (myZmin - P1.Z())/D.Z()*D.X() + P1.X(),
1036 (myZmin - P1.Z())/D.Z()*D.Y() + P1.Y(),
1037 (myZmin - P2.Z())/D.Z()*D.X() + P2.X(),
1038 (myZmin - P2.Z())/D.Z()*D.Y() + P2.Y()))
1039 return Standard_False;
1040
1041 if(!IsSegmentOut(myXmin,myYmin,myXmax,myYmax,
1042 (myZmax - P1.Z())/D.Z()*D.X() + P1.X(),
1043 (myZmax - P1.Z())/D.Z()*D.Y() + P1.Y(),
1044 (myZmax - P2.Z())/D.Z()*D.X() + P2.X(),
1045 (myZmax - P2.Z())/D.Z()*D.Y() + P2.Y()))
1046 return Standard_False;
1047
1048 if(!IsSegmentOut(myZmin,myYmin,myZmax,myYmax,
1049 (myXmin - P1.X())/D.X()*D.Z() + P1.Z(),
1050 (myXmin - P1.X())/D.X()*D.Y() + P1.Y(),
1051 (myXmin - P2.X())/D.X()*D.Z() + P2.Z(),
1052 (myXmin - P2.X())/D.X()*D.Y() + P2.Y()))
1053 return Standard_False;
1054
1055 if(!IsSegmentOut(myZmin,myYmin,myZmax,myYmax,
1056 (myXmax - P1.X())/D.X()*D.Z() + P1.Z(),
1057 (myXmax - P1.X())/D.X()*D.Y() + P1.Y(),
1058 (myXmax - P2.X())/D.X()*D.Z() + P2.Z(),
1059 (myXmax - P2.X())/D.X()*D.Y() + P2.Y()))
1060 return Standard_False;
1061
1062 return Standard_True;
1063
1064}
1065
1066//=======================================================================
1067//function : Distance
1068//purpose : computes the minimum distance between two boxes
1069//=======================================================================
1070
1071static Standard_Real DistMini2Box( const Standard_Real r1min, const Standard_Real r1max, const Standard_Real r2min, const Standard_Real r2max)
1072{ Standard_Real r1, r2;
1073
1074 r1 = Square(r1min - r2max);
1075 r2 = Square(r1max - r2min);
1076 return (Min( r1, r2 ));
1077}
1078
1079
1080
1081Standard_Real Bnd_Box::Distance(const Bnd_Box& Other) const
1082{ Standard_Real xminB1, yminB1, zminB1, xmaxB1, ymaxB1, zmaxB1;
1083 Standard_Real xminB2, yminB2, zminB2, xmaxB2, ymaxB2, zmaxB2;
1084 Standard_Real dist_x, dist_y, dist_z, dist_t;
1085
1086 Get( xminB1, yminB1, zminB1, xmaxB1, ymaxB1, zmaxB1);
1087 Other.Get( xminB2, yminB2, zminB2, xmaxB2, ymaxB2, zmaxB2);
1088
1089 if ( ((xminB1<= xminB2)&&( xminB2 <= xmaxB1)) || ((xminB2<= xminB1)&&( xminB1 <= xmaxB2)) )
1090 { dist_x=0; }
1091 else { dist_x= DistMini2Box(xminB1, xmaxB1, xminB2, xmaxB2);}
1092 if ( ((yminB1<= yminB2)&&( yminB2 <= ymaxB1)) || ((yminB2<= yminB1)&&( yminB1 <= ymaxB2)) )
1093 { dist_y=0; }
1094 else { dist_y= DistMini2Box(yminB1, ymaxB1, yminB2, ymaxB2);}
1095 if ( ((zminB1<= zminB2)&&( zminB2 <= zmaxB1)) || ((zminB2<= zminB1)&&( zminB1 <= zmaxB2)) )
1096 { dist_z=0; }
1097 else { dist_z= DistMini2Box(zminB1, zmaxB1, zminB2, zmaxB2);}
1098 dist_t = dist_x+ dist_y+ dist_z;
1099 return( Sqrt ( dist_t));
1100}
1101
1102//=======================================================================
1103//function : Dump
1104//purpose :
1105//=======================================================================
1106
1107void Bnd_Box::Dump () const
1108{
1109 cout << "Box3D : ";
1110 if (IsVoid()) cout << "Void";
1111 else if (IsWhole()) cout << "Whole";
1112 else {
1113 cout << "\n Xmin : ";
1114 if (IsOpenXmin()) cout << "Infinite";
1115 else cout << Xmin;
1116 cout << "\n Xmax : ";
1117 if (IsOpenXmax()) cout << "Infinite";
1118 else cout << Xmax;
1119 cout << "\n Ymin : ";
1120 if (IsOpenYmin()) cout << "Infinite";
1121 else cout << Ymin;
1122 cout << "\n Ymax : ";
1123 if (IsOpenYmax()) cout << "Infinite";
1124 else cout << Ymax;
1125 cout << "\n Zmin : ";
1126 if (IsOpenZmin()) cout << "Infinite";
1127 else cout << Zmin;
1128 cout << "\n Zmax : ";
1129 if (IsOpenZmax()) cout << "Infinite";
1130 else cout << Zmax;
1131 }
1132 cout << "\n Gap : " << Gap;
1133 cout << "\n";
1134}