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$ 00028 // 00029 // 00030 // class G4ReflectionFactory 00031 // 00032 // Class description: 00033 // 00034 // Class providing functions for volumes placements with a general 00035 // transfomation that can contain reflection. 00036 // Reflection is then applied to a solid: a new G4ReflectedSolid 00037 // instance is created and is placed with a transformation containing 00038 // pure rotation and translation only. 00039 // The pair of constituent and reflected logical volumes is 00040 // considered as a generalized logical volume that is addressed 00041 // by user specifying the constituent logical volume. 00042 // 00043 // Decomposition of a general transformation that can include reflection 00044 // in a "reflection-free" transformation: 00045 // 00046 // x(inM') = TG*x(inM) TG - general transformation 00047 // = T*(R*x(inM)) T - "reflection-free" transformation 00048 // = T* x(inReflM) 00049 // 00050 // Daughters transformation: 00051 // When a volume V containing daughter D with transformation TD 00052 // is placed in mother M with a general tranformation TGV, 00053 // the TGV is decomposed. New reflected volume ReflV containing 00054 // a new daughter ReflD with reflected transformation ReflTD is created: 00055 // 00056 // x(inV) = TD * x(inD); 00057 // x(inM) = TGV * x(inV) 00058 // = TV * R * x(inV) 00059 // = TV * R * TD * x(inD) 00060 // = TV * R*TD*R-1 * R*x(inD) 00061 // = TV * ReflTD * x(inReflD) 00062 00063 // Author: Ivana Hrivnacova, 16.10.2001 (Ivana.Hrivnacova@cern.ch) 00064 // -------------------------------------------------------------------- 00065 #ifndef G4_REFLECTION_FACTORY_HH 00066 #define G4_REFLECTION_FACTORY_HH 00067 00068 #include "G4Types.hh" 00069 #include "G4Transform3D.hh" 00070 #include "geomdefs.hh" 00071 00072 #include <map> 00073 00074 class G4VPhysicalVolume; 00075 class G4LogicalVolume; 00076 class G4VSolid; 00077 class G4VPVDivisionFactory; 00078 00079 typedef std::pair<G4VPhysicalVolume*, 00080 G4VPhysicalVolume*> G4PhysicalVolumesPair; 00081 typedef std::map<G4LogicalVolume*, G4LogicalVolume*, 00082 std::less<G4LogicalVolume*> > G4ReflectedVolumesMap; 00083 00084 class G4ReflectionFactory 00085 { 00086 typedef G4ReflectedVolumesMap::const_iterator LogicalVolumesMapIterator; 00087 00088 public: // with description 00089 00090 virtual ~G4ReflectionFactory(); 00091 // Virtual destructor. 00092 00093 static G4ReflectionFactory* Instance(); 00094 // Gets pointer to the instance of the singleton. 00095 00096 G4PhysicalVolumesPair Place(const G4Transform3D& transform3D, 00097 const G4String& name, 00098 G4LogicalVolume* LV, 00099 G4LogicalVolume* motherLV, 00100 G4bool isMany, 00101 G4int copyNo, 00102 G4bool surfCheck=false); 00103 // Evaluates the passed transformation; if it contains reflection 00104 // it performs its decomposition, creates new reflected solid and 00105 // logical volume (or retrieves them from a map if the reflected 00106 // objects were already created), transforms the daughters (if present) 00107 // and place it in the given mother. 00108 // The result is a pair of physical volumes; 00109 // the second physical volume is a placement in a reflected mother 00110 // or 0 if mother LV was not reflected. 00111 00112 G4PhysicalVolumesPair Replicate(const G4String& name, 00113 G4LogicalVolume* LV, 00114 G4LogicalVolume* motherLV, 00115 EAxis axis, 00116 G4int nofReplicas, 00117 G4double width, 00118 G4double offset=0); 00119 // Creates replica in the given mother. 00120 // The result is a pair of physical volumes; 00121 // the second physical volume is a replica in a reflected mother 00122 // or 0 if mother LV was not reflected. 00123 00124 G4PhysicalVolumesPair Divide(const G4String& name, 00125 G4LogicalVolume* LV, 00126 G4LogicalVolume* motherLV, 00127 EAxis axis, 00128 G4int nofDivisions, 00129 G4double width, 00130 G4double offset); 00131 G4PhysicalVolumesPair Divide(const G4String& name, 00132 G4LogicalVolume* LV, 00133 G4LogicalVolume* motherLV, 00134 EAxis axis, 00135 G4int nofDivisions, 00136 G4double offset); 00137 G4PhysicalVolumesPair Divide(const G4String& name, 00138 G4LogicalVolume* LV, 00139 G4LogicalVolume* motherLV, 00140 EAxis axis, 00141 G4double width, 00142 G4double offset); 00143 // Creates division in the given mother. 00144 // The result is a pair of physical volumes; 00145 // the second physical volume is a division in a reflected mother 00146 // or 0 if mother LV was not reflected. 00147 00148 void SetVerboseLevel(G4int verboseLevel); 00149 G4int GetVerboseLevel() const; 00150 // Sets/gets verbosity level. 00151 00152 void SetVolumesNameExtension(const G4String& nameExtension); 00153 const G4String& GetVolumesNameExtension() const; 00154 // Returns the name extension for the reflected solids 00155 // and logical volumes. 00156 00157 void SetScalePrecision(G4double scaleValue); 00158 G4double GetScalePrecision() const; 00159 // Sets/gets precision factor for the scale consistency check 00160 // The default value is set to 10*kCarTolerance. 00161 00162 G4LogicalVolume* GetConstituentLV(G4LogicalVolume* reflLV) const; 00163 // Returns the consituent volume of the given reflected volume, 00164 // 0 if the given reflected volume was not found. 00165 00166 G4LogicalVolume* GetReflectedLV(G4LogicalVolume* lv) const; 00167 // Returns the reflected volume of the given consituent volume, 00168 // 0 if the given volume was not reflected. 00169 00170 G4bool IsConstituent(G4LogicalVolume* lv) const; 00171 // Returns true if the given volume has been already reflected 00172 // (is in the map of constituent volumes). 00173 00174 G4bool IsReflected(G4LogicalVolume* lv) const; 00175 // Returns true if the given volume is a reflected volume 00176 // (is in the map reflected volumes). 00177 00178 const G4ReflectedVolumesMap& GetReflectedVolumesMap() const; 00179 // Returns a handle to the internal map of volumes which have 00180 // been reflected, after that placement or replication is performed. 00181 00182 void Reset(); 00183 // Resets maps of constituent and reflected volumes. 00184 // To be used exclusively when volumes are removed from the stores. 00185 00186 protected: 00187 00188 G4ReflectionFactory(); 00189 // Protected singleton constructor. 00190 00191 G4ReflectionFactory(const G4ReflectionFactory&); 00192 G4ReflectionFactory& operator=(const G4ReflectionFactory&); 00193 // Disabled copy constructor and assignment operator. 00194 00195 private: 00196 00197 G4LogicalVolume* ReflectLV(G4LogicalVolume* LV, G4bool surfCheck=false); 00198 // Gets/creates the reflected solid and logical volume 00199 // and copies + transforms LV daughters. 00200 00201 G4LogicalVolume* CreateReflectedLV(G4LogicalVolume* LV); 00202 // Creates the reflected solid and logical volume 00203 // and add the logical volumes pair in the maps. 00204 00205 void ReflectDaughters(G4LogicalVolume* LV, 00206 G4LogicalVolume* refLV, G4bool surfCheck=false); 00207 // Reflects daughters recursively. 00208 00209 void ReflectPVPlacement(G4VPhysicalVolume* PV, 00210 G4LogicalVolume* refLV, G4bool surfCheck=false); 00211 // Copies and transforms daughter of PVPlacement type of 00212 // a constituent volume into a reflected volume. 00213 00214 void ReflectPVReplica(G4VPhysicalVolume* PV, G4LogicalVolume* refLV); 00215 // Copies and transforms daughter of PVReplica type of 00216 // a constituent volume into a reflected volume. 00217 00218 void ReflectPVDivision(G4VPhysicalVolume* PV, G4LogicalVolume* refLV); 00219 // Copies and transforms daughter of PVDivision type of 00220 // a constituent volume into a reflected volume. 00221 00222 void ReflectPVParameterised(G4VPhysicalVolume* PV, 00223 G4LogicalVolume* refLV, G4bool surfCheck=false); 00224 // Not implemented yet. 00225 // Should copy and transform daughter of PVReplica type of 00226 // a constituent volume into a reflected volume. 00227 00228 G4bool IsReflection(const G4Scale3D& scale) const; 00229 // Returns true if the scale is negative, false otherwise. 00230 00231 void CheckScale(const G4Scale3D& scale) const; 00232 // Checks if scale correspond to fScale, if not gives exception. 00233 00234 G4VPVDivisionFactory* GetPVDivisionFactory() const; 00235 // Checks if the division factory is instanciated, 00236 // if not gives exception. 00237 00238 void PrintConstituentLVMap(); 00239 // Temporary - for debugging purpose. 00240 00241 private: 00242 00243 static G4ReflectionFactory* fInstance; 00244 static const G4String fDefaultNameExtension; 00245 static const G4Scale3D fScale; 00246 G4double fScalePrecision; 00247 00248 G4int fVerboseLevel; 00249 G4String fNameExtension; 00250 G4ReflectedVolumesMap fConstituentLVMap; 00251 G4ReflectedVolumesMap fReflectedLVMap; 00252 }; 00253 00254 #endif