G4TwistedTubs.hh

Go to the documentation of this file.
00001 //
00002 // ********************************************************************
00003 // * License and Disclaimer                                           *
00004 // *                                                                  *
00005 // * The  Geant4 software  is  copyright of the Copyright Holders  of *
00006 // * the Geant4 Collaboration.  It is provided  under  the terms  and *
00007 // * conditions of the Geant4 Software License,  included in the file *
00008 // * LICENSE and available at  http://cern.ch/geant4/license .  These *
00009 // * include a list of copyright holders.                             *
00010 // *                                                                  *
00011 // * Neither the authors of this software system, nor their employing *
00012 // * institutes,nor the agencies providing financial support for this *
00013 // * work  make  any representation or  warranty, express or implied, *
00014 // * regarding  this  software system or assume any liability for its *
00015 // * use.  Please see the license in the file  LICENSE  and URL above *
00016 // * for the full disclaimer and the limitation of liability.         *
00017 // *                                                                  *
00018 // * This  code  implementation is the result of  the  scientific and *
00019 // * technical work of the GEANT4 collaboration.                      *
00020 // * By using,  copying,  modifying or  distributing the software (or *
00021 // * any work based  on the software)  you  agree  to acknowledge its *
00022 // * use  in  resulting  scientific  publications,  and indicate your *
00023 // * acceptance of all terms of the Geant4 Software license.          *
00024 // ********************************************************************
00025 //
00026 //
00027 // $Id: G4TwistedTubs.hh 67011 2013-01-29 16:17:41Z gcosmo $
00028 //
00029 // 
00030 // --------------------------------------------------------------------
00031 // GEANT 4 class header file
00032 //
00033 //
00034 // G4TwistedTubs
00035 //
00036 // Class description:
00037 //
00038 //  G4TwistedTubs is a sort of twisted cylinder.
00039 //  A twisted cylinder which is placed along with z-axis and is
00040 //  separated into phi-segments should become a hyperboloid, and
00041 //  its each segmented piece should be tilted with a stereo angle. 
00042 //  G4TwistedTubs is a G4VSolid.
00043 //  It can have inner & outer surfaces as well as G4TwistedTubs, 
00044 //  but cannot has different stereo angles between the inner surface
00045 //  and outer surface.
00046 
00047 // Author: 
00048 //   01-Aug-2002 - Kotoyo Hoshina (hoshina@hepburn.s.chiba-u.ac.jp)
00049 //
00050 // History:
00051 //   13-Nov-2003 - O.Link (Oliver.Link@cern.ch), Integration in Geant4
00052 //                 from original version in Jupiter-2.5.02 application.
00053 // --------------------------------------------------------------------
00054 #ifndef __G4TWISTEDTUBS__
00055 #define __G4TWISTEDTUBS__
00056 
00057 #include "G4VSolid.hh"
00058 #include "G4TwistTubsFlatSide.hh"
00059 #include "G4TwistTubsSide.hh"
00060 #include "G4TwistTubsHypeSide.hh"
00061 
00062 class G4SolidExtentList;
00063 class G4ClippablePolygon;
00064 
00065 class G4TwistedTubs : public G4VSolid
00066 {
00067  public:  // with description
00068  
00069   G4TwistedTubs(const G4String &pname,         // Name of instance
00070                       G4double  twistedangle,  // Twisted angle
00071                       G4double  endinnerrad,   // Inner radius at endcap 
00072                       G4double  endouterrad,   // Outer radius at endcap 
00073                       G4double  halfzlen,      // half z length 
00074                       G4double  dphi);         // Phi angle of a segment
00075                       
00076   G4TwistedTubs(const G4String &pname,         // Name of instance
00077                       G4double  twistedangle,  // Stereo angle
00078                       G4double  endinnerrad,   // Inner radius at endcap 
00079                       G4double  endouterrad,   // Outer radius at endcap 
00080                       G4double  halfzlen,      // half z length 
00081                       G4int     nseg,          // Number of segments in totalPhi
00082                       G4double  totphi);       // Total angle of all segments
00083                       
00084   G4TwistedTubs(const G4String &pname,         // Name of instance
00085                       G4double  twistedangle,  // Twisted angle
00086                       G4double  innerrad,      // Inner radius at z=0 
00087                       G4double  outerrad,      // Outer radius at z=0 
00088                       G4double  negativeEndz,  // -ve z endplate
00089                       G4double  positiveEndz,  // +ve z endplate
00090                       G4double  dphi);         // Phi angle of a segment
00091 
00092   G4TwistedTubs(const G4String &pname,         // Name of instance
00093                       G4double  twistedangle,  // Stereo angle
00094                       G4double  innerrad,      // Inner radius at z=0 
00095                       G4double  outerrad,      // Outer radius at z=0 
00096                       G4double  negativeEndz,  // -ve z endplate
00097                       G4double  positiveEndz,  // +ve z endplate
00098                       G4int     nseg,          // Number of segments in totalPhi
00099                       G4double  totphi);       // Total angle of all segments
00100 
00101   virtual ~G4TwistedTubs();
00102              
00103   void ComputeDimensions(G4VPVParameterisation   *  /* p  */ ,
00104                          const G4int                /* n  */ ,
00105                          const G4VPhysicalVolume *  /* prep */ );
00106  
00107   G4bool CalculateExtent(const EAxis               paxis,
00108                          const G4VoxelLimits      &pvoxellimit,
00109                          const G4AffineTransform  &ptransform,
00110                                G4double           &pmin,
00111                                G4double           &pmax ) const;
00112 
00113   G4double DistanceToIn (const G4ThreeVector &p,
00114                          const G4ThreeVector &v ) const;
00115 
00116   G4double DistanceToIn (const G4ThreeVector &p ) const;
00117    
00118   G4double DistanceToOut(const G4ThreeVector &p, 
00119                          const G4ThreeVector &v,
00120                          const G4bool         calcnorm=G4bool(false),
00121                                G4bool        *validnorm=0, 
00122                                G4ThreeVector *n=0 ) const;
00123 
00124   G4double DistanceToOut(const G4ThreeVector &p) const;
00125   
00126   EInside Inside (const G4ThreeVector &p) const;
00127 
00128   G4ThreeVector SurfaceNormal(const G4ThreeVector &p) const;
00129 
00130   void            DescribeYourselfTo (G4VGraphicsScene &scene) const;
00131   G4Polyhedron   *CreatePolyhedron   () const;
00132   G4NURBS        *CreateNURBS        () const;
00133   G4Polyhedron   *GetPolyhedron      () const;
00134 
00135   std::ostream &StreamInfo(std::ostream& os) const;
00136 
00137   // accessors
00138   
00139   inline G4double GetDPhi        () const { return fDPhi       ; }
00140   inline G4double GetPhiTwist    () const { return fPhiTwist   ; }
00141   inline G4double GetInnerRadius () const { return fInnerRadius; }
00142   inline G4double GetOuterRadius () const { return fOuterRadius; }
00143   inline G4double GetInnerStereo () const { return fInnerStereo; }
00144   inline G4double GetOuterStereo () const { return fOuterStereo; }
00145   inline G4double GetZHalfLength () const { return fZHalfLength; }
00146   inline G4double GetKappa       () const { return fKappa      ; }
00147 
00148   inline G4double GetTanInnerStereo () const { return fTanInnerStereo  ; }
00149   inline G4double GetTanInnerStereo2() const { return fTanInnerStereo2 ; }
00150   inline G4double GetTanOuterStereo () const { return fTanOuterStereo  ; }
00151   inline G4double GetTanOuterStereo2() const { return fTanOuterStereo2 ; }
00152   
00153   inline G4double GetEndZ           (G4int i) const { return fEndZ[i]  ; }
00154   inline G4double GetEndPhi         (G4int i) const { return fEndPhi[i]; }
00155   inline G4double GetEndInnerRadius (G4int i) const
00156                   { return fEndInnerRadius[i]; }
00157   inline G4double GetEndOuterRadius (G4int i) const
00158                   { return fEndOuterRadius[i]; }
00159   inline G4double GetEndInnerRadius () const 
00160                   { return (fEndInnerRadius[0] > fEndInnerRadius[1] ?
00161                     fEndInnerRadius[0] : fEndInnerRadius[1]); }
00162   inline G4double GetEndOuterRadius () const
00163                   { return (fEndOuterRadius[0] > fEndOuterRadius[1] ?
00164                     fEndOuterRadius[0] : fEndOuterRadius[1]); }
00165   
00166   G4VisExtent     GetExtent    () const;
00167   G4GeometryType  GetEntityType() const;
00168   G4VSolid* Clone() const;
00169 
00170   G4double GetCubicVolume();
00171     // Returns an estimation of the geometrical cubic volume of the
00172     // solid. Caches the computed value once computed the first time.
00173   G4double GetSurfaceArea();
00174     // Returns an estimation of the geometrical surface area of the
00175     // solid. Caches the computed value once computed the first time.
00176 
00177   G4ThreeVector GetPointOnSurface() const ;
00178 
00179  public:  // without description
00180 
00181   G4TwistedTubs(__void__&);
00182     // Fake default constructor for usage restricted to direct object
00183     // persistency for clients requiring preallocation of memory for
00184     // persistifiable objects.
00185 
00186   G4TwistedTubs(const G4TwistedTubs& rhs);
00187   G4TwistedTubs& operator=(const G4TwistedTubs& rhs); 
00188     // Copy constructor and assignment operator.
00189 
00190 #ifdef G4TWISTDEBUG
00191   G4VTwistSurface * GetOuterHype() const { return fOuterHype; }
00192 #endif
00193   
00194  private:
00195  
00196   inline void  SetFields(G4double phitwist, G4double innerrad,
00197                          G4double outerrad,
00198                          G4double negativeEndz, G4double positiveEndz);
00199                      
00200   void         CreateSurfaces();
00201 
00202   static void  AddPolyToExtent( const G4ThreeVector     &v0,
00203                                 const G4ThreeVector     &v1,
00204                                 const G4ThreeVector     &w1,
00205                                 const G4ThreeVector     &w0,
00206                                 const G4VoxelLimits     &voxellimit,
00207                                 const EAxis              axis,
00208                                       G4SolidExtentList &extentlist );
00209  private:
00210  
00211   G4double fPhiTwist;       // Twist angle from -fZHalfLength to fZHalfLength
00212   G4double fInnerRadius;    // Inner-hype radius at z=0
00213   G4double fOuterRadius;    // Outer-hype radius at z=0
00214   G4double fEndZ[2];        // z at endcaps, [0] = -ve z, [1] = +ve z
00215   G4double fDPhi;           // Phi-width of a segment fDPhi > 0
00216   G4double fZHalfLength;    // Half length along z-axis
00217  
00218   G4double fInnerStereo;       // Inner-hype stereo angle
00219   G4double fOuterStereo;       // Outer-hype stereo angle
00220   G4double fTanInnerStereo;    // std::tan(innerStereoAngle)
00221   G4double fTanOuterStereo;    // std::tan(outerStereoAngle)
00222   G4double fKappa;             // std::tan(fPhiTwist/2)/fZHalfLen;
00223   G4double fEndInnerRadius[2]; // Inner-hype radii endcaps [0] -ve z, [1] +ve z
00224   G4double fEndOuterRadius[2]; // Outer-hype radii endcaps [0] -ve z, [1] +ve z
00225   G4double fEndPhi[2];         // Phi endcaps, [0] = -ve z, [1] = +ve z
00226   
00227   G4double fInnerRadius2;      // fInnerRadius * fInnerRadius
00228   G4double fOuterRadius2;      // fOuterRadius * fOuterRadius
00229   G4double fTanInnerStereo2;   // fInnerRadius * fInnerRadius
00230   G4double fTanOuterStereo2;   // fInnerRadius * fInnerRadius
00231   G4double fEndZ2[2];          // fEndZ * fEndZ
00232   
00233   G4VTwistSurface *fLowerEndcap;    // Surface of -ve z
00234   G4VTwistSurface *fUpperEndcap;    // Surface of +ve z
00235   G4VTwistSurface *fLatterTwisted;  // Surface of -ve phi
00236   G4VTwistSurface *fFormerTwisted;  // Surface of +ve phi
00237   G4VTwistSurface *fInnerHype;      // Surface of -ve r
00238   G4VTwistSurface *fOuterHype;      // Surface of +ve r
00239 
00240   G4double fCubicVolume;       // Cached value for cubic volume
00241   G4double fSurfaceArea;       // Cached value for surface area
00242 
00243   mutable G4Polyhedron* fpPolyhedron;  // pointer to polyhedron for vis
00244 
00245   class LastState              // last Inside result
00246   {
00247     public:
00248       LastState()
00249       {
00250         p.set(kInfinity,kInfinity,kInfinity);
00251         inside = kOutside;
00252       }
00253       ~LastState(){}
00254       LastState(const LastState& r) : p(r.p), inside(r.inside){}
00255       LastState& operator=(const LastState& r)
00256       {
00257         if (this == &r)  { return *this; }
00258         p = r.p; inside = r.inside;
00259         return *this;
00260       }
00261     public:
00262       G4ThreeVector p;
00263       EInside       inside;
00264   };
00265               
00266   class LastVector             // last SurfaceNormal result
00267   {
00268     public:
00269       LastVector()
00270       {
00271         p.set(kInfinity,kInfinity,kInfinity);
00272         vec.set(kInfinity,kInfinity,kInfinity);
00273         surface = new G4VTwistSurface*[1];
00274       }
00275       ~LastVector()
00276       {
00277         delete [] surface;
00278       }
00279       LastVector(const LastVector& r) : p(r.p), vec(r.vec)
00280       {
00281         surface = new G4VTwistSurface*[1];
00282         surface[0] = r.surface[0];
00283       }
00284       LastVector& operator=(const LastVector& r)
00285       {
00286         if (&r == this)  { return *this; }
00287         p = r.p; vec = r.vec;
00288         delete [] surface; surface = new G4VTwistSurface*[1];
00289         surface[0] = r.surface[0];
00290         return *this;
00291       }
00292     public:
00293       G4ThreeVector   p;
00294       G4ThreeVector   vec;
00295       G4VTwistSurface **surface;
00296   };
00297 
00298   class LastValue              // last G4double value
00299   {
00300     public:
00301       LastValue()
00302       {
00303         p.set(kInfinity,kInfinity,kInfinity);
00304         value = DBL_MAX;
00305       }
00306       ~LastValue(){}
00307       LastValue(const LastValue& r) : p(r.p), value(r.value){}
00308       LastValue& operator=(const LastValue& r)
00309       {
00310         if (this == &r)  { return *this; }
00311         p = r.p; value = r.value;
00312         return *this;
00313       }
00314     public:
00315       G4ThreeVector p;
00316       G4double      value;
00317   };
00318               
00319   class LastValueWithDoubleVector   // last G4double value
00320   {
00321     public:
00322       LastValueWithDoubleVector()
00323       {
00324         p.set(kInfinity,kInfinity,kInfinity);
00325         vec.set(kInfinity,kInfinity,kInfinity);
00326         value = DBL_MAX;
00327       }
00328       ~LastValueWithDoubleVector(){}
00329       LastValueWithDoubleVector(const LastValueWithDoubleVector& r)
00330         : p(r.p), vec(r.vec), value(r.value){}
00331       LastValueWithDoubleVector& operator=(const LastValueWithDoubleVector& r)
00332       {
00333         if (this == &r)  { return *this; }
00334         p = r.p; vec = r.vec; value = r.value;
00335         return *this;
00336       }
00337     public:
00338       G4ThreeVector p;
00339       G4ThreeVector vec;
00340       G4double      value;
00341   };
00342               
00343   LastState    fLastInside;
00344   LastVector   fLastNormal;
00345   LastValue    fLastDistanceToIn;
00346   LastValue    fLastDistanceToOut;
00347   LastValueWithDoubleVector   fLastDistanceToInWithV;
00348   LastValueWithDoubleVector   fLastDistanceToOutWithV;
00349 
00350  };
00351 
00352 //=====================================================================
00353 
00354 //---------------------
00355 // inline functions
00356 //---------------------
00357 
00358 inline
00359 void G4TwistedTubs::SetFields(G4double phitwist, G4double innerrad, 
00360                               G4double outerrad, G4double negativeEndz, 
00361                               G4double positiveEndz)
00362 {
00363    fCubicVolume  = 0.;
00364    fPhiTwist     = phitwist;
00365    fEndZ[0]      = negativeEndz;
00366    fEndZ[1]      = positiveEndz;
00367    fEndZ2[0]     = fEndZ[0] * fEndZ[0];
00368    fEndZ2[1]     = fEndZ[1] * fEndZ[1];
00369    fInnerRadius  = innerrad;
00370    fOuterRadius  = outerrad;
00371    fInnerRadius2 = fInnerRadius * fInnerRadius;
00372    fOuterRadius2 = fOuterRadius * fOuterRadius;
00373    
00374    if (std::fabs(fEndZ[0]) >= std::fabs(fEndZ[1])) {
00375       fZHalfLength = std::fabs(fEndZ[0]);
00376    } else {
00377       fZHalfLength = std::fabs(fEndZ[1]);
00378    }
00379 
00380    G4double parity         = (fPhiTwist > 0 ? 1 : -1); 
00381    G4double tanHalfTwist   = std::tan(0.5 * fPhiTwist);
00382    G4double innerNumerator = std::fabs(fInnerRadius * tanHalfTwist) * parity;
00383    G4double outerNumerator = std::fabs(fOuterRadius * tanHalfTwist) * parity;
00384 
00385    fTanInnerStereo    = innerNumerator / fZHalfLength; 
00386    fTanOuterStereo    = outerNumerator / fZHalfLength; 
00387    fTanInnerStereo2   = fTanInnerStereo * fTanInnerStereo;
00388    fTanOuterStereo2   = fTanOuterStereo * fTanOuterStereo;
00389    fInnerStereo       = std::atan2(innerNumerator,  fZHalfLength); 
00390    fOuterStereo       = std::atan2(outerNumerator,  fZHalfLength); 
00391    fEndInnerRadius[0] = std::sqrt(fInnerRadius2 + fEndZ2[0] * fTanInnerStereo2);
00392    fEndInnerRadius[1] = std::sqrt(fInnerRadius2 + fEndZ2[1] * fTanInnerStereo2);
00393    fEndOuterRadius[0] = std::sqrt(fOuterRadius2 + fEndZ2[0] * fTanOuterStereo2);
00394    fEndOuterRadius[1] = std::sqrt(fOuterRadius2 + fEndZ2[1] * fTanOuterStereo2);
00395 
00396    fKappa          = tanHalfTwist / fZHalfLength;
00397    fEndPhi[0]      = std::atan2(fEndZ[0] * tanHalfTwist, fZHalfLength);
00398    fEndPhi[1]      = std::atan2(fEndZ[1] * tanHalfTwist, fZHalfLength);
00399 
00400 #ifdef G4TWISTDEBUG
00401    G4cout << "/********* G4TwistedTubs::SetFields() Field Parameters ***************** " << G4endl;
00402    G4cout << "/*   fPhiTwist                  : " << fPhiTwist << G4endl;
00403    G4cout << "/*   fEndZ(0, 1)                : " << fEndZ[0] << " , " << fEndZ[1] << G4endl; 
00404    G4cout << "/*   fEndPhi(0, 1)              : " << fEndPhi[0] << " , " << fEndPhi[1] << G4endl; 
00405    G4cout << "/*   fInnerRadius, fOuterRadius : " << fInnerRadius << " , " << fOuterRadius << G4endl; 
00406    G4cout << "/*   fEndInnerRadius(0, 1)      : " << fEndInnerRadius[0] << " , " 
00407           << fEndInnerRadius[1] << G4endl; 
00408    G4cout << "/*   fEndOuterRadius(0, 1)      : " << fEndOuterRadius[0] << " , " 
00409           << fEndOuterRadius[1] << G4endl; 
00410    G4cout << "/*   fInnerStereo, fOuterStereo : " << fInnerStereo << " , " << fOuterStereo << G4endl; 
00411    G4cout << "/*   tanHalfTwist, fKappa       : " << tanHalfTwist << " , " << fKappa << G4endl; 
00412    G4cout << "/*********************************************************************** " << G4endl;
00413 #endif
00414 }
00415 
00416 #endif

Generated on Mon May 27 17:50:04 2013 for Geant4 by  doxygen 1.4.7