59 #if !defined(G4GEOM_USE_USPHERE)
74 using namespace CLHEP;
93 :
G4CSGSolid(pName), fEpsilon(2.e-11), fSPhi(0.0),
94 fFullPhiSphere(true), fFullThetaSphere(true)
104 if ( (pRmin >= pRmax) || (pRmax < 1.1*
kRadTolerance) || (pRmin < 0) )
106 std::ostringstream message;
107 message <<
"Invalid radii for Solid: " <<
GetName() <<
G4endl
108 <<
" pRmin = " << pRmin <<
", pRmax = " << pRmax;
109 G4Exception(
"G4Sphere::G4Sphere()",
"GeomSolids0002",
128 :
G4CSGSolid(a), fRminTolerance(0.), fRmaxTolerance(0.),
129 kAngTolerance(0.), kRadTolerance(0.), fEpsilon(0.),
130 fRmin(0.), fRmax(0.), fSPhi(0.), fDPhi(0.), fSTheta(0.),
131 fDTheta(0.), sinCPhi(0.), cosCPhi(0.), cosHDPhiOT(0.), cosHDPhiIT(0.),
132 sinSPhi(0.), cosSPhi(0.), sinEPhi(0.), cosEPhi(0.), hDPhi(0.), cPhi(0.),
133 ePhi(0.), sinSTheta(0.), cosSTheta(0.), sinETheta(0.), cosETheta(0.),
134 tanSTheta(0.), tanSTheta2(0.), tanETheta(0.), tanETheta2(0.), eTheta(0.),
135 fFullPhiSphere(false), fFullThetaSphere(false), fFullSphere(true),
136 halfCarTolerance(0.), halfAngTolerance(0.)
153 :
G4CSGSolid(rhs), fRminTolerance(rhs.fRminTolerance),
154 fRmaxTolerance(rhs.fRmaxTolerance), kAngTolerance(rhs.kAngTolerance),
155 kRadTolerance(rhs.kRadTolerance), fEpsilon(rhs.fEpsilon),
156 fRmin(rhs.fRmin), fRmax(rhs.fRmax), fSPhi(rhs.fSPhi), fDPhi(rhs.fDPhi),
157 fSTheta(rhs.fSTheta), fDTheta(rhs.fDTheta),
158 sinCPhi(rhs.sinCPhi), cosCPhi(rhs.cosCPhi),
159 cosHDPhiOT(rhs.cosHDPhiOT), cosHDPhiIT(rhs.cosHDPhiIT),
160 sinSPhi(rhs.sinSPhi), cosSPhi(rhs.cosSPhi),
161 sinEPhi(rhs.sinEPhi), cosEPhi(rhs.cosEPhi),
162 hDPhi(rhs.hDPhi), cPhi(rhs.cPhi), ePhi(rhs.ePhi),
163 sinSTheta(rhs.sinSTheta), cosSTheta(rhs.cosSTheta),
164 sinETheta(rhs.sinETheta), cosETheta(rhs.cosETheta),
165 tanSTheta(rhs.tanSTheta), tanSTheta2(rhs.tanSTheta2),
166 tanETheta(rhs.tanETheta), tanETheta2(rhs.tanETheta2), eTheta(rhs.eTheta),
167 fFullPhiSphere(rhs.fFullPhiSphere), fFullThetaSphere(rhs.fFullThetaSphere),
168 fFullSphere(rhs.fFullSphere),
169 halfCarTolerance(rhs.halfCarTolerance),
170 halfAngTolerance(rhs.halfAngTolerance)
182 if (
this == &rhs) {
return *
this; }
244 G4double diff1,diff2,delta,maxDiff,newMin,newMax;
323 if ((yoff1>=0) && (yoff2>=0))
335 delta=fRmax*fRmax-yoff1*yoff1;
336 diff1=(delta>0.) ? std::sqrt(delta) : 0.;
337 delta=fRmax*fRmax-yoff2*yoff2;
338 diff2=(delta>0.) ? std::sqrt(delta) : 0.;
339 maxDiff=(diff1>diff2) ? diff1:diff2;
340 newMin=xoffset-maxDiff;
341 newMax=xoffset+maxDiff;
342 pMin=(newMin<xMin) ? xMin : newMin;
343 pMax=(newMax>xMax) ? xMax : newMax;
349 if ((xoff1>=0) && (xoff2>=0))
361 delta=fRmax*fRmax-xoff1*xoff1;
362 diff1=(delta>0.) ? std::sqrt(delta) : 0.;
363 delta=fRmax*fRmax-xoff2*xoff2;
364 diff2=(delta>0.) ? std::sqrt(delta) : 0.;
365 maxDiff=(diff1>diff2) ? diff1:diff2;
366 newMin=yoffset-maxDiff;
367 newMax=yoffset+maxDiff;
368 pMin=(newMin<yMin) ? yMin : newMin;
369 pMax=(newMax>yMax) ? yMax : newMax;
386 G4int i,j,noEntries,noBetweenSections;
387 G4bool existsAfterClip=
false;
392 G4int noPolygonVertices ;
398 noEntries=vertices->size();
399 noBetweenSections=noEntries-noPolygonVertices;
402 for (i=0;i<noEntries;i+=noPolygonVertices)
404 for(j=0;j<(noPolygonVertices/2)-1;j++)
406 ThetaPolygon.push_back((*vertices)[i+j]) ;
407 ThetaPolygon.push_back((*vertices)[i+j+1]) ;
408 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices-2-j]) ;
409 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices-1-j]) ;
411 ThetaPolygon.clear() ;
414 for (i=0;i<noBetweenSections;i+=noPolygonVertices)
416 for(j=0;j<noPolygonVertices-1;j++)
418 ThetaPolygon.push_back((*vertices)[i+j]) ;
419 ThetaPolygon.push_back((*vertices)[i+j+1]) ;
420 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices+j+1]) ;
421 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices+j]) ;
423 ThetaPolygon.clear() ;
425 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices-1]) ;
426 ThetaPolygon.push_back((*vertices)[i]) ;
427 ThetaPolygon.push_back((*vertices)[i+noPolygonVertices]) ;
428 ThetaPolygon.push_back((*vertices)[i+2*noPolygonVertices-1]) ;
430 ThetaPolygon.clear() ;
435 existsAfterClip=
true;
456 existsAfterClip=
true;
462 return existsAfterClip;
474 G4double rho,rho2,rad2,tolRMin,tolRMax;
483 rho2 = p.x()*p.x() + p.y()*p.y() ;
484 rad2 = rho2 + p.z()*p.z() ;
489 tolRMax = Rmax_minus;
491 if ( (rad2 <= Rmax_minus*Rmax_minus) && (rad2 >= Rmin_plus*Rmin_plus) )
497 tolRMax =
fRmax + halfRmaxTolerance;
499 if ( (rad2 <= tolRMax*tolRMax) && (rad2 >= tolRMin*tolRMin) )
513 pPhi = std::atan2(p.y(),p.x()) ;
532 rho = std::sqrt(rho2);
533 pTheta = std::atan2(rho,p.z());
571 G4int noSurfaces = 0;
572 G4double rho, rho2, radius, pTheta, pPhi=0.;
579 rho2 = p.x()*p.x()+p.y()*p.y();
580 radius = std::sqrt(rho2+p.z()*p.z());
581 rho = std::sqrt(rho2);
584 if (
fRmin) distRMin = std::fabs(radius-
fRmin);
588 pPhi = std::atan2(p.y(),p.x());
597 distSPhi = std::fabs( pPhi-
fSPhi );
598 distEPhi = std::fabs( pPhi-
ePhi );
612 pTheta = std::atan2(rho,p.z());
613 distSTheta = std::fabs(pTheta-
fSTheta);
614 distETheta = std::fabs(pTheta-
eTheta);
638 if( radius ) { nR =
G4ThreeVector(p.x()/radius,p.y()/radius,p.z()/radius); }
669 else { sumnorm += nTs; }
675 else { sumnorm += nTe; }
676 if(sumnorm.z() == 0.) { sumnorm += nZ; }
679 if ( noSurfaces == 0 )
682 G4Exception(
"G4Sphere::SurfaceNormal(p)",
"GeomSolids1002",
687 else if ( noSurfaces == 1 ) { norm = sumnorm; }
688 else { norm = sumnorm.unit(); }
702 G4double rho,rho2,radius,pPhi,pTheta;
703 G4double distRMin,distRMax,distSPhi,distEPhi,
704 distSTheta,distETheta,distMin;
706 rho2=p.x()*p.x()+p.y()*p.y();
707 radius=std::sqrt(rho2+p.z()*p.z());
714 distRMax=std::fabs(radius-
fRmax);
717 distRMin=std::fabs(radius-
fRmin);
719 if (distRMin<distRMax)
741 pPhi = std::atan2(p.y(),p.x());
742 if (pPhi<0) { pPhi += twopi; }
748 distSPhi=std::fabs(pPhi-(
fSPhi+twopi))*rho;
752 distSPhi=std::fabs(pPhi-
fSPhi)*rho;
759 if (distSPhi<distEPhi)
761 if (distSPhi<distMin)
769 if (distEPhi<distMin)
783 pTheta=std::atan2(rho,p.z());
784 distSTheta=std::fabs(pTheta-
fSTheta)*radius;
789 if (distSTheta<distETheta)
791 if (distSTheta<distMin)
793 distMin = distSTheta ;
799 if (distETheta<distMin)
801 distMin = distETheta ;
810 norm=
G4ThreeVector(-p.x()/radius,-p.y()/radius,-p.z()/radius);
835 "Undefined side for valid surface normal to solid.");
875 G4double rho2, rad2, pDotV2d, pDotV3d, pTheta ;
876 G4double tolSTheta=0., tolETheta=0. ;
882 ? (
fRmin-halfRminTolerance)*(
fRmin-halfRminTolerance) : 0;
884 (
fRmin+halfRminTolerance)*(
fRmin+halfRminTolerance);
886 (
fRmax+halfRmaxTolerance)*(
fRmax+halfRmaxTolerance);
888 (
fRmax-halfRmaxTolerance)*(
fRmax-halfRmaxTolerance);
892 G4double xi, yi, zi, rhoi, rhoi2, radi2, iTheta ;
909 rho2 = p.x()*p.x() + p.y()*p.y() ;
910 rad2 = rho2 + p.z()*p.z() ;
911 pTheta = std::atan2(std::sqrt(rho2),p.z()) ;
913 pDotV2d = p.x()*v.x() + p.y()*v.y() ;
914 pDotV3d = pDotV2d + p.z()*v.z() ;
945 d2 = pDotV3d*pDotV3d - c ;
949 sd = -pDotV3d - std::sqrt(d2) ;
955 G4double fTerm = sd-std::fmod(sd,dRmax);
958 xi = p.x() + sd*v.x() ;
959 yi = p.y() + sd*v.y() ;
960 rhoi = std::sqrt(xi*xi + yi*yi) ;
970 zi = p.z() + sd*v.z() ;
975 iTheta = std::atan2(rhoi,zi) ;
976 if ( (iTheta >= tolSTheta) && (iTheta <= tolETheta) )
991 zi = p.z() + sd*v.z() ;
996 iTheta = std::atan2(rhoi,zi) ;
997 if ( (iTheta >= tolSTheta) && (iTheta <= tolETheta) )
1019 d2 = pDotV3d*pDotV3d - c ;
1021 if ( (rad2 > tolIRMax2)
1075 d2 = pDotV3d*pDotV3d - c ;
1080 if ( (c > -halfRminTolerance) && (rad2 < tolIRMin2)
1127 sd = -pDotV3d + std::sqrt(d2) ;
1128 if ( sd >= halfRminTolerance )
1130 xi = p.x() + sd*v.x() ;
1131 yi = p.y() + sd*v.y() ;
1132 rhoi = std::sqrt(xi*xi+yi*yi) ;
1142 zi = p.z() + sd*v.z() ;
1147 iTheta = std::atan2(rhoi,zi) ;
1148 if ( (iTheta >= tolSTheta) && (iTheta<=tolETheta) )
1163 zi = p.z() + sd*v.z() ;
1168 iTheta = std::atan2(rhoi,zi) ;
1169 if ( (iTheta >= tolSTheta) && (iTheta <= tolETheta) )
1212 xi = p.x() + sd*v.x() ;
1213 yi = p.y() + sd*v.y() ;
1214 zi = p.z() + sd*v.z() ;
1215 rhoi2 = xi*xi + yi*yi ;
1216 radi2 = rhoi2 + zi*zi ;
1227 if ( (radi2 <= tolORMax2)
1228 && (radi2 >= tolORMin2)
1237 iTheta = std::atan2(std::sqrt(rhoi2),zi) ;
1238 if ( (iTheta >= tolSTheta) && (iTheta <= tolETheta) )
1243 if ((yi*
cosCPhi-xi*sinCPhi) <= 0)
1274 xi = p.x() + sd*v.x() ;
1275 yi = p.y() + sd*v.y() ;
1276 zi = p.z() + sd*v.z() ;
1277 rhoi2 = xi*xi + yi*yi ;
1278 radi2 = rhoi2 + zi*zi ;
1289 if ( (radi2 <= tolORMax2)
1290 && (radi2 >= tolORMin2)
1299 iTheta = std::atan2(std::sqrt(rhoi2),zi) ;
1300 if ( (iTheta >= tolSTheta) && (iTheta <= tolETheta) )
1305 if ((yi*
cosCPhi-xi*sinCPhi) >= 0)
1347 dist2STheta = rho2 - p.z()*p.z()*
tanSTheta2 ;
1361 if ( pTheta < tolSTheta )
1371 c = dist2STheta/t1 ;
1378 zi = p.z() + sd*v.z();
1380 if ( (sd < 0) || (zi*(
fSTheta - halfpi) > 0) )
1384 if ((sd >= 0) && (sd < snxt))
1386 xi = p.x() + sd*v.x();
1387 yi = p.y() + sd*v.y();
1388 zi = p.z() + sd*v.z();
1389 rhoi2 = xi*xi + yi*yi;
1390 radi2 = rhoi2 + zi*zi;
1391 if ( (radi2 <= tolORMax2)
1392 && (radi2 >= tolORMin2)
1393 && (zi*(
fSTheta - halfpi) <= 0) )
1422 c = dist2ETheta/t1 ;
1430 if ( (sd >= 0) && (sd < snxt) )
1432 xi = p.x() + sd*v.x() ;
1433 yi = p.y() + sd*v.y() ;
1434 zi = p.z() + sd*v.z() ;
1435 rhoi2 = xi*xi + yi*yi ;
1436 radi2 = rhoi2 + zi*zi ;
1438 if ( (radi2 <= tolORMax2)
1439 && (radi2 >= tolORMin2)
1440 && (zi*(
eTheta - halfpi) <= 0) )
1460 else if ( pTheta > tolETheta )
1471 c = dist2ETheta/t1 ;
1478 zi = p.z() + sd*v.z();
1480 if ( (sd < 0) || (zi*(
eTheta - halfpi) > 0) )
1484 if ( (sd >= 0) && (sd < snxt) )
1486 xi = p.x() + sd*v.x() ;
1487 yi = p.y() + sd*v.y() ;
1488 zi = p.z() + sd*v.z() ;
1489 rhoi2 = xi*xi + yi*yi ;
1490 radi2 = rhoi2 + zi*zi ;
1492 if ( (radi2 <= tolORMax2)
1493 && (radi2 >= tolORMin2)
1494 && (zi*(
eTheta - halfpi) <= 0) )
1523 c = dist2STheta/t1 ;
1531 if ( (sd >= 0) && (sd < snxt) )
1533 xi = p.x() + sd*v.x() ;
1534 yi = p.y() + sd*v.y() ;
1535 zi = p.z() + sd*v.z() ;
1536 rhoi2 = xi*xi + yi*yi ;
1537 radi2 = rhoi2 + zi*zi ;
1539 if ( (radi2 <= tolORMax2)
1540 && (radi2 >= tolORMin2)
1541 && (zi*(
fSTheta - halfpi) <= 0) )
1569 if ( (t2>=0 && tolIRMin2<rad2 && rad2<tolIRMax2 &&
fSTheta<halfpi)
1570 || (t2<0 && tolIRMin2<rad2 && rad2<tolIRMax2 && fSTheta>halfpi)
1571 || (v.z()<0 && tolIRMin2<rad2 && rad2<tolIRMax2 &&
fSTheta==halfpi) )
1593 c = dist2STheta/t1 ;
1602 xi = p.x() + sd*v.x() ;
1603 yi = p.y() + sd*v.y() ;
1604 zi = p.z() + sd*v.z() ;
1605 rhoi2 = xi*xi + yi*yi ;
1606 radi2 = rhoi2 + zi*zi ;
1608 if ( (radi2 <= tolORMax2)
1609 && (radi2 >= tolORMin2)
1610 && (zi*(fSTheta - halfpi) <= 0) )
1638 if ( ((t2<0) && (
eTheta < halfpi)
1639 && (tolIRMin2 < rad2) && (rad2 < tolIRMax2))
1640 || ((t2>=0) && (
eTheta > halfpi)
1641 && (tolIRMin2 < rad2) && (rad2 < tolIRMax2))
1642 || ((v.z()>0) && (
eTheta == halfpi)
1643 && (tolIRMin2 < rad2) && (rad2 < tolIRMax2)) )
1665 c = dist2ETheta/t1 ;
1674 && (sd < snxt) && (
eTheta > halfpi) )
1676 xi = p.x() + sd*v.x() ;
1677 yi = p.y() + sd*v.y() ;
1678 zi = p.z() + sd*v.z() ;
1679 rhoi2 = xi*xi + yi*yi ;
1680 radi2 = rhoi2 + zi*zi ;
1682 if ( (radi2 <= tolORMax2)
1683 && (radi2 >= tolORMin2)
1684 && (zi*(
eTheta - halfpi) <= 0) )
1713 c = dist2STheta/t1 ;
1721 if ((sd >= 0) && (sd < snxt))
1723 xi = p.x() + sd*v.x() ;
1724 yi = p.y() + sd*v.y() ;
1725 zi = p.z() + sd*v.z() ;
1726 rhoi2 = xi*xi + yi*yi ;
1727 radi2 = rhoi2 + zi*zi ;
1729 if ( (radi2 <= tolORMax2)
1730 && (radi2 >= tolORMin2)
1731 && (zi*(
fSTheta - halfpi) <= 0) )
1754 c = dist2ETheta/t1 ;
1762 if ((sd >= 0) && (sd < snxt))
1764 xi = p.x() + sd*v.x() ;
1765 yi = p.y() + sd*v.y() ;
1766 zi = p.z() + sd*v.z() ;
1767 rhoi2 = xi*xi + yi*yi ;
1768 radi2 = rhoi2 + zi*zi ;
1770 if ( (radi2 <= tolORMax2)
1771 && (radi2 >= tolORMin2)
1772 && (zi*(
eTheta - halfpi) <= 0) )
1805 G4double safe=0.0,safeRMin,safeRMax,safePhi,safeTheta;
1809 rho2=p.x()*p.x()+p.y()*p.y();
1810 rds=std::sqrt(rho2+p.z()*p.z());
1811 rho=std::sqrt(rho2);
1820 if (safeRMin>safeRMax)
1842 if (cosPsi<std::cos(
hDPhi))
1854 if (safePhi>safe) { safe=safePhi; }
1862 pTheta=std::acos(p.z()/rds);
1863 if (pTheta<0) { pTheta+=
pi; }
1866 if (dTheta1>dTheta2)
1870 safeTheta=rds*std::sin(dTheta1);
1871 if (safe<=safeTheta)
1881 safeTheta=rds*std::sin(dTheta2);
1882 if (safe<=safeTheta)
1890 if (safe<0) { safe=0; }
1918 G4double pDistS,compS,pDistE,compE,sphi2,vphi;
1920 G4double rho2,rad2,pDotV2d,pDotV3d;
1927 G4double dist2STheta, dist2ETheta, distTheta;
1932 rho2 = p.x()*p.x()+p.y()*p.y();
1933 rad2 = rho2+p.z()*p.z();
1935 pDotV2d = p.x()*v.x()+p.y()*v.y();
1936 pDotV3d = pDotV2d+p.z()*v.z();
1954 if( (rad2 <= Rmax_plus*Rmax_plus) && (rad2 >= Rmin_minus*Rmin_minus) )
1969 d2 = pDotV3d*pDotV3d - c;
1972 && ((pDotV3d >=0) || (d2 < 0)) )
1984 snxt = -pDotV3d+std::sqrt(d2);
1996 d2 = pDotV3d*pDotV3d - c;
2003 if(calcNorm) { *validNorm =
false; }
2010 sd = -pDotV3d-std::sqrt(d2);
2055 if ( std::fabs( p.z() ) <= halfRmaxTolerance )
2064 stheta = -p.z()/v.z();
2074 distTheta = std::sqrt(rho2)-p.z()*
tanSTheta;
2080 if(std::fabs(distTheta) < halfRmaxTolerance)
2082 if( (
fSTheta < halfpi) && (p.z() > 0.) )
2084 if( calcNorm ) { *validNorm =
false; }
2087 else if( (
fSTheta > halfpi) && (p.z() <= 0) )
2094 rhoSecTheta = std::sqrt(rho2*(1+
tanSTheta2));
2105 stheta = -0.5*dist2STheta/t2;
2111 if( std::fabs(distTheta) < halfRmaxTolerance )
2113 if( (
fSTheta > halfpi) && (t2 >= 0.) )
2120 rhoSecTheta = std::sqrt(rho2*(1+
tanSTheta2));
2130 else if( (
fSTheta < halfpi) && (t2 < 0.) && (p.z() >=0.) )
2132 if( calcNorm ) { *validNorm =
false; }
2148 if ( ((std::fabs(
s) < halfRmaxTolerance) && (t2 < 0.))
2149 || (sd < 0.) || ( (sd > 0.) && (p.z() + sd*v.z() > 0.) ) )
2153 if( (sd > halfRmaxTolerance) && (p.z() + sd*v.z() <= 0.) )
2163 if ( ( (std::fabs(sd) < halfRmaxTolerance) && (t2 >= 0.) )
2164 || (sd < 0.) || ( (sd > 0.) && (p.z() + sd*v.z() < 0.) ) )
2168 if( (sd > halfRmaxTolerance) && (p.z() + sd*v.z() >= 0.) )
2184 if ( std::fabs( p.z() ) <= halfRmaxTolerance )
2208 distTheta = std::sqrt(rho2)-p.z()*
tanETheta;
2214 if(std::fabs(distTheta) < halfRmaxTolerance)
2216 if( (
eTheta > halfpi) && (p.z() < 0.) )
2218 if( calcNorm ) { *validNorm =
false; }
2221 else if ( (
eTheta < halfpi) && (p.z() >= 0) )
2228 rhoSecTheta = std::sqrt(rho2*(1+
tanETheta2));
2238 sd = -0.5*dist2ETheta/t2;
2249 if ( std::fabs(distTheta) < halfRmaxTolerance )
2251 if( (
eTheta < halfpi) && (t2 >= 0.) )
2258 rhoSecTheta = std::sqrt(rho2*(1+
tanETheta2));
2267 else if ( (
eTheta > halfpi)
2268 && (t2 < 0.) && (p.z() <=0.) )
2270 if( calcNorm ) { *validNorm =
false; }
2286 if( ((std::fabs(sd) < halfRmaxTolerance) && (t2 < 0.))
2291 if( sd > halfRmaxTolerance )
2304 if ( ((std::fabs(sd) < halfRmaxTolerance) && (t2 >= 0.))
2305 || (sd < 0.) || ( (sd > 0.) && (p.z() + sd*v.z() > 0.) ) )
2309 if( (sd > halfRmaxTolerance) && (p.z() + sd*v.z() <= 0.) )
2329 if ( p.x() || p.y() )
2342 if ( (pDistS <= 0) && (pDistE <= 0) )
2348 sphi = pDistS/compS ;
2349 xi = p.x()+sphi*v.x() ;
2350 yi = p.y()+sphi*v.y() ;
2356 vphi = std::atan2(v.y(),v.x());
2378 sphi2=pDistE/compE ;
2381 xi = p.x()+sphi2*v.x() ;
2382 yi = p.y()+sphi2*v.y() ;
2390 vphi = std::atan2(v.y(),v.x()) ;
2397 else { sphi = 0.0; }
2415 else if ((pDistS >= 0) && (pDistE >= 0))
2417 if ( pDistS <= pDistE )
2427 if ( (compS < 0) && (compE < 0) ) { sphi = 0; }
2435 if ( (compS >= 0) && (compE >= 0) ) { sphi =
kInfinity; }
2439 else if ( (pDistS > 0) && (pDistE < 0) )
2447 sphi = pDistE/compE ;
2448 xi = p.x() + sphi*v.x() ;
2449 yi = p.y() + sphi*v.y() ;
2456 vphi = std::atan2(v.y(),v.x());
2485 sphi = pDistE/compE ;
2486 xi = p.x() + sphi*v.x() ;
2487 yi = p.y() + sphi*v.y() ;
2494 vphi = std::atan2(v.y(),v.x());
2530 xi=p.x()+sphi*v.x();
2531 yi=p.y()+sphi*v.y();
2538 vphi = std::atan2(v.y(),v.x()) ;
2567 sphi = pDistS/compS ;
2568 xi = p.x()+sphi*v.x() ;
2569 yi = p.y()+sphi*v.y() ;
2576 vphi = std::atan2(v.y(),v.x()) ;
2611 if ( v.x() || v.y() )
2613 vphi = std::atan2(v.y(),v.x()) ;
2646 xi=p.x()+snxt*v.x();
2647 yi=p.y()+snxt*v.y();
2648 zi=p.z()+snxt*v.z();
2663 else { *validNorm=
false; }
2672 else { *validNorm=
false; }
2683 xi = p.x() + snxt*v.x();
2684 yi = p.y() + snxt*v.y();
2688 rhoSecTheta = std::sqrt(rho2*(1+
tanSTheta2));
2698 else { *validNorm=
false; }
2707 else if (
eTheta < halfpi )
2709 xi=p.x()+snxt*v.x();
2710 yi=p.y()+snxt*v.y();
2714 rhoSecTheta = std::sqrt(rho2*(1+
tanETheta2));
2724 else { *validNorm=
false; }
2730 std::ostringstream message;
2731 G4int oldprc = message.precision(16);
2732 message <<
"Undefined side for valid surface normal to solid."
2734 <<
"Position:" << G4endl << G4endl
2735 <<
"p.x() = " << p.x()/
mm <<
" mm" << G4endl
2736 <<
"p.y() = " << p.y()/
mm <<
" mm" << G4endl
2737 <<
"p.z() = " << p.z()/
mm <<
" mm" << G4endl << G4endl
2738 <<
"Direction:" << G4endl << G4endl
2739 <<
"v.x() = " << v.x() << G4endl
2740 <<
"v.y() = " << v.y() << G4endl
2741 <<
"v.z() = " << v.z() << G4endl << G4endl
2742 <<
"Proposed distance :" << G4endl << G4endl
2743 <<
"snxt = " << snxt/
mm <<
" mm" <<
G4endl;
2744 message.precision(oldprc);
2754 std::ostringstream message;
2755 G4int oldprc = message.precision(16);
2756 message <<
"Logic error: snxt = kInfinity ???" << G4endl
2757 <<
"Position:" << G4endl << G4endl
2758 <<
"p.x() = " << p.x()/
mm <<
" mm" << G4endl
2759 <<
"p.y() = " << p.y()/
mm <<
" mm" << G4endl
2760 <<
"p.z() = " << p.z()/
mm <<
" mm" << G4endl << G4endl
2761 <<
"Rp = "<< std::sqrt( p.x()*p.x()+p.y()*p.y()+p.z()*p.z() )/
mm
2762 <<
" mm" << G4endl << G4endl
2763 <<
"Direction:" << G4endl << G4endl
2764 <<
"v.x() = " << v.x() << G4endl
2765 <<
"v.y() = " << v.y() << G4endl
2766 <<
"v.z() = " << v.z() << G4endl << G4endl
2767 <<
"Proposed distance :" << G4endl << G4endl
2768 <<
"snxt = " << snxt/
mm <<
" mm" <<
G4endl;
2769 message.precision(oldprc);
2783 G4double safe=0.0,safeRMin,safeRMax,safePhi,safeTheta;
2786 rho2=p.x()*p.x()+p.y()*p.y();
2787 rds=std::sqrt(rho2+p.z()*p.z());
2788 rho=std::sqrt(rho2);
2800 G4cout.precision(old_prc) ;
2802 "GeomSolids1002",
JustWarning,
"Point p is outside !?" );
2813 if (safeRMin<safeRMax)
2840 if (safePhi<safe) { safe=safePhi; }
2848 pTheta=std::acos(p.z()/rds);
2849 if (pTheta<0) { pTheta+=
pi; }
2852 if (dTheta1<dTheta2) { safeTheta=rds*std::sin(dTheta1); }
2853 else { safeTheta=rds*std::sin(dTheta2); }
2854 if (safe>safeTheta) { safe=safeTheta; }
2857 if (safe<0) { safe=0; }
2874 G4int& noPolygonVertices )
const
2878 G4double meshAnglePhi,meshRMax,crossAnglePhi,
2879 coscrossAnglePhi,sincrossAnglePhi,sAnglePhi;
2880 G4double meshTheta,crossTheta,startTheta;
2881 G4double rMaxX,rMaxY,rMinX,rMinY,rMinZ,rMaxZ;
2882 G4int crossSectionPhi,noPhiCrossSections,crossSectionTheta,noThetaSections;
2896 meshAnglePhi=
fDPhi/(noPhiCrossSections-1);
2903 sAnglePhi = -meshAnglePhi*0.5;
2922 meshTheta=
fDTheta/(noThetaSections-1);
2929 startTheta = -meshTheta*0.5;
2936 meshRMax = (meshAnglePhi >= meshTheta) ?
2937 fRmax/std::cos(meshAnglePhi*0.5) :
fRmax/std::cos(meshTheta*0.5);
2941 if (vertices && cosCrossTheta && sinCrossTheta)
2943 vertices->reserve(noPhiCrossSections*(noThetaSections*2));
2944 for (crossSectionPhi=0;
2945 crossSectionPhi<noPhiCrossSections; crossSectionPhi++)
2947 crossAnglePhi=sAnglePhi+crossSectionPhi*meshAnglePhi;
2948 coscrossAnglePhi=std::cos(crossAnglePhi);
2949 sincrossAnglePhi=std::sin(crossAnglePhi);
2950 for (crossSectionTheta=0;
2951 crossSectionTheta<noThetaSections;crossSectionTheta++)
2955 crossTheta=startTheta+crossSectionTheta*meshTheta;
2956 cosCrossTheta[crossSectionTheta]=std::cos(crossTheta);
2957 sinCrossTheta[crossSectionTheta]=std::sin(crossTheta);
2959 rMinX=
fRmin*sinCrossTheta[crossSectionTheta]*coscrossAnglePhi;
2960 rMinY=
fRmin*sinCrossTheta[crossSectionTheta]*sincrossAnglePhi;
2961 rMinZ=
fRmin*cosCrossTheta[crossSectionTheta];
2968 for (crossSectionTheta=noThetaSections-1;
2969 crossSectionTheta>=0; crossSectionTheta--)
2971 rMaxX=meshRMax*sinCrossTheta[crossSectionTheta]*coscrossAnglePhi;
2972 rMaxY=meshRMax*sinCrossTheta[crossSectionTheta]*sincrossAnglePhi;
2973 rMaxZ=meshRMax*cosCrossTheta[crossSectionTheta];
2980 noPolygonVertices = noThetaSections*2 ;
2987 "Error in allocation of vertices. Out of memory !");
2990 delete [] cosCrossTheta;
2991 delete [] sinCrossTheta;
3020 G4int oldprc = os.precision(16);
3021 os <<
"-----------------------------------------------------------\n"
3022 <<
" *** Dump for solid - " <<
GetName() <<
" ***\n"
3023 <<
" ===================================================\n"
3024 <<
" Solid type: G4Sphere\n"
3025 <<
" Parameters: \n"
3026 <<
" inner radius: " <<
fRmin/
mm <<
" mm \n"
3027 <<
" outer radius: " <<
fRmax/
mm <<
" mm \n"
3028 <<
" starting phi of segment : " <<
fSPhi/
degree <<
" degrees \n"
3029 <<
" delta phi of segment : " <<
fDPhi/
degree <<
" degrees \n"
3030 <<
" starting theta of segment: " <<
fSTheta/
degree <<
" degrees \n"
3031 <<
" delta theta of segment : " <<
fDTheta/
degree <<
" degrees \n"
3032 <<
"-----------------------------------------------------------\n";
3033 os.precision(oldprc);
3044 G4double zRand, aOne, aTwo, aThr, aFou, aFiv, chose, phi, sinphi, cosphi;
3045 G4double height1, height2, slant1, slant2, costheta, sintheta, rRand;
3060 cosphi = std::cos(phi);
3061 sinphi = std::sin(phi);
3063 sintheta = std::sqrt(1.-
sqr(costheta));
3072 if( (chose>=0.) && (chose<aOne) )
3077 else if( (chose>=aOne) && (chose<aOne+aTwo) )
3082 else if( (chose>=aOne+aTwo) && (chose<aOne+aTwo+aThr) )
3095 else if( (chose>=aOne+aTwo+aThr) && (chose<aOne+aTwo+aThr+aFou) )
3108 else if( (chose>=aOne+aTwo+aThr+aFou) && (chose<aOne+aTwo+aThr+aFou+aFiv) )
3111 rRand*sintheta*
sinSPhi,rRand*costheta);
3116 rRand*sintheta*
sinEPhi,rRand*costheta);
ThreeVector shoot(const G4int Ap, const G4int Af)
G4double halfCarTolerance
G4double DistanceToIn(const G4ThreeVector &p, const G4ThreeVector &v) const
static const G4double kInfinity
G4double GetMinYExtent() const
CLHEP::Hep3Vector G4ThreeVector
G4bool IsYLimited() const
G4double GetRadiusInRing(G4double rmin, G4double rmax) const
G4Polyhedron * CreatePolyhedron() const
G4bool IsXLimited() const
const G4int kMinMeshSections
virtual void AddSolid(const G4Box &)=0
G4Sphere(const G4String &pName, G4double pRmin, G4double pRmax, G4double pSPhi, G4double pDPhi, G4double pSTheta, G4double pDTheta)
G4ThreeVector GetPointOnSurface() const
G4double GetMaxXExtent() const
G4double GetMinZExtent() const
G4GLOB_DLL std::ostream G4cout
void CalculateClippedPolygonExtent(G4ThreeVectorList &pPolygon, const G4VoxelLimits &pVoxelLimit, const EAxis pAxis, G4double &pMin, G4double &pMax) const
G4bool CalculateExtent(const EAxis pAxis, const G4VoxelLimits &pVoxelLimit, const G4AffineTransform &pTransform, G4double &pmin, G4double &pmax) const
void CheckThetaAngles(G4double sTheta, G4double dTheta)
G4double GetRadialTolerance() const
G4double DistanceToOut(const G4ThreeVector &p, const G4ThreeVector &v, const G4bool calcNorm=G4bool(false), G4bool *validNorm=0, G4ThreeVector *n=0) const
G4ThreeVectorList * CreateRotatedVertices(const G4AffineTransform &pTransform, G4int &noPolygonVertices) const
EInside Inside(const G4ThreeVector &p) const
void CheckPhiAngles(G4double sPhi, G4double dPhi)
std::vector< G4ThreeVector > G4ThreeVectorList
G4GeometryType GetEntityType() const
G4ThreeVector SurfaceNormal(const G4ThreeVector &p) const
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *comments)
G4ThreeVector ApproxSurfaceNormal(const G4ThreeVector &p) const
virtual void ComputeDimensions(G4Box &, const G4int, const G4VPhysicalVolume *) const
G4Sphere & operator=(const G4Sphere &rhs)
G4double GetMinXExtent() const
G4double GetMaxZExtent() const
T max(const T t1, const T t2)
brief Return the largest of the two arguments
std::ostream & StreamInfo(std::ostream &os) const
void ComputeDimensions(G4VPVParameterisation *p, const G4int n, const G4VPhysicalVolume *pRep)
static const double degree
G4VisExtent GetExtent() const
G4double GetSurfaceArea()
G4double GetMaxYExtent() const
G4double GetMaxExtent(const EAxis pAxis) const
G4CSGSolid & operator=(const G4CSGSolid &rhs)
G4bool IsZLimited() const
G4double halfAngTolerance
G4double GetAngularTolerance() const
G4double GetMinExtent(const EAxis pAxis) const
const G4double kMeshAngleDefault
static G4GeometryTolerance * GetInstance()
const G4int kMaxMeshSections
void DescribeYourselfTo(G4VGraphicsScene &scene) const