G4VTwistedFaceted Class Reference

#include <G4VTwistedFaceted.hh>

Inheritance diagram for G4VTwistedFaceted:

G4VSolid G4TwistedBox G4TwistedTrap G4TwistedTrd

Public Member Functions

 G4VTwistedFaceted (const G4String &pname, G4double PhiTwist, G4double pDz, G4double pTheta, G4double pPhi, G4double pDy1, G4double pDx1, G4double pDx2, G4double pDy2, G4double pDx3, G4double pDx4, G4double pAlph)
virtual ~G4VTwistedFaceted ()
virtual void ComputeDimensions (G4VPVParameterisation *, const G4int, const G4VPhysicalVolume *)
virtual G4bool CalculateExtent (const EAxis pAxis, const G4VoxelLimits &pVoxelLimit, const G4AffineTransform &pTransform, G4double &pMin, G4double &pMax) const
virtual G4double DistanceToIn (const G4ThreeVector &p, const G4ThreeVector &v) const
virtual G4double DistanceToIn (const G4ThreeVector &p) const
virtual G4double DistanceToOut (const G4ThreeVector &p, const G4ThreeVector &v, const G4bool calcnorm=false, G4bool *validnorm=0, G4ThreeVector *n=0) const
virtual G4double DistanceToOut (const G4ThreeVector &p) const
virtual EInside Inside (const G4ThreeVector &p) const
virtual G4ThreeVector SurfaceNormal (const G4ThreeVector &p) const
G4ThreeVector GetPointOnSurface () const
G4ThreeVector GetPointInSolid (G4double z) const
virtual G4double GetCubicVolume ()
virtual G4double GetSurfaceArea ()
virtual void DescribeYourselfTo (G4VGraphicsScene &scene) const
virtual G4PolyhedronCreatePolyhedron () const
virtual G4NURBSCreateNURBS () const
virtual G4PolyhedronGetPolyhedron () const
virtual std::ostream & StreamInfo (std::ostream &os) const
G4double GetTwistAngle () const
G4double GetDx1 () const
G4double GetDx2 () const
G4double GetDx3 () const
G4double GetDx4 () const
G4double GetDy1 () const
G4double GetDy2 () const
G4double GetDz () const
G4double GetPhi () const
G4double GetTheta () const
G4double GetAlpha () const
G4double Xcoef (G4double u, G4double phi, G4double ftg) const
G4double GetValueA (G4double phi) const
G4double GetValueB (G4double phi) const
G4double GetValueD (G4double phi) const
virtual G4VisExtent GetExtent () const
virtual G4GeometryType GetEntityType () const
 G4VTwistedFaceted (__void__ &)
 G4VTwistedFaceted (const G4VTwistedFaceted &rhs)
G4VTwistedFacetedoperator= (const G4VTwistedFaceted &rhs)

Protected Member Functions

G4ThreeVectorListCreateRotatedVertices (const G4AffineTransform &pTransform) const

Data Structures

class  LastState
class  LastValue
class  LastValueWithDoubleVector
class  LastVector

Detailed Description

Definition at line 58 of file G4VTwistedFaceted.hh.


Constructor & Destructor Documentation

G4VTwistedFaceted::G4VTwistedFaceted ( const G4String pname,
G4double  PhiTwist,
G4double  pDz,
G4double  pTheta,
G4double  pPhi,
G4double  pDy1,
G4double  pDx1,
G4double  pDx2,
G4double  pDy2,
G4double  pDx3,
G4double  pDx4,
G4double  pAlph 
)

Definition at line 67 of file G4VTwistedFaceted.cc.

References FatalErrorInArgument, G4cout, G4endl, G4Exception(), G4GeometryTolerance::GetAngularTolerance(), G4GeometryTolerance::GetInstance(), G4VSolid::GetName(), G4VSolid::kCarTolerance, and G4INCL::Math::pi.

00080   : G4VSolid(pname), 
00081     fLowerEndcap(0), fUpperEndcap(0), fSide0(0),
00082     fSide90(0), fSide180(0), fSide270(0),
00083     fSurfaceArea(0.), fpPolyhedron(0)
00084 {
00085 
00086   G4double pDytmp ;
00087   G4double fDxUp ;
00088   G4double fDxDown ;
00089 
00090   fDx1 = pDx1 ;
00091   fDx2 = pDx2 ;
00092   fDx3 = pDx3 ;
00093   fDx4 = pDx4 ;
00094   fDy1 = pDy1 ;
00095   fDy2 = pDy2 ;
00096   fDz  = pDz  ;
00097 
00098   G4double kAngTolerance
00099     = G4GeometryTolerance::GetInstance()->GetAngularTolerance();
00100 
00101   // maximum values
00102   //
00103   fDxDown = ( fDx1 > fDx2 ? fDx1 : fDx2 ) ;
00104   fDxUp   = ( fDx3 > fDx4 ? fDx3 : fDx4 ) ;
00105   fDx     = ( fDxUp > fDxDown ? fDxUp : fDxDown ) ;
00106   fDy     = ( fDy1 > fDy2 ? fDy1 : fDy2 ) ;
00107   
00108   // planarity check
00109   //
00110   if ( fDx1 != fDx2 && fDx3 != fDx4 )
00111   {
00112     pDytmp = fDy1 * ( fDx3 - fDx4 ) / ( fDx1 - fDx2 ) ;
00113     if ( std::fabs(pDytmp - fDy2) > kCarTolerance )
00114     {
00115       std::ostringstream message;
00116       message << "Not planar surface in untwisted Trapezoid: "
00117               << GetName() << G4endl
00118               << "fDy2 is " << fDy2 << " but should be "
00119               << pDytmp << ".";
00120       G4Exception("G4VTwistedFaceted::G4VTwistedFaceted()", "GeomSolids0002",
00121                   FatalErrorInArgument, message);
00122     }
00123   }
00124 
00125 #ifdef G4TWISTDEBUG
00126   if ( fDx1 == fDx2 && fDx3 == fDx4 )
00127   { 
00128       G4cout << "Trapezoid is a box" << G4endl ;
00129   }
00130   
00131 #endif
00132 
00133   if ( (  fDx1 == fDx2 && fDx3 != fDx4 ) || ( fDx1 != fDx2 && fDx3 == fDx4 ) )
00134   {
00135     std::ostringstream message;
00136     message << "Not planar surface in untwisted Trapezoid: "
00137             << GetName() << G4endl
00138             << "One endcap is rectangular, the other is a trapezoid." << G4endl
00139             << "For planarity reasons they have to be rectangles or trapezoids "
00140             << "on both sides.";
00141     G4Exception("G4VTwistedFaceted::G4VTwistedFaceted()", "GeomSolids0002",
00142                 FatalErrorInArgument, message);
00143   }
00144 
00145   // twist angle
00146   //
00147   fPhiTwist = PhiTwist ;
00148 
00149   // tilt angle
00150   //
00151   fAlph = pAlph ; 
00152   fTAlph = std::tan(fAlph) ;
00153   
00154   fTheta = pTheta ;
00155   fPhi   = pPhi ;
00156 
00157   // dx in surface equation
00158   //
00159   fdeltaX = 2 * fDz * std::tan(fTheta) * std::cos(fPhi)  ;
00160 
00161   // dy in surface equation
00162   //
00163   fdeltaY = 2 * fDz * std::tan(fTheta) * std::sin(fPhi)  ;
00164 
00165   if  ( ! ( ( fDx1  > 2*kCarTolerance)
00166          && ( fDx2  > 2*kCarTolerance)
00167          && ( fDx3  > 2*kCarTolerance)
00168          && ( fDx4  > 2*kCarTolerance)
00169          && ( fDy1  > 2*kCarTolerance)
00170          && ( fDy2  > 2*kCarTolerance)
00171          && ( fDz   > 2*kCarTolerance) 
00172          && ( std::fabs(fPhiTwist) > 2*kAngTolerance )
00173          && ( std::fabs(fPhiTwist) < pi/2 )
00174          && ( std::fabs(fAlph) < pi/2 )
00175          && ( fTheta < pi/2 && fTheta >= 0 ) )
00176       )
00177   {
00178     std::ostringstream message;
00179     message << "Invalid dimensions. Too small, or twist angle too big: "
00180             << GetName() << G4endl
00181             << "fDx 1-4 = " << fDx1/cm << ", " << fDx2/cm << ", "
00182             << fDx3/cm << ", " << fDx4/cm << " cm" << G4endl 
00183             << "fDy 1-2 = " << fDy1/cm << ", " << fDy2/cm << ", "
00184             << " cm" << G4endl 
00185             << "fDz = " << fDz/cm << " cm" << G4endl 
00186             << " twistangle " << fPhiTwist/deg << " deg" << G4endl 
00187             << " phi,theta = " << fPhi/deg << ", "  << fTheta/deg << " deg";
00188     G4Exception("G4TwistedTrap::G4VTwistedFaceted()",
00189                 "GeomSolids0002", FatalErrorInArgument, message);
00190   }
00191   CreateSurfaces();
00192   fCubicVolume = 2 * fDz * ( ( fDx1 + fDx2 ) * fDy1 + ( fDx3 + fDx4 ) * fDy2 );
00193 }

G4VTwistedFaceted::~G4VTwistedFaceted (  )  [virtual]

Definition at line 211 of file G4VTwistedFaceted.cc.

00212 {
00213   if (fLowerEndcap) delete fLowerEndcap ;
00214   if (fUpperEndcap) delete fUpperEndcap ;
00215 
00216   if (fSide0)       delete fSide0 ;
00217   if (fSide90)      delete fSide90 ;
00218   if (fSide180)     delete fSide180 ;
00219   if (fSide270)     delete fSide270 ;
00220   if (fpPolyhedron) delete fpPolyhedron;
00221 }

G4VTwistedFaceted::G4VTwistedFaceted ( __void__ &   ) 

Definition at line 199 of file G4VTwistedFaceted.cc.

00200   : G4VSolid(a), fTheta(0.), fPhi(0.), fDy1(0.), fDx1(0.), fDx2(0.),
00201     fDy2(0.), fDx3(0.), fDx4(0.), fDz(0.), fDx(0.), fDy(0.), fAlph(0.),
00202     fTAlph(0.), fdeltaX(0.), fdeltaY(0.), fPhiTwist(0.),
00203     fLowerEndcap(0), fUpperEndcap(0), fSide0(0), fSide90(0), fSide180(0),
00204     fSide270(0), fCubicVolume(0.), fSurfaceArea(0.), fpPolyhedron(0)
00205 {
00206 }

G4VTwistedFaceted::G4VTwistedFaceted ( const G4VTwistedFaceted rhs  ) 

Definition at line 226 of file G4VTwistedFaceted.cc.

00227   : G4VSolid(rhs), fTheta(rhs.fTheta), fPhi(rhs.fPhi),
00228     fDy1(rhs.fDy1), fDx1(rhs.fDx1), fDx2(rhs.fDx2), fDy2(rhs.fDy2),
00229     fDx3(rhs.fDx3), fDx4(rhs.fDx4), fDz(rhs.fDz), fDx(rhs.fDx), fDy(rhs.fDy),
00230     fAlph(rhs.fAlph), fTAlph(rhs.fTAlph), fdeltaX(rhs.fdeltaX),
00231     fdeltaY(rhs.fdeltaY), fPhiTwist(rhs.fPhiTwist), fLowerEndcap(0),
00232     fUpperEndcap(0), fSide0(0), fSide90(0), fSide180(0), fSide270(0),
00233     fCubicVolume(rhs.fCubicVolume), fSurfaceArea(rhs.fSurfaceArea),
00234     fpPolyhedron(0),
00235     fLastInside(rhs.fLastInside), fLastNormal(rhs.fLastNormal),
00236     fLastDistanceToIn(rhs.fLastDistanceToIn),
00237     fLastDistanceToOut(rhs.fLastDistanceToOut),
00238     fLastDistanceToInWithV(rhs.fLastDistanceToInWithV),
00239     fLastDistanceToOutWithV(rhs.fLastDistanceToOutWithV)
00240 {
00241   CreateSurfaces();
00242 }


Member Function Documentation

G4bool G4VTwistedFaceted::CalculateExtent ( const EAxis  pAxis,
const G4VoxelLimits pVoxelLimit,
const G4AffineTransform pTransform,
G4double pMin,
G4double pMax 
) const [virtual]

Implements G4VSolid.

Definition at line 295 of file G4VTwistedFaceted.cc.

References G4VSolid::ClipBetweenSections(), G4VSolid::ClipCrossSection(), CreateRotatedVertices(), G4VoxelLimits::GetMaxExtent(), G4VoxelLimits::GetMaxXExtent(), G4VoxelLimits::GetMaxYExtent(), G4VoxelLimits::GetMaxZExtent(), G4VoxelLimits::GetMinExtent(), G4VoxelLimits::GetMinXExtent(), G4VoxelLimits::GetMinYExtent(), G4VoxelLimits::GetMinZExtent(), Inside(), G4AffineTransform::Inverse(), G4VoxelLimits::IsLimited(), G4AffineTransform::IsRotated(), G4VoxelLimits::IsXLimited(), G4VoxelLimits::IsYLimited(), G4VoxelLimits::IsZLimited(), G4VSolid::kCarTolerance, kOutside, kXAxis, kYAxis, kZAxis, G4AffineTransform::NetTranslation(), and G4AffineTransform::TransformPoint().

00300 {
00301   G4double maxRad = std::sqrt( fDx*fDx + fDy*fDy);
00302 
00303   if (!pTransform.IsRotated())
00304     {
00305       // Special case handling for unrotated boxes
00306       // Compute x/y/z mins and maxs respecting limits, with early returns
00307       // if outside limits. Then switch() on pAxis
00308       
00309       G4double xoffset,xMin,xMax;
00310       G4double yoffset,yMin,yMax;
00311       G4double zoffset,zMin,zMax;
00312 
00313       xoffset = pTransform.NetTranslation().x() ;
00314       xMin    = xoffset - maxRad ;
00315       xMax    = xoffset + maxRad ;
00316 
00317       if (pVoxelLimit.IsXLimited())
00318         {
00319           if ( xMin > pVoxelLimit.GetMaxXExtent()+kCarTolerance || 
00320                xMax < pVoxelLimit.GetMinXExtent()-kCarTolerance  ) return false;
00321           else
00322             {
00323               if (xMin < pVoxelLimit.GetMinXExtent())
00324                 {
00325                   xMin = pVoxelLimit.GetMinXExtent() ;
00326                 }
00327               if (xMax > pVoxelLimit.GetMaxXExtent())
00328                 {
00329                   xMax = pVoxelLimit.GetMaxXExtent() ;
00330                 }
00331             }
00332         }
00333       yoffset = pTransform.NetTranslation().y() ;
00334       yMin    = yoffset - maxRad ;
00335       yMax    = yoffset + maxRad ;
00336       
00337       if (pVoxelLimit.IsYLimited())
00338         {
00339           if ( yMin > pVoxelLimit.GetMaxYExtent()+kCarTolerance ||
00340                yMax < pVoxelLimit.GetMinYExtent()-kCarTolerance  ) return false;
00341           else
00342             {
00343               if (yMin < pVoxelLimit.GetMinYExtent())
00344                 {
00345                   yMin = pVoxelLimit.GetMinYExtent() ;
00346                 }
00347               if (yMax > pVoxelLimit.GetMaxYExtent())
00348                 {
00349                   yMax = pVoxelLimit.GetMaxYExtent() ;
00350                 }
00351             }
00352         }
00353       zoffset = pTransform.NetTranslation().z() ;
00354       zMin    = zoffset - fDz ;
00355       zMax    = zoffset + fDz ;
00356       
00357       if (pVoxelLimit.IsZLimited())
00358         {
00359           if ( zMin > pVoxelLimit.GetMaxZExtent()+kCarTolerance ||
00360                zMax < pVoxelLimit.GetMinZExtent()-kCarTolerance  ) return false;
00361           else
00362             {
00363               if (zMin < pVoxelLimit.GetMinZExtent())
00364                 {
00365                   zMin = pVoxelLimit.GetMinZExtent() ;
00366                 }
00367               if (zMax > pVoxelLimit.GetMaxZExtent())
00368                 {
00369                   zMax = pVoxelLimit.GetMaxZExtent() ;
00370                 }
00371             }
00372         }
00373       switch (pAxis)
00374         {
00375         case kXAxis:
00376           pMin = xMin ;
00377           pMax = xMax ;
00378           break ;
00379         case kYAxis:
00380           pMin=yMin;
00381           pMax=yMax;
00382           break;
00383         case kZAxis:
00384         pMin=zMin;
00385         pMax=zMax;
00386         break;
00387         default:
00388           break;
00389         }
00390       pMin -= kCarTolerance ;
00391       pMax += kCarTolerance ;
00392       
00393       return true;
00394   }
00395   else  // General rotated case - create and clip mesh to boundaries
00396     {
00397       G4bool existsAfterClip = false ;
00398       G4ThreeVectorList* vertices ;
00399 
00400       pMin = +kInfinity ;
00401       pMax = -kInfinity ;
00402     
00403     // Calculate rotated vertex coordinates
00404       
00405       vertices = CreateRotatedVertices(pTransform) ;
00406       ClipCrossSection(vertices,0,pVoxelLimit,pAxis,pMin,pMax) ;
00407       ClipCrossSection(vertices,4,pVoxelLimit,pAxis,pMin,pMax) ;
00408       ClipBetweenSections(vertices,0,pVoxelLimit,pAxis,pMin,pMax) ;
00409       
00410       if (pVoxelLimit.IsLimited(pAxis) == false) 
00411         {  
00412           if ( pMin != kInfinity || pMax != -kInfinity ) 
00413             {
00414               existsAfterClip = true ;
00415 
00416               // Add 2*tolerance to avoid precision troubles
00417 
00418               pMin           -= kCarTolerance;
00419               pMax           += kCarTolerance;
00420             }
00421         }      
00422       else
00423         {
00424           G4ThreeVector clipCentre(
00425             ( pVoxelLimit.GetMinXExtent()+pVoxelLimit.GetMaxXExtent())*0.5,
00426             ( pVoxelLimit.GetMinYExtent()+pVoxelLimit.GetMaxYExtent())*0.5,
00427             ( pVoxelLimit.GetMinZExtent()+pVoxelLimit.GetMaxZExtent())*0.5 );
00428           
00429       if ( pMin != kInfinity || pMax != -kInfinity )
00430         {
00431           existsAfterClip = true ;
00432           
00433           // Check to see if endpoints are in the solid
00434           
00435           clipCentre(pAxis) = pVoxelLimit.GetMinExtent(pAxis);
00436           
00437           if (Inside(pTransform.Inverse().TransformPoint(clipCentre))
00438               != kOutside)
00439             {
00440               pMin = pVoxelLimit.GetMinExtent(pAxis);
00441             }
00442           else
00443             {
00444               pMin -= kCarTolerance;
00445             }
00446           clipCentre(pAxis) = pVoxelLimit.GetMaxExtent(pAxis);
00447           
00448           if (Inside(pTransform.Inverse().TransformPoint(clipCentre))
00449               != kOutside)
00450             {
00451               pMax = pVoxelLimit.GetMaxExtent(pAxis);
00452             }
00453           else
00454             {
00455               pMax += kCarTolerance;
00456             }
00457         }
00458       
00459       // Check for case where completely enveloping clipping volume
00460       // If point inside then we are confident that the solid completely
00461       // envelopes the clipping volume. Hence set min/max extents according
00462       // to clipping volume extents along the specified axis.
00463       
00464       else if (Inside(pTransform.Inverse().TransformPoint(clipCentre))
00465                != kOutside)
00466         {
00467           existsAfterClip = true ;
00468           pMin            = pVoxelLimit.GetMinExtent(pAxis) ;
00469           pMax            = pVoxelLimit.GetMaxExtent(pAxis) ;
00470         }
00471         } 
00472       delete vertices;
00473       return existsAfterClip;
00474     } 
00475   
00476   
00477 }

void G4VTwistedFaceted::ComputeDimensions ( G4VPVParameterisation ,
const   G4int,
const G4VPhysicalVolume  
) [virtual]

Reimplemented from G4VSolid.

Definition at line 282 of file G4VTwistedFaceted.cc.

References FatalException, and G4Exception().

00285 {
00286   G4Exception("G4VTwistedFaceted::ComputeDimensions()",
00287               "GeomSolids0001", FatalException,
00288               "G4VTwistedFaceted does not support Parameterisation.");
00289 }

G4NURBS * G4VTwistedFaceted::CreateNURBS (  )  const [virtual]

Reimplemented from G4VSolid.

Definition at line 1131 of file G4VTwistedFaceted.cc.

01132 {
01133   G4double maxRad = std::sqrt( fDx*fDx + fDy*fDy);
01134 
01135   return new G4NURBStube(maxRad, maxRad, fDz); 
01136    // Tube for now!!!
01137 }

G4Polyhedron * G4VTwistedFaceted::CreatePolyhedron (  )  const [virtual]

Reimplemented from G4VSolid.

Definition at line 1334 of file G4VTwistedFaceted.cc.

References G4VTwistSurface::GetFacets(), and CLHEP::detail::n.

Referenced by GetPolyhedron().

01335 {
01336   // number of meshes
01337   const G4int k =
01338     G4int(G4Polyhedron::GetNumberOfRotationSteps() * fPhiTwist / twopi) + 2;
01339   const G4int n = k;
01340 
01341   const G4int nnodes = 4*(k-1)*(n-2) + 2*k*k ;
01342   const G4int nfaces = 4*(k-1)*(n-1) + 2*(k-1)*(k-1) ;
01343 
01344   G4Polyhedron *ph=new G4Polyhedron;
01345   typedef G4double G4double3[3];
01346   typedef G4int G4int4[4];
01347   G4double3* xyz = new G4double3[nnodes];  // number of nodes 
01348   G4int4*  faces = new G4int4[nfaces] ;    // number of faces
01349 
01350   fLowerEndcap->GetFacets(k,k,xyz,faces,0) ;
01351   fUpperEndcap->GetFacets(k,k,xyz,faces,1) ;
01352   fSide270->GetFacets(k,n,xyz,faces,2) ;
01353   fSide0->GetFacets(k,n,xyz,faces,3) ;
01354   fSide90->GetFacets(k,n,xyz,faces,4) ;
01355   fSide180->GetFacets(k,n,xyz,faces,5) ;
01356 
01357   ph->createPolyhedron(nnodes,nfaces,xyz,faces);
01358 
01359   return ph;
01360 }

G4ThreeVectorList * G4VTwistedFaceted::CreateRotatedVertices ( const G4AffineTransform pTransform  )  const [protected]

Definition at line 480 of file G4VTwistedFaceted.cc.

References G4VSolid::DumpInfo(), FatalException, G4Exception(), and G4AffineTransform::TransformPoint().

Referenced by CalculateExtent().

00481 {
00482 
00483   G4ThreeVectorList* vertices = new G4ThreeVectorList();
00484 
00485   if (vertices)
00486   {
00487     vertices->reserve(8);
00488 
00489     G4double maxRad = std::sqrt( fDx*fDx + fDy*fDy);
00490 
00491     G4ThreeVector vertex0(-maxRad,-maxRad,-fDz) ;
00492     G4ThreeVector vertex1(maxRad,-maxRad,-fDz) ;
00493     G4ThreeVector vertex2(maxRad,maxRad,-fDz) ;
00494     G4ThreeVector vertex3(-maxRad,maxRad,-fDz) ;
00495     G4ThreeVector vertex4(-maxRad,-maxRad,fDz) ;
00496     G4ThreeVector vertex5(maxRad,-maxRad,fDz) ;
00497     G4ThreeVector vertex6(maxRad,maxRad,fDz) ;
00498     G4ThreeVector vertex7(-maxRad,maxRad,fDz) ;
00499 
00500     vertices->push_back(pTransform.TransformPoint(vertex0));
00501     vertices->push_back(pTransform.TransformPoint(vertex1));
00502     vertices->push_back(pTransform.TransformPoint(vertex2));
00503     vertices->push_back(pTransform.TransformPoint(vertex3));
00504     vertices->push_back(pTransform.TransformPoint(vertex4));
00505     vertices->push_back(pTransform.TransformPoint(vertex5));
00506     vertices->push_back(pTransform.TransformPoint(vertex6));
00507     vertices->push_back(pTransform.TransformPoint(vertex7));
00508   }
00509   else
00510   {
00511     DumpInfo();
00512     G4Exception("G4VTwistedFaceted::CreateRotatedVertices()",
00513                 "GeomSolids0003", FatalException,
00514                 "Error in allocation of vertices. Out of memory !");
00515   }
00516   return vertices;
00517 }

void G4VTwistedFaceted::DescribeYourselfTo ( G4VGraphicsScene scene  )  const [virtual]

Implements G4VSolid.

Definition at line 1110 of file G4VTwistedFaceted.cc.

References G4VGraphicsScene::AddSolid().

01111 {
01112   scene.AddSolid (*this);
01113 }

G4double G4VTwistedFaceted::DistanceToIn ( const G4ThreeVector p  )  const [virtual]

Implements G4VSolid.

Definition at line 772 of file G4VTwistedFaceted.cc.

References FatalException, G4Exception(), Inside(), kInside, kOutside, and kSurface.

00773 {
00774    // DistanceToIn(p):
00775    // Calculate distance to surface of shape from `outside',
00776    // allowing for tolerance
00777    //
00778    
00779    //
00780    // checking last value
00781    //
00782    
00783    G4ThreeVector *tmpp;
00784    G4double      *tmpdist;
00785    if (fLastDistanceToIn.p == p)
00786    {
00787       return fLastDistanceToIn.value;
00788    }
00789    else
00790    {
00791       tmpp    = const_cast<G4ThreeVector*>(&(fLastDistanceToIn.p));
00792       tmpdist = const_cast<G4double*>(&(fLastDistanceToIn.value));
00793       tmpp->set(p.x(), p.y(), p.z());
00794    }
00795 
00796    //
00797    // Calculate DistanceToIn(p) 
00798    //
00799    
00800    EInside currentside = Inside(p);
00801 
00802    switch (currentside)
00803    {
00804       case (kInside) :
00805       {
00806       }
00807 
00808       case (kSurface) :
00809       {
00810          *tmpdist = 0.;
00811          return fLastDistanceToIn.value;
00812       }
00813 
00814       case (kOutside) :
00815       {
00816          // Initialize
00817          //
00818          G4double      distance = kInfinity;   
00819 
00820          // Find intersections and choose nearest one
00821          //
00822          G4VTwistSurface *surfaces[6];
00823 
00824          surfaces[0] = fSide0;
00825          surfaces[1] = fSide90 ;
00826          surfaces[2] = fSide180 ;
00827          surfaces[3] = fSide270 ;
00828          surfaces[4] = fLowerEndcap;
00829          surfaces[5] = fUpperEndcap;
00830 
00831          G4int i;
00832          G4ThreeVector xx;
00833          G4ThreeVector bestxx;
00834          for (i=0; i< 6; i++)
00835          {
00836             G4double tmpdistance = surfaces[i]->DistanceTo(p, xx);
00837             if (tmpdistance < distance)
00838             {
00839                distance = tmpdistance;
00840                bestxx = xx;
00841             }
00842          }
00843          *tmpdist = distance;
00844          return fLastDistanceToIn.value;
00845       }
00846 
00847       default :
00848       {
00849          G4Exception("G4VTwistedFaceted::DistanceToIn(p)", "GeomSolids0003",
00850                      FatalException, "Unknown point location!");
00851       }
00852    } // switch end
00853 
00854    return 0;
00855 }

G4double G4VTwistedFaceted::DistanceToIn ( const G4ThreeVector p,
const G4ThreeVector v 
) const [virtual]

Implements G4VSolid.

Definition at line 673 of file G4VTwistedFaceted.cc.

References G4VTwistSurface::DistanceToIn(), G4cout, G4endl, Inside(), kInside, kSurface, and SurfaceNormal().

00675 {
00676 
00677    // DistanceToIn (p, v):
00678    // Calculate distance to surface of shape from `outside' 
00679    // along with the v, allowing for tolerance.
00680    // The function returns kInfinity if no intersection or
00681    // just grazing within tolerance.
00682 
00683    //
00684    // checking last value
00685    //
00686    
00687    G4ThreeVector *tmpp;
00688    G4ThreeVector *tmpv;
00689    G4double      *tmpdist;
00690    if (fLastDistanceToInWithV.p == p && fLastDistanceToInWithV.vec == v)
00691    {
00692       return fLastDistanceToIn.value;
00693    }
00694    else
00695    {
00696       tmpp    = const_cast<G4ThreeVector*>(&(fLastDistanceToInWithV.p));
00697       tmpv    = const_cast<G4ThreeVector*>(&(fLastDistanceToInWithV.vec));
00698       tmpdist = const_cast<G4double*>(&(fLastDistanceToInWithV.value));
00699       tmpp->set(p.x(), p.y(), p.z());
00700       tmpv->set(v.x(), v.y(), v.z());
00701    }
00702 
00703    //
00704    // Calculate DistanceToIn(p,v)
00705    //
00706    
00707    EInside currentside = Inside(p);
00708 
00709    if (currentside == kInside)
00710    {
00711    }
00712    else if (currentside == kSurface)
00713    {
00714      // particle is just on a boundary.
00715      // if the particle is entering to the volume, return 0
00716      //
00717      G4ThreeVector normal = SurfaceNormal(p);
00718      if (normal*v < 0)
00719      {
00720        *tmpdist = 0;
00721        return fLastDistanceToInWithV.value;
00722      } 
00723    }
00724       
00725    // now, we can take smallest positive distance.
00726    
00727    // Initialize
00728    //
00729    G4double      distance = kInfinity;   
00730 
00731    // Find intersections and choose nearest one
00732    //
00733    G4VTwistSurface *surfaces[6];
00734 
00735    surfaces[0] = fSide0;
00736    surfaces[1] = fSide90 ;
00737    surfaces[2] = fSide180 ;
00738    surfaces[3] = fSide270 ;
00739    surfaces[4] = fLowerEndcap;
00740    surfaces[5] = fUpperEndcap;
00741    
00742    G4ThreeVector xx;
00743    G4ThreeVector bestxx;
00744    G4int i;
00745    for (i=0; i < 6 ; i++)
00746    {
00747 #ifdef G4TWISTDEBUG
00748       G4cout << G4endl << "surface " << i << ": " << G4endl << G4endl ;
00749 #endif
00750       G4double tmpdistance = surfaces[i]->DistanceToIn(p, v, xx);
00751 #ifdef G4TWISTDEBUG
00752       G4cout << "Solid DistanceToIn : distance = " << tmpdistance << G4endl ; 
00753       G4cout << "intersection point = " << xx << G4endl ;
00754 #endif 
00755       if (tmpdistance < distance)
00756       {
00757          distance = tmpdistance;
00758          bestxx = xx;
00759       }
00760    }
00761 
00762 #ifdef G4TWISTDEBUG
00763    G4cout << "best distance = " << distance << G4endl ;
00764 #endif
00765 
00766    *tmpdist = distance;
00767    // timer.Stop();
00768    return fLastDistanceToInWithV.value;
00769 }

G4double G4VTwistedFaceted::DistanceToOut ( const G4ThreeVector p  )  const [virtual]

Implements G4VSolid.

Definition at line 967 of file G4VTwistedFaceted.cc.

References G4VSolid::DumpInfo(), FatalException, G4cout, G4endl, G4Exception(), Inside(), JustWarning, kInside, kOutside, and kSurface.

00968 {
00969    // DistanceToOut(p):
00970    // Calculate distance to surface of shape from `inside', 
00971    // allowing for tolerance
00972 
00973    //
00974    // checking last value
00975    //
00976 
00977    G4ThreeVector *tmpp;
00978    G4double      *tmpdist;
00979 
00980    if (fLastDistanceToOut.p == p)
00981    {
00982       return fLastDistanceToOut.value;
00983    }
00984    else
00985    {
00986       tmpp    = const_cast<G4ThreeVector*>(&(fLastDistanceToOut.p));
00987       tmpdist = const_cast<G4double*>(&(fLastDistanceToOut.value));
00988       tmpp->set(p.x(), p.y(), p.z());
00989    }
00990    
00991    //
00992    // Calculate DistanceToOut(p)
00993    //
00994    
00995    EInside currentside = Inside(p);
00996    G4double     retval = kInfinity;   
00997 
00998    switch (currentside)
00999    {
01000       case (kOutside) :
01001       {
01002 #ifdef G4SPECSDEBUG
01003         G4int oldprc = G4cout.precision(16) ;
01004         G4cout << G4endl ;
01005         DumpInfo();
01006         G4cout << "Position:"  << G4endl << G4endl ;
01007         G4cout << "p.x() = "   << p.x()/mm << " mm" << G4endl ;
01008         G4cout << "p.y() = "   << p.y()/mm << " mm" << G4endl ;
01009         G4cout << "p.z() = "   << p.z()/mm << " mm" << G4endl << G4endl ;
01010         G4cout.precision(oldprc) ;
01011         G4Exception("G4VTwistedFaceted::DistanceToOut(p)", "GeomSolids1002",
01012                     JustWarning, "Point p is outside !?" );
01013 #endif
01014         break;
01015       }
01016       case (kSurface) :
01017       {
01018         *tmpdist = 0.;
01019         retval = fLastDistanceToOut.value;
01020         break;
01021       }
01022       
01023       case (kInside) :
01024       {
01025         // Initialize
01026         //
01027         G4double      distance = kInfinity;
01028    
01029         // find intersections and choose nearest one
01030         //
01031         G4VTwistSurface *surfaces[6];
01032 
01033         surfaces[0] = fSide0;
01034         surfaces[1] = fSide90 ;
01035         surfaces[2] = fSide180 ;
01036         surfaces[3] = fSide270 ;
01037         surfaces[4] = fLowerEndcap;
01038         surfaces[5] = fUpperEndcap;
01039 
01040         G4int i;
01041         G4ThreeVector xx;
01042         G4ThreeVector bestxx;
01043         for (i=0; i< 6; i++)
01044         {
01045           G4double tmpdistance = surfaces[i]->DistanceTo(p, xx);
01046           if (tmpdistance < distance)
01047           {
01048             distance = tmpdistance;
01049             bestxx = xx;
01050           }
01051         }
01052         *tmpdist = distance;
01053    
01054         retval = fLastDistanceToOut.value;
01055         break;
01056       }
01057       
01058       default :
01059       {
01060         G4Exception("G4VTwistedFaceted::DistanceToOut(p)", "GeomSolids0003",
01061                     FatalException, "Unknown point location!");
01062         break;
01063       }
01064    } // switch end
01065 
01066    return retval;
01067 }

G4double G4VTwistedFaceted::DistanceToOut ( const G4ThreeVector p,
const G4ThreeVector v,
const G4bool  calcnorm = false,
G4bool validnorm = 0,
G4ThreeVector n = 0 
) const [virtual]

Implements G4VSolid.

Definition at line 862 of file G4VTwistedFaceted.cc.

References G4VTwistSurface::GetNormal(), Inside(), G4VTwistSurface::IsValidNorm(), kOutside, kSurface, and SurfaceNormal().

00867 {
00868    // DistanceToOut (p, v):
00869    // Calculate distance to surface of shape from `inside'
00870    // along with the v, allowing for tolerance.
00871    // The function returns kInfinity if no intersection or
00872    // just grazing within tolerance.
00873 
00874    //
00875    // checking last value
00876    //
00877    
00878    G4ThreeVector *tmpp;
00879    G4ThreeVector *tmpv;
00880    G4double      *tmpdist;
00881    if (fLastDistanceToOutWithV.p == p && fLastDistanceToOutWithV.vec == v  )
00882    {
00883       return fLastDistanceToOutWithV.value;
00884    }
00885    else
00886    {
00887       tmpp    = const_cast<G4ThreeVector*>(&(fLastDistanceToOutWithV.p));
00888       tmpv    = const_cast<G4ThreeVector*>(&(fLastDistanceToOutWithV.vec));
00889       tmpdist = const_cast<G4double*>(&(fLastDistanceToOutWithV.value));
00890       tmpp->set(p.x(), p.y(), p.z());
00891       tmpv->set(v.x(), v.y(), v.z());
00892    }
00893 
00894    //
00895    // Calculate DistanceToOut(p,v)
00896    //
00897    
00898    EInside currentside = Inside(p);
00899 
00900    if (currentside == kOutside)
00901    {
00902    }
00903    else if (currentside == kSurface)
00904    {
00905       // particle is just on a boundary.
00906       // if the particle is exiting from the volume, return 0
00907       //
00908       G4ThreeVector normal = SurfaceNormal(p);
00909       G4VTwistSurface *blockedsurface = fLastNormal.surface[0];
00910       if (normal*v > 0)
00911       {
00912             if (calcNorm)
00913             {
00914                *norm = (blockedsurface->GetNormal(p, true));
00915                *validNorm = blockedsurface->IsValidNorm();
00916             }
00917             *tmpdist = 0.;
00918             // timer.Stop();
00919             return fLastDistanceToOutWithV.value;
00920       }
00921    }
00922       
00923    // now, we can take smallest positive distance.
00924    
00925    // Initialize
00926    G4double      distance = kInfinity;
00927        
00928    // find intersections and choose nearest one.
00929    G4VTwistSurface *surfaces[6];
00930 
00931    surfaces[0] = fSide0;
00932    surfaces[1] = fSide90 ;
00933    surfaces[2] = fSide180 ;
00934    surfaces[3] = fSide270 ;
00935    surfaces[4] = fLowerEndcap;
00936    surfaces[5] = fUpperEndcap;
00937 
00938    G4int i;
00939    G4int besti = -1;
00940    G4ThreeVector xx;
00941    G4ThreeVector bestxx;
00942    for (i=0; i< 6 ; i++) {
00943       G4double tmpdistance = surfaces[i]->DistanceToOut(p, v, xx);
00944       if (tmpdistance < distance)
00945       {
00946          distance = tmpdistance;
00947          bestxx = xx; 
00948          besti = i;
00949       }
00950    }
00951 
00952    if (calcNorm)
00953    {
00954       if (besti != -1)
00955       {
00956          *norm = (surfaces[besti]->GetNormal(p, true));
00957          *validNorm = surfaces[besti]->IsValidNorm();
00958       }
00959    }
00960 
00961    *tmpdist = distance;
00962    // timer.Stop();
00963    return fLastDistanceToOutWithV.value;
00964 }

G4double G4VTwistedFaceted::GetAlpha (  )  const [inline]

Definition at line 131 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrap::GetTiltAngleAlpha().

00131 { return fAlph  ; }

G4double G4VTwistedFaceted::GetCubicVolume (  )  [inline, virtual]

Reimplemented from G4VSolid.

Definition at line 313 of file G4VTwistedFaceted.hh.

00314 {
00315   if(fCubicVolume != 0.) ;
00316   else   fCubicVolume = 2 * fDz
00317                       * ( ( fDx1 + fDx2 ) * fDy1 + ( fDx3 + fDx4 ) * fDy2  );
00318   return fCubicVolume;
00319 }

G4double G4VTwistedFaceted::GetDx1 (  )  const [inline]

Definition at line 122 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetX1HalfLength(), G4TwistedTrap::GetX1HalfLength(), and G4TwistedBox::GetXHalfLength().

00122 { return fDx1   ; } 

G4double G4VTwistedFaceted::GetDx2 (  )  const [inline]

Definition at line 123 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrap::GetX2HalfLength().

00123 { return fDx2   ; } 

G4double G4VTwistedFaceted::GetDx3 (  )  const [inline]

Definition at line 124 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetX2HalfLength(), and G4TwistedTrap::GetX3HalfLength().

00124 { return fDx3   ; } 

G4double G4VTwistedFaceted::GetDx4 (  )  const [inline]

Definition at line 125 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrap::GetX4HalfLength().

00125 { return fDx4   ; } 

G4double G4VTwistedFaceted::GetDy1 (  )  const [inline]

Definition at line 126 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetY1HalfLength(), G4TwistedTrap::GetY1HalfLength(), and G4TwistedBox::GetYHalfLength().

00126 { return fDy1   ; } 

G4double G4VTwistedFaceted::GetDy2 (  )  const [inline]

Definition at line 127 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetY2HalfLength(), and G4TwistedTrap::GetY2HalfLength().

00127 { return fDy2   ; } 

G4double G4VTwistedFaceted::GetDz (  )  const [inline]

Definition at line 128 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetZHalfLength(), G4TwistedTrap::GetZHalfLength(), and G4TwistedBox::GetZHalfLength().

00128 { return fDz    ; }

G4GeometryType G4VTwistedFaceted::GetEntityType (  )  const [virtual]

Implements G4VSolid.

Reimplemented in G4TwistedBox, G4TwistedTrap, and G4TwistedTrd.

Definition at line 1192 of file G4VTwistedFaceted.cc.

01193 {
01194   return G4String("G4VTwistedFaceted");
01195 }

G4VisExtent G4VTwistedFaceted::GetExtent (  )  const [virtual]

Reimplemented from G4VSolid.

Definition at line 1118 of file G4VTwistedFaceted.cc.

01119 {
01120   G4double maxRad = std::sqrt( fDx*fDx + fDy*fDy);
01121 
01122   return G4VisExtent(-maxRad, maxRad ,
01123                      -maxRad, maxRad ,
01124                      -fDz, fDz );
01125 }

G4double G4VTwistedFaceted::GetPhi (  )  const [inline]

Definition at line 129 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrap::GetAzimuthalAnglePhi().

00129 { return fPhi   ; }

G4ThreeVector G4VTwistedFaceted::GetPointInSolid ( G4double  z  )  const

Definition at line 1218 of file G4VTwistedFaceted.cc.

01219 {
01220 
01221 
01222   // this routine is only used for a test
01223   // can be deleted ...
01224 
01225   if ( z == fDz ) z -= 0.1*fDz ;
01226   if ( z == -fDz ) z += 0.1*fDz ;
01227 
01228   G4double phi = z/(2*fDz)*fPhiTwist ;
01229 
01230   return G4ThreeVector(fdeltaX * phi/fPhiTwist, fdeltaY * phi/fPhiTwist, z ) ;
01231 }

G4ThreeVector G4VTwistedFaceted::GetPointOnSurface (  )  const [virtual]

Reimplemented from G4VSolid.

Definition at line 1237 of file G4VTwistedFaceted.cc.

References G4cout, G4endl, G4VTwistSurface::GetBoundaryMax(), G4VTwistSurface::GetBoundaryMin(), G4VTwistSurface::GetSurfaceArea(), and G4VTwistSurface::SurfacePoint().

01238 {
01239 
01240   G4double  phi = G4RandFlat::shoot(-fPhiTwist/2.,fPhiTwist/2.);
01241   G4double u , umin, umax ;  //  variable for twisted surfaces
01242   G4double y  ;              //  variable for flat surface (top and bottom)
01243 
01244   // Compute the areas. Attention: Only correct for trapezoids
01245   // where the twisting is done along the z-axis. In the general case
01246   // the computed surface area is more difficult. However this simplification
01247   // does not affect the tracking through the solid. 
01248  
01249   G4double a1   = fSide0->GetSurfaceArea();
01250   G4double a2   = fSide90->GetSurfaceArea();
01251   G4double a3   = fSide180->GetSurfaceArea() ;
01252   G4double a4   = fSide270->GetSurfaceArea() ;
01253   G4double a5   = fLowerEndcap->GetSurfaceArea() ;
01254   G4double a6   = fUpperEndcap->GetSurfaceArea() ;
01255 
01256 #ifdef G4TWISTDEBUG
01257   G4cout << "Surface 0   deg = " << a1 << G4endl ;
01258   G4cout << "Surface 90  deg = " << a2 << G4endl ;
01259   G4cout << "Surface 180 deg = " << a3 << G4endl ;
01260   G4cout << "Surface 270 deg = " << a4 << G4endl ;
01261   G4cout << "Surface Lower   = " << a5 << G4endl ;
01262   G4cout << "Surface Upper   = " << a6 << G4endl ;
01263 #endif 
01264 
01265   G4double chose = G4RandFlat::shoot(0.,a1 + a2 + a3 + a4 + a5 + a6) ;
01266 
01267   if(chose < a1)
01268   {
01269 
01270     umin = fSide0->GetBoundaryMin(phi) ;
01271     umax = fSide0->GetBoundaryMax(phi) ;
01272     u = G4RandFlat::shoot(umin,umax) ;
01273 
01274     return  fSide0->SurfacePoint(phi, u, true) ;   // point on 0deg surface
01275   }
01276 
01277   else if( (chose >= a1) && (chose < a1 + a2 ) )
01278   {
01279 
01280     umin = fSide90->GetBoundaryMin(phi) ;
01281     umax = fSide90->GetBoundaryMax(phi) ;
01282     
01283     u = G4RandFlat::shoot(umin,umax) ;
01284 
01285     return fSide90->SurfacePoint(phi, u, true);   // point on 90deg surface
01286   }
01287 
01288   else if( (chose >= a1 + a2 ) && (chose < a1 + a2 + a3 ) )
01289   {
01290 
01291     umin = fSide180->GetBoundaryMin(phi) ;
01292     umax = fSide180->GetBoundaryMax(phi) ;
01293     u = G4RandFlat::shoot(umin,umax) ;
01294 
01295      return fSide180->SurfacePoint(phi, u, true); // point on 180 deg surface
01296   }
01297 
01298   else if( (chose >= a1 + a2 + a3  ) && (chose < a1 + a2 + a3 + a4  ) )
01299   {
01300 
01301     umin = fSide270->GetBoundaryMin(phi) ;
01302     umax = fSide270->GetBoundaryMax(phi) ;
01303     u = G4RandFlat::shoot(umin,umax) ;
01304 
01305     return fSide270->SurfacePoint(phi, u, true); // point on 270 deg surface
01306   }
01307 
01308   else if( (chose >= a1 + a2 + a3 + a4  ) && (chose < a1 + a2 + a3 + a4 + a5 ) )
01309   {
01310 
01311     y = G4RandFlat::shoot(-fDy1,fDy1) ;
01312     umin = fLowerEndcap->GetBoundaryMin(y) ;
01313     umax = fLowerEndcap->GetBoundaryMax(y) ;
01314     u = G4RandFlat::shoot(umin,umax) ;
01315 
01316     return fLowerEndcap->SurfacePoint(u,y,true); // point on lower endcap
01317   }
01318   else {
01319 
01320     y = G4RandFlat::shoot(-fDy2,fDy2) ;
01321     umin = fUpperEndcap->GetBoundaryMin(y) ;
01322     umax = fUpperEndcap->GetBoundaryMax(y) ;
01323     u = G4RandFlat::shoot(umin,umax) ;
01324 
01325     return fUpperEndcap->SurfacePoint(u,y,true) ; // point on upper endcap
01326 
01327   }
01328 }

G4Polyhedron * G4VTwistedFaceted::GetPolyhedron (  )  const [virtual]

Reimplemented from G4VSolid.

Definition at line 1201 of file G4VTwistedFaceted.cc.

References CreatePolyhedron(), and G4Polyhedron::GetNumberOfRotationStepsAtTimeOfCreation().

01202 {
01203   if (!fpPolyhedron ||
01204       fpPolyhedron->GetNumberOfRotationStepsAtTimeOfCreation() !=
01205       fpPolyhedron->GetNumberOfRotationSteps())
01206     {
01207       delete fpPolyhedron;
01208       fpPolyhedron = CreatePolyhedron();
01209     }
01210 
01211   return fpPolyhedron;
01212 }

G4double G4VTwistedFaceted::GetSurfaceArea (  )  [inline, virtual]

Reimplemented from G4VSolid.

Definition at line 322 of file G4VTwistedFaceted.hh.

References G4VSolid::GetSurfaceArea().

00323 {
00324   if(fSurfaceArea != 0.) ;
00325   else   fSurfaceArea = G4VSolid::GetSurfaceArea();
00326   return fSurfaceArea;
00327 }

G4double G4VTwistedFaceted::GetTheta (  )  const [inline]

Definition at line 130 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrap::GetPolarAngleTheta().

00130 { return fTheta ; }

G4double G4VTwistedFaceted::GetTwistAngle (  )  const [inline]

Definition at line 120 of file G4VTwistedFaceted.hh.

Referenced by G4TwistedTrd::GetPhiTwist(), G4TwistedTrap::GetPhiTwist(), and G4TwistedBox::GetPhiTwist().

00120 { return fPhiTwist; }

G4double G4VTwistedFaceted::GetValueA ( G4double  phi  )  const [inline]

Definition at line 330 of file G4VTwistedFaceted.hh.

Referenced by Xcoef().

00331 {
00332   return ( fDx4 + fDx2  + ( fDx4 - fDx2 ) * ( 2 * phi ) / fPhiTwist  ) ;
00333 }

G4double G4VTwistedFaceted::GetValueB ( G4double  phi  )  const [inline]

Definition at line 342 of file G4VTwistedFaceted.hh.

Referenced by Inside(), and Xcoef().

00343 {
00344   return ( fDy2 + fDy1  + ( fDy2 - fDy1 ) * ( 2 * phi ) / fPhiTwist ) ;
00345 }

G4double G4VTwistedFaceted::GetValueD ( G4double  phi  )  const [inline]

Definition at line 336 of file G4VTwistedFaceted.hh.

Referenced by Xcoef().

00337 {
00338   return ( fDx3 + fDx1  + ( fDx3 - fDx1 ) * ( 2 * phi ) / fPhiTwist  ) ;
00339 } 

EInside G4VTwistedFaceted::Inside ( const G4ThreeVector p  )  const [virtual]

Implements G4VSolid.

Definition at line 522 of file G4VTwistedFaceted.cc.

References G4cout, G4endl, GetValueB(), G4VSolid::kCarTolerance, kInside, kOutside, kSurface, and Xcoef().

Referenced by CalculateExtent(), DistanceToIn(), and DistanceToOut().

00523 {
00524 
00525    G4ThreeVector *tmpp;
00526    EInside       *tmpin;
00527    if (fLastInside.p == p) {
00528      return fLastInside.inside;
00529    } else {
00530       tmpp      = const_cast<G4ThreeVector*>(&(fLastInside.p));
00531       tmpin     = const_cast<EInside*>(&(fLastInside.inside));
00532       tmpp->set(p.x(), p.y(), p.z());
00533    }
00534 
00535    *tmpin = kOutside ;
00536 
00537    G4double phi = p.z()/(2*fDz) * fPhiTwist ;  // rotate the point to z=0
00538    G4double cphi = std::cos(-phi) ;
00539    G4double sphi = std::sin(-phi) ;
00540 
00541    G4double px  = p.x() + fdeltaX * ( -phi/fPhiTwist) ;  // shift
00542    G4double py  = p.y() + fdeltaY * ( -phi/fPhiTwist) ;
00543    G4double pz  = p.z() ;
00544 
00545    G4double posx = px * cphi - py * sphi   ;  // rotation
00546    G4double posy = px * sphi + py * cphi   ;
00547    G4double posz = pz  ;
00548 
00549    G4double xMin = Xcoef(posy,phi,fTAlph) - 2*Xcoef(posy,phi,0.) ; 
00550    G4double xMax = Xcoef(posy,phi,fTAlph) ;  
00551 
00552    G4double yMax = GetValueB(phi)/2. ;  // b(phi)/2 is limit
00553    G4double yMin = -yMax ;
00554 
00555 #ifdef G4TWISTDEBUG
00556 
00557    G4cout << "inside called: p = " << p << G4endl ; 
00558    G4cout << "fDx1 = " << fDx1 << G4endl ;
00559    G4cout << "fDx2 = " << fDx2 << G4endl ;
00560    G4cout << "fDx3 = " << fDx3 << G4endl ;
00561    G4cout << "fDx4 = " << fDx4 << G4endl ;
00562 
00563    G4cout << "fDy1 = " << fDy1 << G4endl ;
00564    G4cout << "fDy2 = " << fDy2 << G4endl ;
00565 
00566    G4cout << "fDz  = " << fDz  << G4endl ;
00567 
00568    G4cout << "Tilt angle alpha = " << fAlph << G4endl ;
00569    G4cout << "phi,theta = " << fPhi << " , " << fTheta << G4endl ;
00570 
00571    G4cout << "Twist angle = " << fPhiTwist << G4endl ;
00572 
00573    G4cout << "posx = " << posx << G4endl ;
00574    G4cout << "posy = " << posy << G4endl ;
00575    G4cout << "xMin = " << xMin << G4endl ;
00576    G4cout << "xMax = " << xMax << G4endl ;
00577    G4cout << "yMin = " << yMin << G4endl ;
00578    G4cout << "yMax = " << yMax << G4endl ;
00579 
00580 #endif 
00581 
00582 
00583   if ( posx <= xMax - kCarTolerance*0.5
00584     && posx >= xMin + kCarTolerance*0.5 )
00585   {
00586     if ( posy <= yMax - kCarTolerance*0.5
00587       && posy >= yMin + kCarTolerance*0.5 )
00588     {
00589       if      (std::fabs(posz) <= fDz - kCarTolerance*0.5 ) *tmpin = kInside ;
00590       else if (std::fabs(posz) <= fDz + kCarTolerance*0.5 ) *tmpin = kSurface ;
00591     }
00592     else if ( posy <= yMax + kCarTolerance*0.5
00593            && posy >= yMin - kCarTolerance*0.5 )
00594     {
00595       if (std::fabs(posz) <= fDz + kCarTolerance*0.5 ) *tmpin = kSurface ;
00596     }
00597   }
00598   else if ( posx <= xMax + kCarTolerance*0.5
00599          && posx >= xMin - kCarTolerance*0.5 )
00600   {
00601     if ( posy <= yMax + kCarTolerance*0.5
00602       && posy >= yMin - kCarTolerance*0.5 )
00603     {
00604       if (std::fabs(posz) <= fDz + kCarTolerance*0.5) *tmpin = kSurface ;
00605     }
00606   }
00607 
00608 #ifdef G4TWISTDEBUG
00609   G4cout << "inside = " << fLastInside.inside << G4endl ;
00610 #endif
00611 
00612   return fLastInside.inside;
00613 
00614 }

G4VTwistedFaceted & G4VTwistedFaceted::operator= ( const G4VTwistedFaceted rhs  ) 

Definition at line 248 of file G4VTwistedFaceted.cc.

References fAlph, fCubicVolume, fdeltaX, fdeltaY, fDx, fDx1, fDx2, fDx3, fDx4, fDy, fDy1, fDy2, fDz, fLastDistanceToIn, fLastDistanceToInWithV, fLastDistanceToOut, fLastDistanceToOutWithV, fLastInside, fLastNormal, fPhi, fPhiTwist, fSurfaceArea, fTAlph, fTheta, and G4VSolid::operator=().

Referenced by G4TwistedTrd::operator=(), G4TwistedTrap::operator=(), and G4TwistedBox::operator=().

00249 {
00250    // Check assignment to self
00251    //
00252    if (this == &rhs)  { return *this; }
00253 
00254    // Copy base class data
00255    //
00256    G4VSolid::operator=(rhs);
00257 
00258    // Copy data
00259    //
00260    fTheta = rhs.fTheta; fPhi = rhs.fPhi;
00261    fDy1= rhs.fDy1; fDx1= rhs.fDx1; fDx2= rhs.fDx2; fDy2= rhs.fDy2;
00262    fDx3= rhs.fDx3; fDx4= rhs.fDx4; fDz= rhs.fDz; fDx= rhs.fDx; fDy= rhs.fDy;
00263    fAlph= rhs.fAlph; fTAlph= rhs.fTAlph; fdeltaX= rhs.fdeltaX;
00264    fdeltaY= rhs.fdeltaY; fPhiTwist= rhs.fPhiTwist; fLowerEndcap= 0;
00265    fUpperEndcap= 0; fSide0= 0; fSide90= 0; fSide180= 0; fSide270= 0;
00266    fCubicVolume= rhs.fCubicVolume; fSurfaceArea= rhs.fSurfaceArea;
00267    fpPolyhedron= 0;
00268    fLastInside= rhs.fLastInside; fLastNormal= rhs.fLastNormal;
00269    fLastDistanceToIn= rhs.fLastDistanceToIn;
00270    fLastDistanceToOut= rhs.fLastDistanceToOut;
00271    fLastDistanceToInWithV= rhs.fLastDistanceToInWithV;
00272    fLastDistanceToOutWithV= rhs.fLastDistanceToOutWithV;
00273  
00274    CreateSurfaces();
00275 
00276    return *this;
00277 }

std::ostream & G4VTwistedFaceted::StreamInfo ( std::ostream &  os  )  const [virtual]

Implements G4VSolid.

Reimplemented in G4TwistedBox, G4TwistedTrap, and G4TwistedTrd.

Definition at line 1073 of file G4VTwistedFaceted.cc.

References G4endl, and G4VSolid::GetName().

01074 {
01075   //
01076   // Stream object contents to an output stream
01077   //
01078   G4int oldprc = os.precision(16);
01079   os << "-----------------------------------------------------------\n"
01080      << "    *** Dump for solid - " << GetName() << " ***\n"
01081      << "    ===================================================\n"
01082      << " Solid type: G4VTwistedFaceted\n"
01083      << " Parameters: \n"
01084      << "  polar angle theta = "   <<  fTheta/degree      << " deg" << G4endl
01085      << "  azimuthal angle phi = "  << fPhi/degree        << " deg" << G4endl  
01086      << "  tilt angle  alpha = "   << fAlph/degree        << " deg" << G4endl  
01087      << "  TWIST angle = "         << fPhiTwist/degree    << " deg" << G4endl  
01088      << "  Half length along y (lower endcap) = "         << fDy1/cm << " cm"
01089      << G4endl 
01090      << "  Half length along x (lower endcap, bottom) = " << fDx1/cm << " cm"
01091      << G4endl 
01092      << "  Half length along x (lower endcap, top) = "    << fDx2/cm << " cm"
01093      << G4endl 
01094      << "  Half length along y (upper endcap) = "         << fDy2/cm << " cm"
01095      << G4endl 
01096      << "  Half length along x (upper endcap, bottom) = " << fDx3/cm << " cm"
01097      << G4endl 
01098      << "  Half length along x (upper endcap, top) = "    << fDx4/cm << " cm"
01099      << G4endl 
01100      << "-----------------------------------------------------------\n";
01101   os.precision(oldprc);
01102 
01103   return os;
01104 }

G4ThreeVector G4VTwistedFaceted::SurfaceNormal ( const G4ThreeVector p  )  const [virtual]

Implements G4VSolid.

Definition at line 619 of file G4VTwistedFaceted.cc.

References G4VTwistSurface::GetNormal().

Referenced by DistanceToIn(), and DistanceToOut().

00620 {
00621    //
00622    // return the normal unit vector to the Hyperbolical Surface at a point 
00623    // p on (or nearly on) the surface
00624    //
00625    // Which of the three or four surfaces are we closest to?
00626    //
00627 
00628    if (fLastNormal.p == p)
00629    {
00630      return fLastNormal.vec;
00631    } 
00632    
00633    G4ThreeVector *tmpp       = const_cast<G4ThreeVector*>(&(fLastNormal.p));
00634    G4ThreeVector *tmpnormal  = const_cast<G4ThreeVector*>(&(fLastNormal.vec));
00635    G4VTwistSurface    **tmpsurface = const_cast<G4VTwistSurface**>(fLastNormal.surface);
00636    tmpp->set(p.x(), p.y(), p.z());
00637 
00638    G4double      distance = kInfinity;
00639 
00640    G4VTwistSurface *surfaces[6];
00641 
00642    surfaces[0] = fSide0 ;
00643    surfaces[1] = fSide90 ;
00644    surfaces[2] = fSide180 ;
00645    surfaces[3] = fSide270 ;
00646    surfaces[4] = fLowerEndcap;
00647    surfaces[5] = fUpperEndcap;
00648 
00649    G4ThreeVector xx;
00650    G4ThreeVector bestxx;
00651    G4int i;
00652    G4int besti = -1;
00653    for (i=0; i< 6; i++)
00654    {
00655       G4double tmpdistance = surfaces[i]->DistanceTo(p, xx);
00656       if (tmpdistance < distance)
00657       {
00658          distance = tmpdistance;
00659          bestxx = xx;
00660          besti = i; 
00661       }
00662    }
00663 
00664    tmpsurface[0] = surfaces[besti];
00665    *tmpnormal = tmpsurface[0]->GetNormal(bestxx, true);
00666    
00667    return fLastNormal.vec;
00668 }

G4double G4VTwistedFaceted::Xcoef ( G4double  u,
G4double  phi,
G4double  ftg 
) const [inline]

Definition at line 348 of file G4VTwistedFaceted.hh.

References GetValueA(), GetValueB(), and GetValueD().

Referenced by Inside().

00349 {
00350   return GetValueA(phi)/2. + (GetValueD(phi)-GetValueA(phi))/4. 
00351     - u*( ( GetValueD(phi)-GetValueA(phi) ) / ( 2 * GetValueB(phi) ) - ftg );
00352 }


The documentation for this class was generated from the following files:
Generated on Mon May 27 17:53:57 2013 for Geant4 by  doxygen 1.4.7