49#define G4MT_phphix ((subInstanceManager.offset[instanceID]).fPhix)
50#define G4MT_phphiy ((subInstanceManager.offset[instanceID]).fPhiy)
51#define G4MT_phphiz ((subInstanceManager.offset[instanceID]).fPhiz)
52#define G4MT_phphik ((subInstanceManager.offset[instanceID]).fPhik)
58 return subInstanceManager;
86 r[0] = tail->
r;
z[0] = tail->
z;
87 r[1] = head->
r;
z[1] = head->
z;
99 phiTotal = (
phiIsOpen) ? thePhiTotal : twopi;
111 numSide = theNumSide>0 ? theNumSide : 1;
115 const std::size_t maxSides =
numSide;
124 b1(
r[1]*std::cos(phi),
r[1]*std::sin(phi),
z[1] ),
125 c1( prevRZ->
r*std::cos(phi), prevRZ->
r*std::sin(phi), prevRZ->
z ),
126 d1( nextRZ->
r*std::cos(phi), nextRZ->
r*std::sin(phi), nextRZ->
z ),
139 c2 =
G4ThreeVector( prevRZ->
r*std::cos(phi), prevRZ->
r*std::sin(phi), prevRZ->
z );
140 d2 =
G4ThreeVector( nextRZ->
r*std::cos(phi), nextRZ->
r*std::sin(phi), nextRZ->
z );
149 vec->center = 0.25*( a1 + a2 + b1 + b2 );
151 tt = b2 + b1 - a2 - a1;
152 vec->surfRZ = tt.
unit();
155 tt = b2 - b1 + a2 - a1;
156 vec->surfPhi = tt.
unit();
164 tt = vec->surfPhi.
cross(vec->surfRZ);
165 vec->normal = tt.
unit();
184 adj = 0.5*(c1+c2-a1-a2);
185 adj = adj.
cross(a12);
186 adj = adj.
unit() + vec->normal;
187 vec->edgeNorm[0] = adj.
unit();
190 adj = 0.5*(d1+d2-b1-b2);
191 adj = adj.
cross(a12);
192 adj = adj.
unit() + vec->normal;
193 vec->edgeNorm[1] = adj.
unit();
200 vec->edges[0] = edge;
201 edge->corner[0] = a1;
202 edge->corner[1] = b1;
204 vec->edges[1] = edge;
210 }
while( ++vec <
vecs+maxSides );
217 edge->corner[0] = a2;
218 edge->corner[1] = b2;
232 edge = vec->edges[0];
238 edge->normal = eNorm.
unit();
247 eNorm = vec->edgeNorm[0] + prev->edgeNorm[0];
248 edge->cornNorm[0] = eNorm.
unit();
250 eNorm = vec->edgeNorm[1] + prev->edgeNorm[1];
251 edge->cornNorm[1] = eNorm.
unit();
252 }
while( prev=vec, ++vec <
vecs + maxSides );
268 - vec->edges[0]->corner[1];
269 normvec = normvec.
cross(vec->normal);
270 if (normvec.
dot(vec->surfPhi) > 0) normvec = -normvec;
272 vec->edges[0]->normal = normvec.
unit();
274 vec->edges[0]->cornNorm[0] = (vec->edges[0]->corner[0]
275 - vec->center).unit();
276 vec->edges[0]->cornNorm[1] = (vec->edges[0]->corner[1]
277 - vec->center).unit();
282 vec =
vecs + maxSides - 1;
284 normvec = vec->edges[1]->corner[0] - vec->edges[1]->corner[1];
285 normvec = normvec.
cross(vec->normal);
286 if (normvec.
dot(vec->surfPhi) < 0) normvec = -normvec;
288 vec->edges[1]->normal = normvec.
unit();
290 vec->edges[1]->cornNorm[0] = (vec->edges[1]->corner[0]
291 - vec->center).unit();
292 vec->edges[1]->cornNorm[1] = (vec->edges[1]->corner[1]
293 - vec->center).unit();
308 : startPhi(0.), deltaPhi(0.), endPhi(0.),
341 if (
this == &source)
return *
this;
375 kCarTolerance = source.kCarTolerance;
376 fSurfaceArea = source.fSurfaceArea;
384 const std::size_t numEdges =
phiIsOpen ? numSides+1 : numSides;
388 *sourceEdge = source.
edges;
392 }
while( ++sourceEdge, ++edge <
edges + numEdges);
400 *sourceVec = source.
vecs;
404 vec->edges[0] =
edges + (sourceVec->edges[0] - source.
edges);
405 vec->edges[1] =
edges + (sourceVec->edges[1] - source.
edges);
406 }
while( ++sourceVec, ++vec <
vecs + numSides );
458 G4double normSign = outgoing ? +1 : -1;
498 if (dotProd <= 0)
continue;
504 distFromSurface = -normSign*delta.
dot(vec->normal);
506 if (distFromSurface < -surfTolerance)
continue;
520 if (normSign*qc.
cross(qd).
dot(v) < 0)
continue;
525 if (normSign*qa.
cross(qb).
dot(v) > 0)
continue;
532 if (
r[0] > 1/kInfinity && normSign*qa.
cross(qc).
dot(v) < 0)
return false;
533 if (
r[1] > 1/kInfinity && normSign*qb.
cross(qd).
dot(v) > 0)
return false;
540 if (distFromSurface < 0)
545 if (std::fabs(rz) >
lenRZ+surfTolerance)
return false;
548 if (std::fabs(pp) >
lenPhi[0]+
lenPhi[1]*rz+surfTolerance)
return false;
555 distance = distFromSurface/dotProd;
556 normal = vec->normal;
559 }
while( ++vec, ++face <
numSide );
571 G4double normSign = outgoing ? -1 : +1;
581 if (normSign*normDist > -0.5*kCarTolerance)
619 if ( (std::fabs(norm) > tolerance) || (*bestDistance > 2.0*tolerance) )
641 return vecs[iPhi].normal;
678 i1 = iPhi; i2 = iPhi;
681 list[0] =
vecs[i1].edges[0]->corner;
682 list[1] =
vecs[i1].edges[0]->corner+1;
683 list[2] =
vecs[i2].edges[1]->corner;
684 list[3] =
vecs[i2].edges[1]->corner+1;
693 G4double answer = (*vec)->dot(axis);
694 if (answer > best) best = answer;
695 }
while( ++vec < list+4 );
722 TransformPoint(vec->edges[0]->corner[0]));
724 TransformPoint(vec->edges[0]->corner[1]));
726 TransformPoint(vec->edges[1]->corner[1]));
728 TransformPoint(vec->edges[1]->corner[0]));
787 if (dotProd <= 0)
return false;
794 distFromSurface = -normSign*delta.
dot(vec.normal);
796 if (distFromSurface < -surfTolerance)
return false;
802 distance = distFromSurface/dotProd;
824 if (
r[0]==0)
return true;
826 if (atRZ < -
lenRZ*1.2)
return false;
830 qb = q - vec.edges[1]->corner[0];
832 if (normSign*qacb.
dot(v) < 0)
return false;
834 if (distFromSurface < 0)
836 if (atRZ < -
lenRZ-surfTolerance)
return false;
841 if (
r[1]==0)
return true;
843 if (atRZ >
lenRZ*1.2)
return false;
847 qb = q - vec.edges[1]->corner[1];
849 if (normSign*qacb.
dot(v) >= 0)
return false;
851 if (distFromSurface < 0)
853 if (atRZ >
lenRZ+surfTolerance)
return false;
881 *i1 =
PhiSegment( std::atan2( p.
y() + s1*v.
y(), p.
x() + s1*v.
x() ) );
884 return (*i1 < 0) ? 0 : 1;
890 *i2 =
PhiSegment( std::atan2( p.
y() + s2*v.
y(), p.
x() + s2*v.
x() ) );
891 if (*i1 == *i2)
return 0;
895 if (*i2 < 0)
return 0;
900 if (*i2 < 0)
return 1;
913 if (iPhi >= 0)
return iPhi;
929 return (d2 < d1) ? 0 :
numSide-1;
1011 *normDist = vec.normal.
dot(pct);
1054 if (pcDotRZ < -
lenRZ)
1061 if (pcDotPhi < -lenPhiZ)
1066 G4double distOutPhi = pcDotPhi+lenPhiZ;
1067 distOut2 = distOutPhi*distOutPhi + distOutZ*distOutZ;
1069 *normDist = pa.
dot(vec.edges[0]->cornNorm[0]);
1071 else if (pcDotPhi > lenPhiZ)
1076 G4double distOutPhi = pcDotPhi-lenPhiZ;
1077 distOut2 = distOutPhi*distOutPhi + distOutZ*distOutZ;
1079 *normDist = pb.
dot(vec.edges[1]->cornNorm[0]);
1087 distOut2 = distOutZ*distOutZ;
1088 *normDist = pa.
dot(vec.edgeNorm[0]);
1091 else if (pcDotRZ >
lenRZ)
1098 if (pcDotPhi < -lenPhiZ)
1103 G4double distOutPhi = pcDotPhi+lenPhiZ;
1104 distOut2 = distOutPhi*distOutPhi + distOutZ*distOutZ;
1106 *normDist = pd.
dot(vec.edges[0]->cornNorm[1]);
1108 else if (pcDotPhi > lenPhiZ)
1113 G4double distOutPhi = pcDotPhi-lenPhiZ;
1114 distOut2 = distOutPhi*distOutPhi + distOutZ*distOutZ;
1116 *normDist = pe.
dot(vec.edges[1]->cornNorm[1]);
1123 distOut2 = distOutZ*distOutZ;
1125 *normDist = pd.
dot(vec.edgeNorm[1]);
1134 if (pcDotPhi < -lenPhiZ)
1140 distOut2 = distOut*distOut;
1142 *normDist = pd.
dot(vec.edges[0]->normal);
1144 else if (pcDotPhi > lenPhiZ)
1150 distOut2 = distOut*distOut;
1152 *normDist = pe.
dot(vec.edges[1]->normal);
1159 return std::fabs(distFaceNorm);
1162 return std::sqrt( distFaceNorm*distFaceNorm + distOut2 );
1180 *p4=p2 + lambda1*w + lambda2*v;
1200 if( (chose>=0.) && (chose < aOne) )
1211 if( fSurfaceArea==0. )
1227 v1=vec->edges[0]->corner[0];
1228 v2=vec->edges[0]->corner[1];
1229 v3=vec->edges[1]->corner[1];
1230 v4=vec->edges[1]->corner[0];
1237 return fSurfaceArea;
1246 std::vector<G4double>areas;
1247 std::vector<G4ThreeVector>points;
1260 v1=vec->edges[0]->corner[0];
1261 v2=vec->edges[0]->corner[1];
1262 v3=vec->edges[1]->corner[1];
1263 v4=vec->edges[1]->corner[0];
1265 points.push_back(point1);
1266 areas.push_back(result1);
1278 if(chose>=Achose1 && chose<Achose2)
1280 point1=points[i] ;
break;
1282 ++i; Achose1=Achose2;
const G4double kCarTolerance
CLHEP::Hep3Vector G4ThreeVector
Hep3Vector cross(const Hep3Vector &) const
double dot(const Hep3Vector &) const
virtual G4bool PartialClip(const G4VoxelLimits &voxelLimit, const EAxis IgnoreMe)
virtual void AddVertexInOrder(const G4ThreeVector vertex)
void SetNormal(const G4ThreeVector &newNormal)
G4int CreateSubInstance()
G4double GetSurfaceTolerance() const
static G4GeometryTolerance * GetInstance()
G4int LineHitsCone(const G4ThreeVector &p, const G4ThreeVector &v, G4double *s1, G4double *s2)
G4PolyhedraSideVec * vecs
G4PolyhedraSideEdge * edges
struct sG4PolyhedraSideVec { G4ThreeVector normal, center, surfPhi, surfRZ; G4PolyhedraSideEdge *edges[2]; G4ThreeVector edgeNorm[2]; } G4PolyhedraSideVec
G4ThreeVector Normal(const G4ThreeVector &p, G4double *bestDistance) override
G4ThreeVector GetPointOnPlane(const G4ThreeVector &p0, const G4ThreeVector &p1, const G4ThreeVector &p2, const G4ThreeVector &p3, G4double *Area)
static const G4PhSideManager & GetSubInstanceManager()
G4PolyhedraSide & operator=(const G4PolyhedraSide &source)
G4double GetPhi(const G4ThreeVector &p)
G4bool IntersectSidePlane(const G4ThreeVector &p, const G4ThreeVector &v, const G4PolyhedraSideVec &vec, G4double normSign, G4double surfTolerance, G4double &distance, G4double &distFromSurface)
G4double SurfaceTriangle(const G4ThreeVector &p1, const G4ThreeVector &p2, const G4ThreeVector &p3, G4ThreeVector *p4)
G4PolyhedraSide(const G4PolyhedraSideRZ *prevRZ, const G4PolyhedraSideRZ *tail, const G4PolyhedraSideRZ *head, const G4PolyhedraSideRZ *nextRZ, G4int numSide, G4double phiStart, G4double phiTotal, G4bool phiIsOpen, G4bool isAllBehind=false)
G4int ClosestPhiSegment(G4double phi)
struct sG4PolyhedraSideEdge { G4ThreeVector normal; G4ThreeVector corner[2]; G4ThreeVector cornNorm[2]; } G4PolyhedraSideEdge
G4int PhiSegment(G4double phi)
G4int LineHitsSegments(const G4ThreeVector &p, const G4ThreeVector &v, G4int *i1, G4int *i2)
G4bool Intersect(const G4ThreeVector &p, const G4ThreeVector &v, G4bool outgoing, G4double surfTolerance, G4double &distance, G4double &distFromSurface, G4ThreeVector &normal, G4bool &allBehind) override
G4double SurfaceArea() override
EInside Inside(const G4ThreeVector &p, G4double tolerance, G4double *bestDistance) override
G4double Extent(const G4ThreeVector axis) override
G4double Distance(const G4ThreeVector &p, G4bool outgoing) override
G4double DistanceAway(const G4ThreeVector &p, const G4PolyhedraSideVec &vec, G4double *normDist)
void CalculateExtent(const EAxis axis, const G4VoxelLimits &voxelLimit, const G4AffineTransform &tranform, G4SolidExtentList &extentList) override
G4double DistanceToOneSide(const G4ThreeVector &p, const G4PolyhedraSideVec &vec, G4double *normDist)
~G4PolyhedraSide() override
G4IntersectingCone * cone
void CopyStuff(const G4PolyhedraSide &source)
G4ThreeVector GetPointOnFace() override
void AddSurface(const G4ClippablePolygon &surface)