59 : fPolygons(&polygons)
71 for (
auto ipoint = (*ibase)->cbegin(); ipoint != (*ibase)->cend(); ++ipoint)
74 if (x < xmin) xmin = x;
75 if (x > xmax) xmax = x;
77 if (y < ymin) ymin = y;
78 if (y > ymax) ymax = y;
80 if (z < zmin) zmin = z;
81 if (z > zmax) zmax = z;
99 const std::vector<const G4ThreeVectorList*>& polygons)
100 : fMin(
pMin), fMax(
pMax), fPolygons(&polygons)
116 std::ostringstream message;
117 message <<
"Badly defined bounding box (min >= max)!"
118 <<
"\npMin = " <<
fMin
119 <<
"\npMax = " <<
fMax;
120 G4Exception(
"G4BoundingEnvelope::CheckBoundingBox()",
135 std::ostringstream message;
136 message <<
"Wrong number of polygons in the sequence: " << nbases
137 <<
"\nShould be at least two!";
138 G4Exception(
"G4BoundingEnvelope::CheckBoundingPolygons()",
146 std::ostringstream message;
147 message <<
"Badly constructed polygons!"
148 <<
"\nNumber of polygons: " << nbases
149 <<
"\nPolygon #0 size: " << (*fPolygons)[0]->size()
150 <<
"\nPolygon #1 size: " << (*fPolygons)[1]->size()
152 G4Exception(
"G4BoundingEnvelope::CheckBoundingPolygons()",
157 for (
G4int k=0; k<nbases; ++k)
159 G4int np = (*fPolygons)[k]->size();
160 if (np == nsize)
continue;
161 if (np == 1 && k==0)
continue;
162 if (np == 1 && k==nbases-1)
continue;
163 std::ostringstream message;
164 message <<
"Badly constructed polygons!"
165 <<
"\nNumber of polygons: " << nbases
166 <<
"\nPolygon #" << k <<
" size: " << np
167 <<
"\nexpected size: " << nsize;
168 G4Exception(
"G4BoundingEnvelope::SetBoundingPolygons()",
197 if (pTransform3D.
xx()==1 && pTransform3D.
yy()==1 && pTransform3D.
zz()==1)
213 if (xmin >= xminlim && xmax <= xmaxlim &&
214 ymin >= yminlim && ymax <= ymaxlim &&
215 zmin >= zminlim && zmax <= zmaxlim)
252 if (center.
x()-radius > xmaxlim)
return true;
253 if (center.
y()-radius > ymaxlim)
return true;
254 if (center.
z()-radius > zmaxlim)
return true;
255 if (center.
x()+radius < xminlim)
return true;
256 if (center.
y()+radius < yminlim)
return true;
257 if (center.
z()+radius < zminlim)
return true;
282 if (pTransform3D.
xx()==1 && pTransform3D.
yy()==1 && pTransform3D.
zz()==1)
335 if (center.
x()-radius >= xminlim && center.
x()+radius <= xmaxlim &&
336 center.
y()-radius >= yminlim && center.
y()+radius <= ymaxlim &&
337 center.
z()-radius >= zminlim && center.
z()+radius <= zmaxlim )
342 cx = pTransform3D.
xx();
343 cy = pTransform3D.
xy();
344 cz = pTransform3D.
xz();
345 cd = pTransform3D.
dx();
349 cx = pTransform3D.
yx();
350 cy = pTransform3D.
yy();
351 cz = pTransform3D.
yz();
352 cd = pTransform3D.
dy();
356 cx = pTransform3D.
zx();
357 cy = pTransform3D.
zy();
358 cz = pTransform3D.
zz();
359 cd = pTransform3D.
dz();
370 if (coor < emin) emin = coor;
373 if (coor < emin) emin = coor;
376 if (coor < emin) emin = coor;
379 if (coor < emin) emin = coor;
382 if (coor < emin) emin = coor;
385 if (coor < emin) emin = coor;
388 if (coor < emin) emin = coor;
391 if (coor < emin) emin = coor;
398 for (
auto ipoint=(*ibase)->cbegin(); ipoint!=(*ibase)->cend(); ++ipoint)
400 G4double coor = ipoint->x()*cx + ipoint->y()*cy + ipoint->z()*cz +
cd;
401 if (coor < emin) emin = coor;
414 if (center.
x()-radius > xmaxlim)
return false;
415 if (center.
y()-radius > ymaxlim)
return false;
416 if (center.
z()-radius > zmaxlim)
return false;
417 if (center.
x()+radius < xminlim)
return false;
418 if (center.
y()+radius < yminlim)
return false;
419 if (center.
z()+radius < zminlim)
return false;
424 std::vector<G4Polygon3D*> bases(nbases);
432 for (
G4int i=0; i<nbases; ++i)
448 for (
auto i=0; i<3; ++i)
463 for (
G4int k=0; k<nbases-1; ++k)
479 if (extent.first.x() > prismAABB.first.x())
480 extent.first.setX( prismAABB.first.x() );
481 if (extent.first.y() > prismAABB.first.y())
482 extent.first.setY( prismAABB.first.y() );
483 if (extent.first.z() > prismAABB.first.z())
484 extent.first.setZ( prismAABB.first.z() );
485 if (extent.second.x() < prismAABB.second.x())
486 extent.second.setX(prismAABB.second.x());
487 if (extent.second.y() < prismAABB.second.y())
488 extent.second.setY(prismAABB.second.y());
489 if (extent.second.z() < prismAABB.second.z())
490 extent.second.setZ(prismAABB.second.z());
503 std::vector<G4Segment3D> vecEdges;
525 if (bits == 0xFFF)
continue;
527 std::vector<G4Plane3D> vecPlanes;
534 for (
G4int i=0; i<nbases; ++i) {
delete bases[i]; bases[i] =
nullptr; }
539 if (pAxis ==
kXAxis) { emin = extent.first.x();
emax = extent.second.x(); }
540 if (pAxis ==
kYAxis) { emin = extent.first.y();
emax = extent.second.y(); }
541 if (pAxis ==
kZAxis) { emin = extent.first.z();
emax = extent.second.z(); }
543 if (emin >
emax)
return false;
561 if (pTransform3D.
xx() == 1. &&
562 pTransform3D.
yy() == 1. &&
563 pTransform3D.
zz() == 1.)
return 1.;
568 G4double sxsx = xx*xx + yx*yx + zx*zx;
572 G4double sysy = xy*xy + yy*yy + zy*zy;
576 G4double szsz = xz*xz + yz*yz + zz*zz;
578 return (ss <= 1.) ? 1. : std::sqrt(ss);
587 std::vector<G4Polygon3D*>& pBases)
const
590 std::vector<const G4ThreeVectorList*> aabb(2);
591 aabb[0] = &baseA; aabb[1] = &baseB;
603 std::vector<const G4ThreeVectorList*>::const_iterator ia, iaend;
604 auto ib = pBases.begin();
608 if (pTransform3D.
xx()==1 && pTransform3D.
yy()==1 && pTransform3D.
zz()==1)
611 for ( ; ia != iaend; ++ia, ++ib)
613 auto ka = (*ia)->cbegin();
614 auto kb = (*ib)->begin();
615 for ( ; ka != (*ia)->cend(); ++ka, ++kb) { (*kb) = (*ka) + offset; }
620 for ( ; ia != iaend; ++ia, ++ib)
622 auto ka = (*ia)->cbegin();
623 auto kb = (*ib)->begin();
624 for ( ; ka != (*ia)->cend(); ++ka, ++kb)
646 for (
auto it1 = pBaseA.cbegin(); it1 != pBaseA.cend(); ++it1)
649 if (x < xmin) xmin = x;
650 if (x > xmax) xmax = x;
652 if (y < ymin) ymin = y;
653 if (y > ymax) ymax = y;
655 if (z < zmin) zmin = z;
656 if (z > zmax) zmax = z;
661 for (
auto it2 = pBaseB.cbegin(); it2 != pBaseB.cend(); ++it2)
664 if (x < xmin) xmin = x;
665 if (x > xmax) xmax = x;
667 if (y < ymin) ymin = y;
668 if (y > ymax) ymax = y;
670 if (z < zmin) zmin = z;
671 if (z > zmax) zmax = z;
677 pAABB.second =
G4Point3D(xmax,ymax,zmax);
687 std::vector<G4Segment3D>& pEdges)
const
689 G4int na = baseA.size();
690 G4int nb = baseB.size();
696 for (
G4int i=0; i<na; ++i)
708 for (
G4int i=0; i<na; ++i)
719 for (
G4int i=0; i<nb; ++i)
735 std::vector<G4Plane3D>& pPlanes)
const
739 G4int na = baseA.size();
740 G4int nb = baseB.size();
741 G4Point3D pa(0.,0.,0.), pb(0.,0.,0.), p0;
743 for (
G4int i=0; i<na; ++i) pa += baseA[i];
744 for (
G4int i=0; i<nb; ++i) pb += baseB[i];
745 pa /= na; pb /= nb; p0 = (pa+pb)/2.;
753 for (
G4int i=0; i<na; ++i)
755 norm = (baseB[k]-baseA[i]).cross(baseA[k]-baseB[i]);
758 pPlanes.push_back(
G4Plane3D(norm,baseA[i]));
762 norm = (baseA[2]-baseA[0]).cross(baseA[1]-pa);
767 norm = (baseB[2]-baseB[0]).cross(baseB[1]-pb);
776 for (
G4int i=0; i<na; ++i)
778 norm = (baseA[i]-baseB[0]).cross(baseA[k]-baseB[0]);
781 pPlanes.push_back(
G4Plane3D(norm,baseB[0]));
785 norm = (baseA[2]-baseA[0]).cross(baseA[1]-pa);
794 for (
G4int i=0; i<nb; ++i)
796 norm = (baseB[i]-baseA[0]).cross(baseB[k]-baseA[0]);
799 pPlanes.push_back(
G4Plane3D(norm,baseA[0]));
803 norm = (baseB[2]-baseB[0]).cross(baseB[1]-pb);
812 G4int nplanes = pPlanes.size();
813 for (
G4int i=0; i<nplanes; ++i)
815 pPlanes[i].normalize();
816 if (pPlanes[i].distance(p0) > 0)
818 pPlanes[i] =
G4Plane3D(-pPlanes[i].a(),-pPlanes[i].b(),
819 -pPlanes[i].c(),-pPlanes[i].d());
839 G4int nedges = pEdges.size();
840 for (
G4int k=0; k<nedges; ++k)
844 if (std::abs(p1.
x()-p2.
x())+
845 std::abs(p1.
y()-p2.
y())+
853 if (
d2 > 0.0) { done =
false;
continue; }
866 if (
d2 > 0.) { done =
false;
continue; }
879 if (
d2 > 0.) { done =
false;
continue; }
892 if (
d2 > 0.) { done =
false;
continue; }
905 if (
d2 > 0.) { done =
false;
continue; }
918 if (
d2 > 0.) { done =
false;
continue; }
938 pExtent.first = emin;
939 pExtent.second =
emax;
951 const std::vector<G4Plane3D>& pPlanes,
970 std::vector<G4Segment3D> edges(12);
971 G4int i = 0, bits = pBits;
974 edges[i ].first.set( xmin,ymin,zmin);
975 edges[i++].second.set(xmax,ymin,zmin);
979 edges[i ].first.set( xmax,ymin,zmin);
980 edges[i++].second.set(xmax,ymax,zmin);
984 edges[i ].first.set( xmax,ymax,zmin);
985 edges[i++].second.set(xmin,ymax,zmin);
989 edges[i ].first.set( xmin,ymax,zmin);
990 edges[i++].second.set(xmin,ymin,zmin);
995 edges[i ].first.set( xmin,ymin,zmax);
996 edges[i++].second.set(xmax,ymin,zmax);
1000 edges[i ].first.set( xmax,ymin,zmax);
1001 edges[i++].second.set(xmax,ymax,zmax);
1003 if (!(bits & 0x040))
1005 edges[i ].first.set( xmax,ymax,zmax);
1006 edges[i++].second.set(xmin,ymax,zmax);
1008 if (!(bits & 0x080))
1010 edges[i ].first.set( xmin,ymax,zmax);
1011 edges[i++].second.set(xmin,ymin,zmax);
1014 if (!(bits & 0x100))
1016 edges[i ].first.set( xmin,ymin,zmin);
1017 edges[i++].second.set(xmin,ymin,zmax);
1019 if (!(bits & 0x200))
1021 edges[i ].first.set( xmax,ymin,zmin);
1022 edges[i++].second.set(xmax,ymin,zmax);
1024 if (!(bits & 0x400))
1026 edges[i ].first.set( xmax,ymax,zmin);
1027 edges[i++].second.set(xmax,ymax,zmax);
1029 if (!(bits & 0x800))
1031 edges[i ].first.set( xmin,ymax,zmin);
1032 edges[i++].second.set(xmin,ymax,zmax);
1038 for (
auto iedge = edges.cbegin(); iedge != edges.cend(); ++iedge)
1043 for (
auto iplane = pPlanes.cbegin(); iplane != pPlanes.cend(); ++iplane)
1050 if (
d2 > 0.0) { exist =
false;
break; }
1055 if (
d2 > 0.0) { p2 = (p1*
d2-p2*
d1)/(
d2-
d1); }
1073 pExtent.first = emin;
1074 pExtent.second =
emax;
const G4double kCarTolerance
std::pair< G4Point3D, G4Point3D > G4Segment3D
std::vector< G4Point3D > G4Polygon3D
std::vector< G4ThreeVector > G4ThreeVectorList
static const G4double emax
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *description)
static const G4double pMax
static const G4double pMin
HepGeom::Plane3D< G4double > G4Plane3D
HepGeom::Point3D< G4double > G4Point3D
void set(double x, double y, double z)
void CheckBoundingPolygons()
G4bool BoundingBoxVsVoxelLimits(const EAxis pAxis, const G4VoxelLimits &pVoxelLimits, const G4Transform3D &pTransform3D, G4double &pMin, G4double &pMax) const
G4bool CalculateExtent(const EAxis pAxis, const G4VoxelLimits &pVoxelLimits, const G4Transform3D &pTransform3D, G4double &pMin, G4double &pMax) const
void ClipVoxelByPlanes(G4int pBits, const G4VoxelLimits &pLimits, const std::vector< G4Plane3D > &pPlanes, const G4Segment3D &pAABB, G4Segment3D &pExtent) const
void TransformVertices(const G4Transform3D &pTransform3D, std::vector< G4Polygon3D * > &pBases) const
void CreateListOfEdges(const G4Polygon3D &baseA, const G4Polygon3D &baseB, std::vector< G4Segment3D > &pEdges) const
G4double FindScaleFactor(const G4Transform3D &pTransform3D) const
void GetPrismAABB(const G4Polygon3D &pBaseA, const G4Polygon3D &pBaseB, G4Segment3D &pAABB) const
G4bool ClipEdgesByVoxel(const std::vector< G4Segment3D > &pEdges, const G4VoxelLimits &pLimits, G4Segment3D &pExtent) const
const std::vector< const G4ThreeVectorList * > * fPolygons
G4BoundingEnvelope(const G4ThreeVector &pMin, const G4ThreeVector &pMax)
void CreateListOfPlanes(const G4Polygon3D &baseA, const G4Polygon3D &baseB, std::vector< G4Plane3D > &pPlanes) const
G4double GetSurfaceTolerance() const
static G4GeometryTolerance * GetInstance()
G4double GetMinExtent(const EAxis pAxis) const
G4double GetMinZExtent() const
void AddLimit(const EAxis pAxis, const G4double pMin, const G4double pMax)
G4double GetMaxExtent(const EAxis pAxis) const
G4double GetMaxYExtent() const
G4double GetMaxZExtent() const
G4double GetMinYExtent() const
G4double GetMinXExtent() const
G4double GetMaxXExtent() const
static const G4double kInfinity
T max(const T t1, const T t2)
brief Return the largest of the two arguments
T min(const T t1, const T t2)
brief Return the smallest of the two arguments