59 using namespace CLHEP;
89 "Invalid radius > 10*kCarTolerance.");
91 fRmaxTolerance = std::max( kRadTolerance, fEpsilon*fRmax);
101 :
G4CSGSolid(a), fRmax(0.), fRmaxTolerance(0.)
118 :
G4CSGSolid(rhs), fRmax(rhs.fRmax), fRmaxTolerance(rhs.fRmaxTolerance)
130 if (
this == &rhs) {
return *
this; }
139 fRmaxTolerance = rhs.fRmaxTolerance;
173 G4double diff1,diff2,delta,maxDiff,newMin,newMax;
254 if ( yoff1 >= 0 && yoff2 >= 0 )
266 delta=fRmax*fRmax-yoff1*yoff1;
267 diff1=(delta>0.) ? std::sqrt(delta) : 0.;
268 delta=fRmax*fRmax-yoff2*yoff2;
269 diff2=(delta>0.) ? std::sqrt(delta) : 0.;
270 maxDiff=(diff1>diff2) ? diff1:diff2;
271 newMin=xoffset-maxDiff;
272 newMax=xoffset+maxDiff;
273 pMin=(newMin<xMin) ? xMin : newMin;
274 pMax=(newMax>xMax) ? xMax : newMax;
280 if (xoff1>=0&&xoff2>=0)
292 delta=fRmax*fRmax-xoff1*xoff1;
293 diff1=(delta>0.) ? std::sqrt(delta) : 0.;
294 delta=fRmax*fRmax-xoff2*xoff2;
295 diff2=(delta>0.) ? std::sqrt(delta) : 0.;
296 maxDiff=(diff1>diff2) ? diff1:diff2;
297 newMin=yoffset-maxDiff;
298 newMax=yoffset+maxDiff;
299 pMin=(newMin<yMin) ? yMin : newMin;
300 pMax=(newMax>yMax) ? yMax : newMax;
310 pMin -= fRmaxTolerance;
311 pMax += fRmaxTolerance;
329 rad2 = p.
x()*p.
x()+p.
y()*p.
y()+p.
z()*p.
z();
337 tolRMax = fRmax - fRmaxTolerance*0.5;
339 if ( radius <= tolRMax ) { in =
kInside; }
342 tolRMax = fRmax + fRmaxTolerance*0.5;
343 if ( radius <= tolRMax ) { in =
kSurface; }
369 "Undefined side for valid surface normal to solid.");
397 radius = std::sqrt(p.
x()*p.
x() + p.
y()*p.
y() + p.
z()*p.
z());
398 pDotV3d = p.
x()*v.
x() + p.
y()*v.
y() + p.
z()*v.
z();
419 c = (radius - fRmax)*(radius + fRmax);
421 if( radius > fRmax-fRmaxTolerance*0.5 )
423 if ( c > fRmaxTolerance*fRmax )
428 d2 = pDotV3d*pDotV3d -
c;
432 sd = -pDotV3d - std::sqrt(d2);
437 G4double fTerm = sd - std::fmod(sd,dRmax);
445 return snxt = kInfinity;
450 if ( c > -fRmaxTolerance*fRmax )
452 d2 = pDotV3d*pDotV3d -
c;
453 if ( (d2 < fRmaxTolerance*fRmax) || (pDotV3d >= 0) )
455 return snxt = kInfinity;
467 G4Exception(
"G4Orb::DistanceToIn(p,v)",
"GeomSolids1002",
484 radius = std::sqrt(p.
x()*p.
x()+p.
y()*p.
y()+p.
z()*p.
z());
485 safe = radius - fRmax;
486 if( safe < 0 ) { safe = 0.; }
508 rad2 = p.
x()*p.
x() + p.
y()*p.
y() + p.
z()*p.
z();
509 pDotV3d = p.
x()*v.
x() + p.
y()*v.
y() + p.
z()*v.
z();
527 const G4double Rmax_plus = fRmax + fRmaxTolerance*0.5;
530 if ( radius <= Rmax_plus )
532 c = (radius - fRmax)*(radius + fRmax);
534 if ( c < fRmaxTolerance*fRmax )
545 d2 = pDotV3d*pDotV3d -
c;
547 if( ( c > -fRmaxTolerance*fRmax) &&
548 ( ( pDotV3d >= 0 ) || ( d2 < 0 )) )
560 snxt = -pDotV3d + std::sqrt(d2);
569 std::ostringstream message;
570 G4int oldprc = message.precision(16);
571 message <<
"Logic error: snxt = kInfinity ???" << G4endl
572 <<
"Position:" << G4endl << G4endl
573 <<
"p.x() = " << p.
x()/
mm <<
" mm" << G4endl
574 <<
"p.y() = " << p.
y()/
mm <<
" mm" << G4endl
575 <<
"p.z() = " << p.
z()/
mm <<
" mm" << G4endl << G4endl
576 <<
"Rp = "<< std::sqrt( p.
x()*p.
x()+p.
y()*p.
y()+p.
z()*p.
z() )/
mm
577 <<
" mm" << G4endl << G4endl
578 <<
"Direction:" << G4endl << G4endl
579 <<
"v.x() = " << v.
x() << G4endl
580 <<
"v.y() = " << v.
y() << G4endl
581 <<
"v.z() = " << v.
z() << G4endl << G4endl
582 <<
"Proposed distance :" << G4endl << G4endl
583 <<
"snxt = " << snxt/
mm <<
" mm" <<
G4endl;
584 message.precision(oldprc);
585 G4Exception(
"G4Orb::DistanceToOut(p,v,..)",
"GeomSolids1002",
602 std::ostringstream message;
603 G4int oldprc = message.precision(16);
604 message <<
"Undefined side for valid surface normal to solid."
606 <<
"Position:" << G4endl << G4endl
607 <<
"p.x() = " << p.
x()/
mm <<
" mm" << G4endl
608 <<
"p.y() = " << p.
y()/
mm <<
" mm" << G4endl
609 <<
"p.z() = " << p.
z()/
mm <<
" mm" << G4endl << G4endl
610 <<
"Direction:" << G4endl << G4endl
611 <<
"v.x() = " << v.
x() << G4endl
612 <<
"v.y() = " << v.
y() << G4endl
613 <<
"v.z() = " << v.
z() << G4endl << G4endl
614 <<
"Proposed distance :" << G4endl << G4endl
615 <<
"snxt = " << snxt/
mm <<
" mm" <<
G4endl;
616 message.precision(oldprc);
617 G4Exception(
"G4Orb::DistanceToOut(p,v,..)",
"GeomSolids1002",
631 G4double safe=0.0,radius = std::sqrt(p.
x()*p.
x()+p.
y()*p.
y()+p.
z()*p.
z());
644 G4Exception(
"G4Orb::DistanceToOut(p)",
"GeomSolids1002",
649 safe = fRmax - radius;
650 if ( safe < 0. ) safe = 0.;
669 return new G4Orb(*
this);
678 G4int oldprc = os.precision(16);
679 os <<
"-----------------------------------------------------------\n"
680 <<
" *** Dump for solid - " <<
GetName() <<
" ***\n"
681 <<
" ===================================================\n"
682 <<
" Solid type: G4Orb\n"
685 <<
" outer radius: " << fRmax/
mm <<
" mm \n"
686 <<
"-----------------------------------------------------------\n";
687 os.precision(oldprc);
705 G4double costheta = RandFlat::shoot(-1.,1.);
709 fRmax*sintheta*sinphi, fRmax*costheta);