121 std::ostringstream message;
122 message <<
"Invalid swept radius for Solid: " <<
GetName() <<
G4endl
123 <<
" pRtor = " << pRtor <<
", pRmax = " << pRmax;
130 if ( pRmin < pRmax - 1.e2*kCarTolerance && pRmin >= 0 )
133 else { fRmin = 0.0 ; }
138 std::ostringstream message;
139 message <<
"Invalid values of radii for Solid: " <<
GetName() <<
G4endl
140 <<
" pRmin = " << pRmin <<
", pRmax = " << pRmax;
147 fRminTolerance = (fRmin)
148 ? 0.5*std::max( kRadTolerance, fEpsilon*(fRtor-fRmin )) : 0;
149 fRmaxTolerance = 0.5*std::max( kRadTolerance, fEpsilon*(fRtor+fRmax) );
153 if ( pDPhi >= twopi ) { fDPhi = twopi ; }
156 if (pDPhi > 0) { fDPhi = pDPhi ; }
159 std::ostringstream message;
160 message <<
"Invalid Z delta-Phi for Solid: " <<
GetName() <<
G4endl
161 <<
" pDPhi = " << pDPhi;
171 if (fSPhi < 0) { fSPhi = twopi-std::fmod(std::fabs(fSPhi),twopi) ; }
172 else { fSPhi = std::fmod(fSPhi,twopi) ; }
174 if (fSPhi+fDPhi > twopi) { fSPhi-=twopi ; }
183 :
G4CSGSolid(a), fRmin(0.), fRmax(0.), fRtor(0.), fSPhi(0.),
184 fDPhi(0.), fRminTolerance(0.), fRmaxTolerance(0. ),
185 kRadTolerance(0.), kAngTolerance(0.)
201 :
G4CSGSolid(rhs), fRmin(rhs.fRmin),fRmax(rhs.fRmax),
202 fRtor(rhs.fRtor),fSPhi(rhs.fSPhi),fDPhi(rhs.fDPhi),
203 fRminTolerance(rhs.fRminTolerance), fRmaxTolerance(rhs.fRmaxTolerance),
204 kRadTolerance(rhs.kRadTolerance), kAngTolerance(rhs.kAngTolerance)
216 if (
this == &rhs) {
return *
this; }
224 fRmin = rhs.fRmin; fRmax = rhs.fRmax;
225 fRtor = rhs.fRtor; fSPhi = rhs.fSPhi; fDPhi = rhs.fDPhi;
226 fRminTolerance = rhs.fRminTolerance; fRmaxTolerance = rhs.fRmaxTolerance;
227 kRadTolerance = rhs.kRadTolerance; kAngTolerance = rhs.kAngTolerance;
254 std::vector<G4double>& roots )
const
260 G4double Rtor2 = fRtor*fRtor, r2 = r*r ;
267 c[2] = 2*(pRad2 + 2*pDotV*pDotV - Rtor2 - r2 + 2*Rtor2*v.
z()*v.
z()) ;
268 c[3] = 4*(pDotV*(pRad2 - Rtor2 - r2) + 2*Rtor2*p.
z()*v.
z()) ;
269 c[4] = pRad2*pRad2 - 2*pRad2*(Rtor2+r2)
270 + 4*Rtor2*p.
z()*p.
z() + (Rtor2-r2)*(Rtor2-r2) ;
274 num = torusEq.
FindRoots( c, 4, srd, si );
276 for ( i = 0; i < num; i++ )
278 if( si[i] == 0. ) { roots.push_back(srd[i]) ; }
281 std::sort(roots.begin() , roots.end() ) ;
294 G4bool IsDistanceToIn )
const
300 static const G4double halfAngTolerance = 0.5*kAngTolerance;
305 std::vector<G4double> roots ;
306 std::vector<G4double> rootsrefined ;
307 TorusRootsJT(p,v,r,roots) ;
313 for (
size_t k = 0 ; k<roots.size() ; k++ )
317 if ( t < -halfCarTolerance ) { continue ; }
319 if ( t > bigdist && t<kInfinity )
322 TorusRootsJT(ptmp,v,r,rootsrefined) ;
323 if ( rootsrefined.size()==roots.size() )
325 t = t + rootsrefined[k] ;
331 G4double theta = std::atan2(ptmp.
y(),ptmp.
x());
335 if ( theta < - halfAngTolerance ) { theta += twopi; }
336 if ( (std::fabs(theta) < halfAngTolerance)
337 && (std::fabs(fSPhi + fDPhi - twopi) < halfAngTolerance) )
342 if ((fSPhi <= -pi )&&(theta>halfAngTolerance)) { theta = theta-twopi; }
347 if ( (theta - fSPhi >= - halfAngTolerance)
348 && (theta - (fSPhi + fDPhi) <= halfAngTolerance) )
353 if ( IsDistanceToIn ==
true )
355 if (std::fabs(t) < halfCarTolerance )
362 p.
y()*(1-fRtor/std::sqrt(p.
x()*p.
x()
368 if ( r ==
GetRmin() ) { scal = -scal ; }
369 if ( scal < 0 ) {
return 0.0 ; }
376 if ( IsDistanceToIn ==
false )
378 if (std::fabs(t) < halfCarTolerance )
384 p.
y()*(1-fRtor/std::sqrt(p.
x()*p.
x()
390 if ( r ==
GetRmin() ) { scal = -scal ; }
391 if ( scal > 0 ) {
return 0.0 ; }
397 if( t > halfCarTolerance )
417 if ((!pTransform.
IsRotated()) && (fDPhi==twopi) && (fRmin==0))
428 G4double RTorus,delta,diff1,diff2,maxDiff,newMin,newMax;
432 xMin = xoffset - fRmax - fRtor ;
433 xMax = xoffset + fRmax + fRtor ;
453 yMin = yoffset - fRmax - fRtor ;
454 yMax = yoffset + fRmax + fRtor ;
476 zMin = zoffset - fRmax ;
477 zMax = zoffset + fRmax ;
506 if ( yoff1 >= 0 && yoff2 >= 0 )
520 delta = RTorus*RTorus - yoff1*yoff1;
521 diff1 = (delta>0.) ? std::sqrt(delta) : 0.;
522 delta = RTorus*RTorus - yoff2*yoff2;
523 diff2 = (delta>0.) ? std::sqrt(delta) : 0.;
524 maxDiff = (diff1 > diff2) ? diff1:diff2 ;
525 newMin = xoffset - maxDiff ;
526 newMax = xoffset + maxDiff ;
527 pMin = (newMin < xMin) ? xMin : newMin ;
528 pMax = (newMax > xMax) ? xMax : newMax ;
533 xoff1 = xoffset - xMin ;
534 xoff2 = xMax - xoffset ;
535 if (xoff1 >= 0 && xoff2 >= 0 )
548 delta = RTorus*RTorus - xoff1*xoff1;
549 diff1 = (delta>0.) ? std::sqrt(delta) : 0.;
550 delta = RTorus*RTorus - xoff2*xoff2;
551 diff2 = (delta>0.) ? std::sqrt(delta) : 0.;
552 maxDiff = (diff1 > diff2) ? diff1 : diff2 ;
553 newMin = yoffset - maxDiff ;
554 newMax = yoffset + maxDiff ;
555 pMin = (newMin < yMin) ? yMin : newMin ;
556 pMax = (newMax > yMax) ? yMax : newMax ;
575 G4int i, noEntries, noBetweenSections4 ;
576 G4bool existsAfterClip = false ;
581 G4int noPolygonVertices ;
582 vertices = CreateRotatedVertices(pTransform,noPolygonVertices) ;
587 noEntries = vertices->size() ;
588 noBetweenSections4 = noEntries - noPolygonVertices ;
590 for (i=0;i<noEntries;i+=noPolygonVertices)
594 for (i=0;i<noBetweenSections4;i+=noPolygonVertices)
598 if (pMin!=kInfinity||pMax!=-kInfinity)
600 existsAfterClip = true ;
618 existsAfterClip = true ;
624 return existsAfterClip;
634 G4double r2, pt2, pPhi, tolRMin, tolRMax ;
637 static const G4double halfAngTolerance = 0.5*kAngTolerance;
640 r2 = p.
x()*p.
x() + p.
y()*p.
y() ;
641 pt2 = r2 + p.
z()*p.
z() + fRtor*fRtor - 2*fRtor*std::sqrt(r2) ;
643 if (fRmin) tolRMin = fRmin + fRminTolerance ;
646 tolRMax = fRmax - fRmaxTolerance;
648 if (pt2 >= tolRMin*tolRMin && pt2 <= tolRMax*tolRMax )
650 if ( fDPhi == twopi || pt2 == 0 )
659 pPhi = std::atan2(p.
y(),p.
x()) ;
661 if ( pPhi < -halfAngTolerance ) { pPhi += twopi ; }
664 if ( (std::fabs(pPhi) < halfAngTolerance)
665 && (std::fabs(fSPhi + fDPhi - twopi) < halfAngTolerance) )
669 if ( (pPhi >= fSPhi + halfAngTolerance)
670 && (pPhi <= fSPhi + fDPhi - halfAngTolerance) )
674 else if ( (pPhi >= fSPhi - halfAngTolerance)
675 && (pPhi <= fSPhi + fDPhi + halfAngTolerance) )
682 if ( (pPhi <= fSPhi + twopi - halfAngTolerance)
683 && (pPhi >= fSPhi + fDPhi + halfAngTolerance) ) {;}
693 tolRMin = fRmin - fRminTolerance ;
694 tolRMax = fRmax + fRmaxTolerance ;
696 if (tolRMin < 0 ) { tolRMin = 0 ; }
698 if ( (pt2 >= tolRMin*tolRMin) && (pt2 <= tolRMax*tolRMax) )
700 if ( (fDPhi == twopi) || (pt2 == 0) )
706 pPhi = std::atan2(p.
y(),p.
x()) ;
708 if ( pPhi < -halfAngTolerance ) { pPhi += twopi ; }
711 if ( (std::fabs(pPhi) < halfAngTolerance)
712 && (std::fabs(fSPhi + fDPhi - twopi) < halfAngTolerance) )
716 if ( (pPhi >= fSPhi - halfAngTolerance)
717 && (pPhi <= fSPhi + fDPhi + halfAngTolerance) )
724 if ( (pPhi <= fSPhi + twopi - halfAngTolerance)
725 && (pPhi >= fSPhi + fDPhi + halfAngTolerance) ) {;}
745 G4int noSurfaces = 0;
748 G4double distSPhi = kInfinity, distEPhi = kInfinity;
753 1.0e-8*(fRtor+fRmax));
754 const G4double dAngle = 10.0*kAngTolerance;
759 rho2 = p.
x()*p.
x() + p.
y()*p.
y();
760 rho = std::sqrt(rho2);
761 pt2 = rho2+p.
z()*p.
z() +fRtor * (fRtor-2*rho);
762 pt2 = std::max(pt2, 0.0);
763 pt = std::sqrt(pt2) ;
765 G4double distRMax = std::fabs(pt - fRmax);
766 if(fRmin) distRMin = std::fabs(pt - fRmin);
768 if( rho > delta && pt != 0.0 )
770 G4double redFactor= (rho-fRtor)/rho;
781 pPhi = std::atan2(p.
y(),p.
x());
783 if(pPhi < fSPhi-delta) { pPhi += twopi; }
784 else if(pPhi > fSPhi+fDPhi+delta) { pPhi -= twopi; }
786 distSPhi = std::fabs( pPhi - fSPhi );
787 distEPhi = std::fabs(pPhi-fSPhi-fDPhi);
790 nPe =
G4ThreeVector(-std::sin(fSPhi+fDPhi),std::cos(fSPhi+fDPhi),0);
792 if( distRMax <= delta )
797 else if( fRmin && (distRMin <= delta) )
806 if( (fDPhi < twopi) && (fRmin-delta <= pt) && (pt <= (fRmax+delta)) )
808 if (distSPhi <= dAngle)
813 if (distEPhi <= dAngle)
819 if ( noSurfaces == 0 )
829 ed <<
" ERROR> Surface Normal was called for Torus,"
830 <<
" with point not on surface." <<
G4endl;
834 ed <<
" ERROR> Surface Normal has not found a surface, "
835 <<
" despite the point being on the surface. " <<
G4endl;
846 ed <<
" Coordinates of point : " << p <<
G4endl;
847 ed <<
" Parameters of solid : " <<
G4endl << *
this <<
G4endl;
851 G4Exception(
"G4Torus::SurfaceNormal(p)",
"GeomSolids1002",
853 "Failing to find normal, even though point is on surface!" );
857 static const char* NameInside[3]= {
"Inside",
"Surface",
"Outside" };
858 ed <<
" The point is " << NameInside[inIt] <<
" the solid. "<<
G4endl;
859 G4Exception(
"G4Torus::SurfaceNormal(p)",
"GeomSolids1002",
863 norm = ApproxSurfaceNormal(p);
865 else if ( noSurfaces == 1 ) { norm = sumnorm; }
866 else { norm = sumnorm.
unit(); }
883 G4double distRMin,distRMax,distSPhi,distEPhi,distMin;
885 rho2 = p.
x()*p.
x() + p.
y()*p.
y();
886 rho = std::sqrt(rho2) ;
887 pt2 = std::fabs(rho2+p.
z()*p.
z() +fRtor*fRtor - 2*fRtor*rho) ;
888 pt = std::sqrt(pt2) ;
891 G4cout <<
" G4Torus::ApproximateSurfaceNormal called for point " << p
895 distRMax = std::fabs(pt - fRmax) ;
899 distRMin = std::fabs(pt - fRmin) ;
901 if (distRMin < distRMax)
917 if ( (fDPhi < twopi) && rho )
919 phi = std::atan2(p.
y(),p.
x()) ;
921 if (phi < 0) { phi += twopi ; }
923 if (fSPhi < 0 ) { distSPhi = std::fabs(phi-(fSPhi+twopi))*rho ; }
924 else { distSPhi = std::fabs(phi-fSPhi)*rho ; }
926 distEPhi = std::fabs(phi - fSPhi - fDPhi)*rho ;
928 if (distSPhi < distEPhi)
930 if (distSPhi<distMin) side = kNSPhi ;
934 if (distEPhi < distMin) { side = kNEPhi ; }
941 -p.
y()*(1-fRtor/rho)/pt,
946 p.
y()*(1-fRtor/rho)/pt,
953 norm =
G4ThreeVector(-std::sin(fSPhi+fDPhi),std::cos(fSPhi+fDPhi),0) ;
959 "Undefined side for valid surface normal to solid.");
991 G4double snxt=kInfinity, sphi=kInfinity;
1000 G4double cPhi,sinCPhi=0.,cosCPhi=0.;
1015 if ( fDPhi < twopi )
1019 cPhi = fSPhi + hDPhi ;
1020 sinCPhi = std::sin(cPhi) ;
1021 cosCPhi = std::cos(cPhi) ;
1028 if (fRmin > fRminTolerance)
1030 tolORMin2 = (fRmin - fRminTolerance)*(fRmin - fRminTolerance) ;
1036 tolORMax2 = (fRmax + fRmaxTolerance)*(fRmax + fRmaxTolerance) ;
1042 snxt = SolveNumericJT(p,v,fRmax,
true);
1046 sd[0] = SolveNumericJT(p,v,fRmin,
true);
1047 if ( sd[0] < snxt ) { snxt = sd[0] ; }
1062 sinSPhi = std::sin(fSPhi) ;
1063 cosSPhi = std::cos(fSPhi) ;
1064 Comp = v.
x()*sinSPhi - v.
y()*cosSPhi ;
1068 Dist = (p.
y()*cosSPhi - p.
x()*sinSPhi) ;
1070 if (Dist < halfCarTolerance)
1075 if ( sphi < 0 ) { sphi = 0 ; }
1077 xi = p.
x() + sphi*v.
x() ;
1078 yi = p.
y() + sphi*v.
y() ;
1079 zi = p.
z() + sphi*v.
z() ;
1080 rhoi2 = xi*xi + yi*yi ;
1081 it2 = std::fabs(rhoi2 + zi*zi + Rtor2 - 2*fRtor*std::sqrt(rhoi2)) ;
1083 if ( it2 >= tolORMin2 && it2 <= tolORMax2 )
1088 if ((yi*cosCPhi-xi*sinCPhi)<=0) { snxt=sphi; }
1094 sinEPhi=std::sin(ePhi);
1095 cosEPhi=std::cos(ePhi);
1096 Comp=-(v.
x()*sinEPhi-v.
y()*cosEPhi);
1100 Dist = -(p.
y()*cosEPhi - p.
x()*sinEPhi) ;
1102 if (Dist < halfCarTolerance )
1108 if (sphi < 0 ) { sphi = 0 ; }
1110 xi = p.
x() + sphi*v.
x() ;
1111 yi = p.
y() + sphi*v.
y() ;
1112 zi = p.
z() + sphi*v.
z() ;
1113 rhoi2 = xi*xi + yi*yi ;
1114 it2 = std::fabs(rhoi2 + zi*zi + Rtor2 - 2*fRtor*std::sqrt(rhoi2)) ;
1116 if (it2 >= tolORMin2 && it2 <= tolORMax2)
1121 if ((yi*cosCPhi-xi*sinCPhi)>=0) { snxt=sphi; }
1127 if(snxt < halfCarTolerance) { snxt = 0.0 ; }
1142 G4double phiC, cosPhiC, sinPhiC, safePhi, ePhi, cosPsi ;
1145 rho2 = p.
x()*p.
x() + p.
y()*p.
y() ;
1146 rho = std::sqrt(rho2) ;
1147 pt2 = std::fabs(rho2 + p.
z()*p.
z() + fRtor*fRtor - 2*fRtor*rho) ;
1148 pt = std::sqrt(pt2) ;
1150 safe1 = fRmin - pt ;
1151 safe2 = pt - fRmax ;
1153 if (safe1 > safe2) { safe = safe1; }
1154 else { safe = safe2; }
1156 if ( fDPhi < twopi && rho )
1158 phiC = fSPhi + fDPhi*0.5 ;
1159 cosPhiC = std::cos(phiC) ;
1160 sinPhiC = std::sin(phiC) ;
1161 cosPsi = (p.
x()*cosPhiC + p.
y()*sinPhiC)/rho ;
1163 if (cosPsi < std::cos(fDPhi*0.5) )
1165 if ((p.
y()*cosPhiC - p.
x()*sinPhiC) <= 0 )
1167 safePhi = std::fabs(p.
x()*std::sin(fSPhi) - p.
y()*std::cos(fSPhi)) ;
1171 ePhi = fSPhi + fDPhi ;
1172 safePhi = std::fabs(p.
x()*std::sin(ePhi) - p.
y()*std::cos(ePhi)) ;
1174 if (safePhi > safe) { safe = safePhi ; }
1177 if (safe < 0 ) { safe = 0 ; }
1193 ESide side = kNull, sidephi = kNull ;
1194 G4double snxt = kInfinity, sphi, sd[4] ;
1197 static const G4double halfAngTolerance = 0.5*kAngTolerance;
1201 G4double sinSPhi, cosSPhi, ePhi, sinEPhi, cosEPhi;
1203 G4double pDistS, compS, pDistE, compE, sphi2, xi, yi, zi, vphi ;
1218 G4double pt2 = rho2 + p.
z()*p.
z() + fRtor * (fRtor - 2.0*rho);
1223 pt2= std::fabs( pt2 );
1230 G4double tolRMax = fRmax - fRmaxTolerance ;
1232 G4double vDotNmax = pDotV - fRtor*(v.
x()*p.
x() + v.
y()*p.
y())/rho ;
1233 G4double pDotxyNmax = (1 - fRtor/rho) ;
1235 if( (pt2 > tolRMax*tolRMax) && (vDotNmax >= 0) )
1241 if ( calcNorm && (pDotxyNmax >= -2.*fRmaxTolerance) )
1244 p.
y()*(1 - fRtor/rho)/pt,
1252 snxt = SolveNumericJT(p,v,fRmax,
false);
1259 G4double tolRMin = fRmin + fRminTolerance ;
1261 if ( (pt2 < tolRMin*tolRMin) && (vDotNmax < 0) )
1263 if (calcNorm) { *validNorm = false ; }
1267 sd[0] = SolveNumericJT(p,v,fRmin,
false);
1280 snxt = SolveNumericJT(p,v,fRmax,
false);
1285 sd[0] = SolveNumericJT(p,v,fRmin,
false);
1293 if ( calcNorm && (snxt == 0.0) )
1295 *validNorm = false ;
1303 sinSPhi = std::sin(fSPhi) ;
1304 cosSPhi = std::cos(fSPhi) ;
1305 ePhi = fSPhi + fDPhi ;
1306 sinEPhi = std::sin(ePhi) ;
1307 cosEPhi = std::cos(ePhi) ;
1308 cPhi = fSPhi + fDPhi*0.5 ;
1309 sinCPhi = std::sin(cPhi) ;
1310 cosCPhi = std::cos(cPhi) ;
1315 vphi = std::atan2(v.
y(),v.
x()) ;
1317 if ( vphi < fSPhi - halfAngTolerance ) { vphi += twopi; }
1318 else if ( vphi > ePhi + halfAngTolerance ) { vphi -= twopi; }
1320 if ( p.
x() || p.
y() )
1322 pDistS = p.
x()*sinSPhi - p.
y()*cosSPhi ;
1323 pDistE = -p.
x()*sinEPhi + p.
y()*cosEPhi ;
1327 compS = -sinSPhi*v.
x() + cosSPhi*v.
y() ;
1328 compE = sinEPhi*v.
x() - cosEPhi*v.
y() ;
1331 if( ( (fDPhi <= pi) && ( (pDistS <= halfCarTolerance)
1332 && (pDistE <= halfCarTolerance) ) )
1333 || ( (fDPhi > pi) && !((pDistS > halfCarTolerance)
1334 && (pDistE > halfCarTolerance) ) ) )
1340 sphi = pDistS/compS ;
1342 if (sphi >= -halfCarTolerance)
1344 xi = p.
x() + sphi*v.
x() ;
1345 yi = p.
y() + sphi*v.
y() ;
1354 if ( ((fSPhi-halfAngTolerance)<=vphi)
1355 && ((ePhi+halfAngTolerance)>=vphi) )
1360 else if ( yi*cosCPhi-xi*sinCPhi >=0 )
1381 sphi2 = pDistE/compE ;
1387 xi = p.
x() + sphi2*v.
x() ;
1388 yi = p.
y() + sphi2*v.
y() ;
1395 if( !( (fSPhi-halfAngTolerance <= vphi)
1396 && (ePhi+halfAngTolerance >= vphi) ) )
1404 if ( (yi*cosCPhi-xi*sinCPhi) >= 0)
1426 vphi = std::atan2(v.
y(),v.
x());
1428 if ( ( fSPhi-halfAngTolerance <= vphi ) &&
1429 ( vphi <= ( ePhi+halfAngTolerance ) ) )
1449 G4double rhoi2,rhoi,it2,it,iDotxyNmax ;
1458 xi = p.
x() + snxt*v.
x() ;
1459 yi =p.
y() + snxt*v.
y() ;
1460 zi = p.
z() + snxt*v.
z() ;
1461 rhoi2 = xi*xi + yi*yi ;
1462 rhoi = std::sqrt(rhoi2) ;
1463 it2 = std::fabs(rhoi2 + zi*zi + fRtor*fRtor - 2*fRtor*rhoi) ;
1464 it = std::sqrt(it2) ;
1465 iDotxyNmax = (1-fRtor/rhoi) ;
1466 if(iDotxyNmax >= -2.*fRmaxTolerance)
1469 yi*(1-fRtor/rhoi)/it,
1475 *validNorm = false ;
1480 *validNorm = false ;
1491 *validNorm = false ;
1498 *n=
G4ThreeVector(-std::sin(fSPhi+fDPhi),std::cos(fSPhi+fDPhi),0);
1503 *validNorm = false ;
1513 std::ostringstream message;
1514 G4int oldprc = message.precision(16);
1515 message <<
"Undefined side for valid surface normal to solid."
1518 <<
"p.x() = " << p.
x()/mm <<
" mm" <<
G4endl
1519 <<
"p.y() = " << p.
y()/mm <<
" mm" <<
G4endl
1522 <<
"v.x() = " << v.
x() <<
G4endl
1523 <<
"v.y() = " << v.
y() <<
G4endl
1526 <<
"snxt = " << snxt/mm <<
" mm" <<
G4endl;
1527 message.precision(oldprc);
1533 if ( snxt<halfCarTolerance ) { snxt=0 ; }
1546 G4double safePhi,phiC,cosPhiC,sinPhiC,ePhi;
1547 rho2 = p.
x()*p.
x() + p.
y()*p.
y() ;
1548 rho = std::sqrt(rho2) ;
1549 pt2 = std::fabs(rho2 + p.
z()*p.
z() + fRtor*fRtor - 2*fRtor*rho) ;
1550 pt = std::sqrt(pt2) ;
1562 G4cout.precision(oldprc);
1563 G4Exception(
"G4Torus::DistanceToOut(p)",
"GeomSolids1002",
1570 safeR1 = pt - fRmin ;
1571 safeR2 = fRmax - pt ;
1573 if (safeR1 < safeR2) { safe = safeR1 ; }
1574 else { safe = safeR2 ; }
1585 phiC = fSPhi + fDPhi*0.5 ;
1586 cosPhiC = std::cos(phiC) ;
1587 sinPhiC = std::sin(phiC) ;
1589 if ((p.
y()*cosPhiC-p.
x()*sinPhiC)<=0)
1591 safePhi = -(p.
x()*std::sin(fSPhi) - p.
y()*std::cos(fSPhi)) ;
1595 ePhi = fSPhi + fDPhi ;
1596 safePhi = (p.
x()*std::sin(ePhi) - p.
y()*std::cos(ePhi)) ;
1598 if (safePhi < safe) { safe = safePhi ; }
1600 if (safe < 0) { safe = 0 ; }
1617 G4int& noPolygonVertices )
const
1621 G4double meshAngle,meshRMax,crossAngle,cosCrossAngle,sinCrossAngle,sAngle;
1623 G4int crossSection,noCrossSections;
1637 meshAngle = fDPhi/(noCrossSections - 1) ;
1638 meshRMax = (fRtor + fRmax)/std::cos(meshAngle*0.5) ;
1643 if ( (fDPhi == twopi) && (fSPhi == 0) )
1645 sAngle = -meshAngle*0.5 ;
1655 vertices->reserve(noCrossSections*4) ;
1656 for (crossSection=0;crossSection<noCrossSections;crossSection++)
1660 crossAngle=sAngle+crossSection*meshAngle;
1661 cosCrossAngle=std::cos(crossAngle);
1662 sinCrossAngle=std::sin(crossAngle);
1664 rMaxX=meshRMax*cosCrossAngle;
1665 rMaxY=meshRMax*sinCrossAngle;
1666 rMinX=(fRtor-fRmax)*cosCrossAngle;
1667 rMinY=(fRtor-fRmax)*sinCrossAngle;
1678 noPolygonVertices = 4 ;
1685 "Error in allocation of vertices. Out of memory !");
1714 G4int oldprc = os.precision(16);
1715 os <<
"-----------------------------------------------------------\n"
1716 <<
" *** Dump for solid - " <<
GetName() <<
" ***\n"
1717 <<
" ===================================================\n"
1718 <<
" Solid type: G4Torus\n"
1719 <<
" Parameters: \n"
1720 <<
" inner radius: " << fRmin/mm <<
" mm \n"
1721 <<
" outer radius: " << fRmax/mm <<
" mm \n"
1722 <<
" swept radius: " << fRtor/mm <<
" mm \n"
1723 <<
" starting phi: " << fSPhi/degree <<
" degrees \n"
1724 <<
" delta phi : " << fDPhi/degree <<
" degrees \n"
1725 <<
"-----------------------------------------------------------\n";
1726 os.precision(oldprc);
1737 G4double cosu, sinu,cosv, sinv, aOut, aIn, aSide, chose, phi, theta, rRand;
1742 cosu = std::cos(phi); sinu = std::sin(phi);
1743 cosv = std::cos(theta); sinv = std::sin(theta);
1747 aOut = (fDPhi)*twopi*fRtor*fRmax;
1748 aIn = (fDPhi)*twopi*fRtor*fRmin;
1749 aSide = pi*(fRmax*fRmax-fRmin*fRmin);
1751 if ((fSPhi == 0) && (fDPhi == twopi)){ aSide = 0; }
1757 (fRtor+fRmax*cosv)*sinu, fRmax*sinv);
1759 else if( (chose >= aOut) && (chose < aOut + aIn) )
1762 (fRtor+fRmin*cosv)*sinu, fRmin*sinv);
1764 else if( (chose >= aOut + aIn) && (chose < aOut + aIn + aSide) )
1768 (fRtor+rRand*cosv)*std::sin(fSPhi), rRand*sinv);
1773 return G4ThreeVector ((fRtor+rRand*cosv)*std::cos(fSPhi+fDPhi),
1774 (fRtor+rRand*cosv)*std::sin(fSPhi+fDPhi),
1817 fSPhi, fSPhi + fDPhi);
CLHEP::Hep3Vector G4ThreeVector
std::vector< G4ThreeVector > G4ThreeVectorList
G4DLLIMPORT std::ostream G4cout
G4Polyhedron * fpPolyhedron
G4double GetRadiusInRing(G4double rmin, G4double rmax) const
G4CSGSolid & operator=(const G4CSGSolid &rhs)
G4double GetRadialTolerance() const
static G4GeometryTolerance * GetInstance()
G4double GetAngularTolerance() const
G4int FindRoots(G4double *op, G4int degree, G4double *zeror, G4double *zeroi)
EInside Inside(const G4ThreeVector &p) const
G4Torus & operator=(const G4Torus &rhs)
G4GeometryType GetEntityType() const
G4double DistanceToOut(const G4ThreeVector &p, const G4ThreeVector &v, const G4bool calcNorm=G4bool(false), G4bool *validNorm=0, G4ThreeVector *n=0) const
G4bool CalculateExtent(const EAxis pAxis, const G4VoxelLimits &pVoxelLimit, const G4AffineTransform &pTransform, G4double &pmin, G4double &pmax) const
void SetAllParameters(G4double pRmin, G4double pRmax, G4double pRtor, G4double pSPhi, G4double pDPhi)
void ComputeDimensions(G4VPVParameterisation *p, const G4int n, const G4VPhysicalVolume *pRep)
G4ThreeVector SurfaceNormal(const G4ThreeVector &p) const
G4double DistanceToIn(const G4ThreeVector &p, const G4ThreeVector &v) const
G4ThreeVector GetPointOnSurface() const
void DescribeYourselfTo(G4VGraphicsScene &scene) const
G4NURBS * CreateNURBS() const
std::ostream & StreamInfo(std::ostream &os) const
G4Torus(const G4String &pName, G4double pRmin, G4double pRmax, G4double pRtor, G4double pSPhi, G4double pDPhi)
G4Polyhedron * CreatePolyhedron() const
virtual void AddSolid(const G4Box &)=0
virtual void ComputeDimensions(G4Box &, const G4int, const G4VPhysicalVolume *) const
void ClipBetweenSections(G4ThreeVectorList *pVertices, const G4int pSectionIndex, const G4VoxelLimits &pVoxelLimit, const EAxis pAxis, G4double &pMin, G4double &pMax) const
void ClipCrossSection(G4ThreeVectorList *pVertices, const G4int pSectionIndex, const G4VoxelLimits &pVoxelLimit, const EAxis pAxis, G4double &pMin, G4double &pMax) const
G4double GetMinExtent(const EAxis pAxis) const
G4bool IsYLimited() const
G4double GetMinZExtent() const
G4bool IsXLimited() const
G4double GetMaxExtent(const EAxis pAxis) const
G4double GetMaxYExtent() const
G4double GetMaxZExtent() const
G4double GetMinYExtent() const
G4double GetMinXExtent() const
G4bool IsZLimited() const
G4double GetMaxXExtent() const
void G4Exception(const char *originOfException, const char *exceptionCode, G4ExceptionSeverity severity, const char *comments)
std::ostringstream G4ExceptionDescription
const G4int kMaxMeshSections
const G4int kMinMeshSections
const G4double kMeshAngleDefault