Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-08-19 09:10:18

0001 //
0002 // ********************************************************************
0003 // * License and Disclaimer                                           *
0004 // *                                                                  *
0005 // * The  Geant4 software  is  copyright of the Copyright Holders  of *
0006 // * the Geant4 Collaboration.  It is provided  under  the terms  and *
0007 // * conditions of the Geant4 Software License,  included in the file *
0008 // * LICENSE and available at  http://cern.ch/geant4/license .  These *
0009 // * include a list of copyright holders.                             *
0010 // *                                                                  *
0011 // * Neither the authors of this software system, nor their employing *
0012 // * institutes,nor the agencies providing financial support for this *
0013 // * work  make  any representation or  warranty, express or implied, *
0014 // * regarding  this  software system or assume any liability for its *
0015 // * use.  Please see the license in the file  LICENSE  and URL above *
0016 // * for the full disclaimer and the limitation of liability.         *
0017 // *                                                                  *
0018 // * This  code  implementation is the result of  the  scientific and *
0019 // * technical work of the GEANT4 collaboration.                      *
0020 // * By using,  copying,  modifying or  distributing the software (or *
0021 // * any work based  on the software)  you  agree  to acknowledge its *
0022 // * use  in  resulting  scientific  publications,  and indicate your *
0023 // * acceptance of all terms of the Geant4 Software license.          *
0024 // ********************************************************************
0025 //
0026 // G4VTwistSurface
0027 //
0028 // Class description:
0029 //
0030 // Abstract base class for boundary surface of G4VSolid.
0031 
0032 // Author: Kotoyo Hoshina (Chiba University), 01.08.2002 - Created.
0033 //         Oliver Link (CERN), 13.11.2003 - Integration in Geant4
0034 //               from original version in Jupiter-2.5.02 application.
0035 // --------------------------------------------------------------------
0036 #ifndef G4VTWISTSURFACE_HH
0037 #define G4VTWISTSURFACE_HH
0038 
0039 #include <CLHEP/Units/SystemOfUnits.h>
0040 
0041 #include "G4VSolid.hh"
0042 #include "geomdefs.hh"
0043 
0044 #include "G4RotationMatrix.hh"
0045 
0046 #define G4VSURFACENXX 10
0047 
0048 /**
0049  * @brief G4VTwistSurface is a base class for boundary surface of a G4VSolid.
0050  */
0051 
0052 class G4VTwistSurface
0053 {
0054   public:
0055 
0056     enum EValidate { kDontValidate = 0, kValidateWithTol = 1, 
0057                      kValidateWithoutTol = 2, kUninitialized = 3 };
0058 
0059     /**
0060      * Base constructor, given a name.
0061      *  @param[in] name The surface name.
0062      */
0063     G4VTwistSurface (const G4String& name);
0064 
0065     /**
0066      * Constructs a surface, given its parameters.
0067      *  @param[in] name The surface name.
0068      *  @param[in] rot Rotation: 0.5*(phi-width segment).
0069      *  @param[in] tlate Translation.
0070      *  @param[in] handedness Orientation: R-hand = 1, L-hand = -1.
0071      *  @param[in] axis0 First axis.
0072      *  @param[in] axis1 Second axis.
0073      *  @param[in] axis0min Minimum in first axis.
0074      *  @param[in] axis1min Minimum in second axis.
0075      *  @param[in] axis0max Maximum in first axis.
0076      *  @param[in] axis1max Maximum in second axis.
0077      */
0078     G4VTwistSurface (const G4String& name,
0079                      const G4RotationMatrix& rot,
0080                      const G4ThreeVector&    tlate,
0081                            G4int             handedness,
0082                      const EAxis             axis0,
0083                      const EAxis             axis1,
0084                            G4double          axis0min = -kInfinity,
0085                            G4double          axis1min = -kInfinity,
0086                            G4double          axis0max = kInfinity,
0087                            G4double          axis1max = kInfinity);
0088  
0089     /**
0090      * Default destructor.
0091      */
0092     virtual ~G4VTwistSurface() = default;
0093 
0094     /**
0095      * Returns the phi-location of point 'me' (phi relation between 'me' and
0096      * 'vec' projected on z=0 plane). If 'me' is on -ve-phi-side of 'vec', it
0097      * returns 1; on the other hand, if 'me' is on +ve-phi-side of 'vec',
0098      * it returns -1. If 'me' is on boundary of 'vec', it returns 0.
0099      *  @returns The z-coordinate of normal vector of me.cross(vec).
0100      */
0101     virtual G4int AmIOnLeftSide(const G4ThreeVector& me, 
0102                                 const G4ThreeVector& vec, 
0103                                       G4bool withTol = true);
0104 
0105     /**
0106      * Returns the distance to the nearest boundary from an arbitrary point 'p' 
0107      * in local coodinate.
0108      *  @param[in] areacode Point location code according to axes.
0109      *  @param[out] xx The returned reference point on boundary.
0110      *  @param[in] p The arbitrary point in input.
0111      */
0112     virtual G4double DistanceToBoundary(G4int areacode,
0113                                         G4ThreeVector& xx,
0114                                         const G4ThreeVector& p) ;
0115 
0116     /**
0117      * Returns the distance from outside to a boundary from an arbitrary
0118      * point 'gp' and direction 'gv'.
0119      *  @param[in] gp The arbitrary point.
0120      *  @param[in] gv The direction vector.
0121      *  @param[out] gxxbest The returned reference point on boundary.
0122      */
0123     virtual G4double DistanceToIn(const G4ThreeVector& gp,
0124                                   const G4ThreeVector& gv,
0125                                         G4ThreeVector& gxxbest);
0126 
0127     /**
0128      * Returns the distance from inside to a boundary from an arbitrary
0129      * point 'gp' and direction 'gv'.
0130      *  @param[in] gp The arbitrary point.
0131      *  @param[in] gv The direction vector.
0132      *  @param[out] gxxbest The returned reference point on boundary.
0133      */
0134     virtual G4double  DistanceToOut(const G4ThreeVector& gp,
0135                                     const G4ThreeVector& gv,
0136                                           G4ThreeVector& gxxbest);
0137 
0138     /**
0139      * Returns the safety distance to a boundary from an arbitrary point 'gp'.
0140      *  @param[in] gp The arbitrary point.
0141      *  @param[out] gxxbest The returned reference point on boundary.
0142      */
0143     virtual G4double DistanceTo(const G4ThreeVector& gp,
0144                                       G4ThreeVector& gxx);
0145       
0146     /**
0147      * Returns the distance to surface, given point 'gp' and direction 'gv'.
0148      *  @param[in] gp The point from where computing the distance.
0149      *  @param[in] gv The direction along which computing the distance.
0150      *  @param[out] gxx Vector of global points based on number of solutions.
0151      *  @param[out] distance The distance vector based on number of solutions.
0152      *  @param[out] areacode The location vector based on number of solutions.
0153      *  @param[out] isvalid Validity vector based on number of solutions.
0154      *  @param[in] validate Adopted validation criteria.
0155      *  @returns The number of solutions.
0156      */
0157     virtual G4int DistanceToSurface(const G4ThreeVector& gp,
0158                                     const G4ThreeVector& gv,
0159                                           G4ThreeVector  gxx[],
0160                                           G4double       distance[],
0161                                           G4int          areacode[],
0162                                           G4bool         isvalid[],
0163                                     EValidate validate = kValidateWithTol) = 0;
0164 
0165     /**
0166      * Returns the safety distance to surface, given point 'gp'.
0167      *  @param[in] gp The point from where computing the safety distance.
0168      *  @param[out] gxx Vector of global points based on number of solutions.
0169      *  @param[out] distance The distance vector based on number of solutions.
0170      *  @param[out] areacode The location vector based on number of solutions.
0171      *  @returns The number of solutions.
0172      */
0173     virtual G4int DistanceToSurface(const G4ThreeVector& gp,
0174                                           G4ThreeVector  gxx[],
0175                                           G4double       distance[],
0176                                           G4int          areacode[]) = 0;
0177                                              
0178     /**
0179      * Returns a normal vector at a surface (or very close to the surface)
0180      * point at 'p'.
0181      *  @param[in] p The point where computing the normal.
0182      *  @param[in] isGlobal If true, it returns the normal in global coordinates.
0183      *  @returns The normal vector.
0184      */
0185     virtual G4ThreeVector GetNormal(const G4ThreeVector& p,
0186                                           G4bool isGlobal) = 0;
0187    
0188     /**
0189      * Returns parameters of boundaries.
0190      *  @param[in] areacode The location code.
0191      *  @param[out] d Boundary direction.
0192      *  @param[out] x0 The point on boundary.
0193      *  @param[out] boundarytype The boundary code.
0194      */
0195     virtual void GetBoundaryParameters(const G4int& areacode,
0196                                              G4ThreeVector& d,
0197                                              G4ThreeVector& x0,
0198                                              G4int& boundarytype) const;
0199 
0200     /**
0201      * Returns Z projection of point 'p' on boundary.
0202      *  @param[in] areacode The location code.
0203      *  @param[out] p The arbitrary point.
0204      *  @returns The Z projection on boundary.
0205      */
0206     virtual G4ThreeVector GetBoundaryAtPZ(G4int areacode,
0207                                           const G4ThreeVector& p) const;
0208 
0209     /**
0210      * Utility methods to compute the distance from a plane/line.
0211      */
0212     inline G4double DistanceToPlaneWithV(const G4ThreeVector& p,
0213                                          const G4ThreeVector& v,
0214                                          const G4ThreeVector& x0,
0215                                          const G4ThreeVector& n0,
0216                                                G4ThreeVector& xx);
0217     inline G4double DistanceToPlane(const G4ThreeVector& p,
0218                                     const G4ThreeVector& x0,
0219                                     const G4ThreeVector& n0,
0220                                           G4ThreeVector& xx);
0221     inline G4double DistanceToPlane(const G4ThreeVector& p,
0222                                     const G4ThreeVector& x0,
0223                                     const G4ThreeVector& t1,
0224                                     const G4ThreeVector& t2,
0225                                           G4ThreeVector& xx,
0226                                           G4ThreeVector& n);
0227     inline G4double DistanceToLine (const G4ThreeVector& p,
0228                                     const G4ThreeVector& x0,
0229                                     const G4ThreeVector& d,
0230                                           G4ThreeVector& xx);
0231 
0232     /**
0233      * Test functions/accessors, based on 'areacode' location.
0234      */
0235     inline G4bool IsAxis0 (G4int areacode) const;
0236     inline G4bool IsAxis1 (G4int areacode) const;
0237     inline G4bool IsOutside (G4int areacode) const;
0238     inline G4bool IsInside (G4int areacode, G4bool testbitmode = false) const;
0239     inline G4bool IsBoundary (G4int areacode, G4bool testbitmode = false) const;
0240     inline G4bool IsCorner (G4int areacode, G4bool testbitmode = false) const;
0241     inline G4bool IsValidNorm() const { return fIsValidNorm; }
0242     G4bool IsSameBoundary (G4VTwistSurface* surface1, G4int areacode1,
0243                            G4VTwistSurface* surface2, G4int areacode2 ) const;
0244     inline G4int GetAxisType(G4int areacode, G4int whichaxis) const;
0245 
0246     /**
0247      * Utility functions computing global/local point/direction.
0248      */
0249     inline G4ThreeVector ComputeGlobalPoint (const G4ThreeVector& lp) const;
0250     inline G4ThreeVector ComputeLocalPoint (const G4ThreeVector& gp) const;
0251     inline G4ThreeVector ComputeGlobalDirection (const G4ThreeVector& lp) const;
0252     inline G4ThreeVector ComputeLocalDirection (const G4ThreeVector& gp) const;
0253   
0254     /**
0255      * Modifiers for axes.
0256      */
0257     inline void SetAxis(G4int i, const EAxis axis) { fAxis[i] = axis; }
0258     inline void SetNeighbours(G4VTwistSurface* ax0min, G4VTwistSurface* ax1min, 
0259                               G4VTwistSurface* ax0max, G4VTwistSurface* ax1max);
0260 
0261     /**
0262      * Returns point on surface given the axes.
0263      */
0264     virtual G4ThreeVector SurfacePoint(G4double, G4double,
0265                                        G4bool isGlobal = false ) = 0 ;
0266 
0267     /**
0268      * Internal accessors to be implemented in concrete derived classes.
0269      */
0270     virtual G4double GetBoundaryMin(G4double) = 0 ;
0271     virtual G4double GetBoundaryMax(G4double) = 0 ;
0272     virtual G4double GetSurfaceArea() = 0 ;
0273     virtual void GetFacets(G4int m, G4int n, G4double xyz[][3],
0274                            G4int faces[][4], G4int iside) = 0 ;
0275 
0276     /**
0277      * Node/face mapping functions.
0278      */
0279     G4int GetNode( G4int i, G4int j, G4int m, G4int n, G4int iside ) ;
0280     G4int GetFace( G4int i, G4int j, G4int m, G4int n, G4int iside ) ;
0281 
0282     /**
0283      * Checks face visibility, based on verteces and orientation.
0284      *  @returns -1 if invisible; 1 if visible.
0285      */
0286     G4int GetEdgeVisibility( G4int i, G4int j, G4int m, G4int n,
0287                              G4int number, G4int orientation) ;
0288 
0289     /**
0290      * Returns the surface name.
0291      */
0292     inline const G4String& GetName() const { return fName; }
0293 
0294     /**
0295      * Prints on standard output surface data.
0296      */
0297     void DebugPrint() const;
0298 
0299     /**
0300      * Fake default constructor for usage restricted to direct object
0301      * persistency for clients requiring preallocation of memory for
0302      * persistifiable objects.
0303      */
0304     G4VTwistSurface(__void__&);
0305 
0306   protected:
0307  
0308     /**
0309      * Internal accessors.
0310      */
0311     inline G4VTwistSurface** GetNeighbours() { return fNeighbours; } 
0312     inline G4int GetNeighbours(G4int areacode, G4VTwistSurface* surfaces[]);
0313     inline G4ThreeVector GetCorner(G4int areacode) const;
0314     void GetBoundaryAxis(G4int areacode, EAxis axis[]) const;
0315     void GetBoundaryLimit(G4int areacode, G4double limit[]) const;
0316     virtual G4int GetAreaCode(const G4ThreeVector& xx, G4bool withtol=true) = 0;
0317 
0318     /**
0319      * Modifier for boundaries.
0320      *  @param[in] axiscode The location code, either: sAxis0 & sAxisMin,
0321      *             sAxis0 & sAxisMax, sAxis1 & sAxisMin, sAxis1 & sAxisMax.
0322      *  @param[in] direction Direction.
0323      *  @param[in] x0 Point on boundary.
0324      *  @param[in] boundarytype The shape of locus from the start point to
0325      *             end point of boundary (ex. sAxisRho = linear line which
0326      *             start point is fixed at origin; sAxisPhi = part of circle
0327      *             which center placed at the origin.
0328      */
0329     virtual void SetBoundary(const G4int& axiscode, 
0330                              const G4ThreeVector& direction,
0331                              const G4ThreeVector& x0, 
0332                              const G4int& boundarytype);
0333 
0334     /**
0335      * Modifier for corners.
0336      */
0337     void SetCorner(G4int areacode, G4double x, G4double y, G4double z);
0338 
0339   private:
0340 
0341     /**
0342      * Internal setters to be implemented in concrete dereived classes.
0343      */
0344     virtual void SetBoundaries() = 0;
0345     virtual void SetCorners()    = 0;
0346    
0347   // data members ---------------------------------------------------------
0348 
0349   public:
0350 
0351     /** Boundary types. */
0352     static const G4int sOutside ;
0353     static const G4int sInside  ;
0354     static const G4int sBoundary;
0355     static const G4int sCorner;
0356     static const G4int sC0Min1Min;
0357     static const G4int sC0Max1Min;
0358     static const G4int sC0Max1Max;
0359     static const G4int sC0Min1Max;
0360     static const G4int sAxisMin;
0361     static const G4int sAxisMax;
0362     static const G4int sAxisX;
0363     static const G4int sAxisY;
0364     static const G4int sAxisZ;
0365     static const G4int sAxisRho;
0366     static const G4int sAxisPhi;
0367     static const G4int sAxis0;
0368     static const G4int sAxis1;
0369     static const G4int sSizeMask;
0370     static const G4int sAxisMask;
0371     static const G4int sAreaMask;
0372 
0373   protected:
0374  
0375     class CurrentStatus 
0376     {
0377       /**
0378        * @brief Internal class defining the surface status.
0379        */
0380       public:
0381 
0382         CurrentStatus();
0383         virtual ~CurrentStatus();
0384       
0385         inline G4ThreeVector GetXX(G4int i) const { return fXX[i]; }
0386         inline G4double GetDistance(G4int i) const { return fDistance[i]; }
0387         inline G4int GetAreacode(G4int i) const { return fAreacode[i]; }
0388         inline G4int GetNXX() const { return fNXX; }
0389         inline G4bool IsDone() const { return fDone; }
0390         inline G4bool IsValid(G4int i) const { return fIsValid[i]; }
0391 
0392         void SetCurrentStatus(G4int  i, 
0393                               G4ThreeVector& xx, 
0394                               G4double& dist, 
0395                               G4int& areacode, 
0396                               G4bool& isvalid,
0397                               G4int nxx,
0398                               EValidate validate,
0399                         const G4ThreeVector* p, 
0400                         const G4ThreeVector* v = nullptr);
0401 
0402         void ResetfDone(EValidate validate,
0403                   const G4ThreeVector* p, 
0404                   const G4ThreeVector* v = nullptr);
0405 
0406 
0407         void DebugPrint() const;
0408 
0409       private:
0410 
0411         G4double fDistance[G4VSURFACENXX];
0412         G4ThreeVector fXX[G4VSURFACENXX];
0413         G4int fAreacode[G4VSURFACENXX];
0414         G4bool fIsValid[G4VSURFACENXX];
0415         G4int fNXX;
0416         G4ThreeVector fLastp;
0417         G4ThreeVector fLastv;
0418         EValidate fLastValidate;
0419         G4bool fDone;
0420     };
0421       
0422     class Boundary 
0423     {
0424       /**
0425        * @brief Internal class defining a surface boundary type.
0426        */
0427       public:
0428 
0429         Boundary() = default;
0430         virtual ~Boundary() = default;
0431       
0432         void SetFields(const G4int& areacode, 
0433                        const G4ThreeVector& d, 
0434                        const G4ThreeVector& x0, 
0435                        const G4int& boundarytype);
0436       
0437         G4bool IsEmpty() const;
0438       
0439         G4bool GetBoundaryParameters(const G4int& areacode, 
0440                                            G4ThreeVector& d,
0441                                            G4ThreeVector& x0, 
0442                                            G4int& boundarytype) const;
0443 
0444       private:
0445 
0446         G4int fBoundaryAcode{-1};
0447         G4ThreeVector fBoundaryDirection;
0448         G4ThreeVector fBoundaryX0;
0449         G4int fBoundaryType{0};
0450     };
0451 
0452     EAxis fAxis[2];
0453     G4double fAxisMin[2];
0454     G4double fAxisMax[2];
0455     CurrentStatus fCurStatWithV;
0456     CurrentStatus fCurStat;
0457     G4RotationMatrix fRot;
0458     G4ThreeVector fTrans;
0459     G4int fHandedness;
0460 
0461     class G4SurfCurNormal
0462     {
0463       public:
0464 
0465         G4ThreeVector p;
0466         G4ThreeVector normal;
0467     };
0468 
0469     G4SurfCurNormal fCurrentNormal;
0470     G4bool fIsValidNorm;
0471     G4double kCarTolerance;
0472 
0473   private:
0474                      
0475     G4VTwistSurface* fNeighbours[4]; // {0,1,2,3} = sAxis0min, sAxis1min, 
0476                                      //             sAxis0max, sAxis1max
0477     G4ThreeVector fCorners[4]; // corners of the surface in local coordinate
0478     Boundary fBoundaries[4];   // boundaries of the surface.
0479     G4String fName;
0480    
0481     class G4SurfSideQuery
0482     {
0483       public:
0484 
0485         G4ThreeVector me;
0486         G4ThreeVector vec;
0487         G4bool  withTol;
0488         G4int amIOnLeftSide;
0489     };
0490     G4SurfSideQuery fAmIOnLeftSide;
0491 };
0492 
0493 //========================================================
0494 // inline functions
0495 //========================================================
0496 
0497 #include "G4VTwistSurface.icc"
0498 
0499 #endif