Geant4 Cross Reference |
1 // 2 // ******************************************************************** 3 // * License and Disclaimer * 4 // * * 5 // * The Geant4 software is copyright of the Copyright Holders of * 6 // * the Geant4 Collaboration. It is provided under the terms and * 7 // * conditions of the Geant4 Software License, included in the file * 8 // * LICENSE and available at http://cern.ch/geant4/license . These * 9 // * include a list of copyright holders. * 10 // * * 11 // * Neither the authors of this software system, nor their employing * 12 // * institutes,nor the agencies providing financial support for this * 13 // * work make any representation or warranty, express or implied, * 14 // * regarding this software system or assume any liability for its * 15 // * use. Please see the license in the file LICENSE and URL above * 16 // * for the full disclaimer and the limitation of liability. * 17 // * * 18 // * This code implementation is the result of the scientific and * 19 // * technical work of the GEANT4 collaboration. * 20 // * By using, copying, modifying or distributing the software (or * 21 // * any work based on the software) you agree to acknowledge its * 22 // * use in resulting scientific publications, and indicate your * 23 // * acceptance of all terms of the Geant4 Software license. * 24 // ******************************************************************** 25 // 26 // ******************************************************************** 27 // 28 // CaTS (Calorimetry and Tracking Simulation) 29 // 30 // Authors : Hans Wenzel 31 // Soon Yung Jun 32 // (Fermi National Accelerator Laboratory) 33 // 34 // History 35 // October 18th, 2021 : first implementation 36 // 37 // ******************************************************************** 38 // 39 /// \file DetectorConstruction.cc 40 /// \brief Implementation of the CaTS::DetectorConstruction class 41 42 // Geant4 headers 43 #include "G4RunManager.hh" 44 #include "G4PhysicalVolumeStore.hh" 45 #include "G4LogicalVolumeStore.hh" 46 #include "G4VisAttributes.hh" 47 #include "G4UserLimits.hh" 48 #include "G4ios.hh" 49 #include "G4SDManager.hh" 50 #include "G4GDMLParser.hh" 51 // project headers 52 #include "ConfigurationManager.hh" 53 #include "DetectorConstruction.hh" 54 #include "TrackerSD.hh" 55 #include "MscSD.hh" 56 #include "lArTPCSD.hh" 57 #include "CalorimeterSD.hh" 58 #include "DRCalorimeterSD.hh" 59 #include "RadiatorSD.hh" 60 #include "PhotonSD.hh" 61 #include "InteractionSD.hh" 62 #include "ColorReader.hh" 63 // c++ headers 64 #include <iostream> 65 66 DetectorConstruction::DetectorConstruction(G4String fname) 67 : G4VUserDetectorConstruction() 68 , gdmlFile(fname) 69 {} 70 71 DetectorConstruction::~DetectorConstruction() {} 72 G4VPhysicalVolume* DetectorConstruction::Construct() 73 { 74 verbose = ConfigurationManager::getInstance()->isEnable_verbose(); 75 ReadGDML(); 76 const G4GDMLAuxMapType* auxmap = parser->GetAuxMap(); 77 if(verbose) 78 { 79 G4cout << "Found " << auxmap->size() 80 << " volume(s) with auxiliary information." << G4endl << G4endl; 81 } 82 for(G4GDMLAuxMapType::const_iterator iter = auxmap->begin(); 83 iter != auxmap->end(); iter++) 84 { 85 if(verbose) 86 { 87 G4cout << "Volume " << ((*iter).first)->GetName() 88 << " has the following list of auxiliary information: " << G4endl; 89 } 90 for(G4GDMLAuxListType::const_iterator vit = (*iter).second.begin(); 91 vit != (*iter).second.end(); vit++) 92 { 93 if(verbose) 94 { 95 G4cout << "--> Type: " << (*vit).type << " Value: " << (*vit).value 96 << G4endl; 97 } 98 if((*vit).type == "StepLimit") 99 { 100 G4UserLimits* fStepLimit = new G4UserLimits(atof((*vit).value)); 101 ((*iter).first)->SetUserLimits(fStepLimit); 102 } 103 } 104 } 105 G4VPhysicalVolume* worldPhysVol = parser->GetWorldVolume(); 106 if(ConfigurationManager::getInstance()->isDumpgdml()) 107 { 108 std::ifstream ifile; 109 ifile.open(ConfigurationManager::getInstance()->getGDMLFileName()); 110 if(ifile) 111 { 112 G4cout << "****************************************************" 113 << G4endl; 114 G4cout << ConfigurationManager::getInstance()->getGDMLFileName() 115 << " already exists!!!" << G4endl; 116 G4cout << "No new gdml dump created!!!" << G4endl; 117 G4cout << "****************************************************" 118 << G4endl; 119 } 120 else 121 { 122 G4cout << "Writing: " 123 << ConfigurationManager::getInstance()->getGDMLFileName() 124 << G4endl; 125 parser->Write(ConfigurationManager::getInstance()->getGDMLFileName(), 126 worldPhysVol); 127 } 128 } 129 return worldPhysVol; 130 } 131 void DetectorConstruction::ConstructSDandField() 132 { 133 G4SDManager* SDman = G4SDManager::GetSDMpointer(); 134 const G4GDMLAuxMapType* auxmap = parser->GetAuxMap(); 135 if(verbose) 136 { 137 G4cout << "Found " << auxmap->size() 138 << " volume(s) with auxiliary information." << G4endl << G4endl; 139 } 140 for(G4GDMLAuxMapType::const_iterator iter = auxmap->begin(); 141 iter != auxmap->end(); iter++) 142 { 143 if(verbose) 144 { 145 G4cout << "Volume " << ((*iter).first)->GetName() 146 << " has the following list of auxiliary information: " << G4endl; 147 } 148 for(G4GDMLAuxListType::const_iterator vit = (*iter).second.begin(); 149 vit != (*iter).second.end(); vit++) 150 { 151 if(verbose) 152 { 153 G4cout << "--> Type: " << (*vit).type << " Value: " << (*vit).value 154 << G4endl; 155 } 156 if((*vit).type == "SensDet") 157 { 158 if(verbose) 159 { 160 G4cout << "Found sensitive Detector: " << (*vit).value << G4endl; 161 } 162 if((*vit).value == "PhotonDetector") 163 { 164 G4String name = ((*iter).first)->GetName() + "_Photondetector"; 165 PhotonSD* aPhotonSD = new PhotonSD(name); 166 SDman->AddNewDetector(aPhotonSD); 167 ((*iter).first)->SetSensitiveDetector(aPhotonSD); 168 if(verbose) 169 { 170 G4cout << "Attaching sensitive Detector: " << (*vit).value 171 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 172 } 173 } 174 else if((*vit).value == "Target") 175 { 176 G4String name = ((*iter).first)->GetName() + "_Target"; 177 InteractionSD* aInteractionSD = new InteractionSD(name); 178 SDman->AddNewDetector(aInteractionSD); 179 ((*iter).first)->SetSensitiveDetector(aInteractionSD); 180 if(verbose) 181 { 182 G4cout << "Attaching sensitive Detector: " << (*vit).value 183 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 184 } 185 } 186 else if((*vit).value == "Tracker") 187 { 188 G4String name = ((*iter).first)->GetName() + "_Tracker"; 189 TrackerSD* aTrackerSD = new TrackerSD(name); 190 SDman->AddNewDetector(aTrackerSD); 191 ((*iter).first)->SetSensitiveDetector(aTrackerSD); 192 if(verbose) 193 { 194 G4cout << "Attaching sensitive Detector: " << (*vit).value 195 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 196 } 197 } 198 else if((*vit).value == "Msc") 199 { 200 G4String name = ((*iter).first)->GetName() + "_Msc"; 201 MscSD* aMscSD = new MscSD(name); 202 SDman->AddNewDetector(aMscSD); 203 ((*iter).first)->SetSensitiveDetector(aMscSD); 204 if(verbose) 205 { 206 G4cout << "Attaching sensitive Detector: " << (*vit).value 207 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 208 } 209 } 210 else if((*vit).value == "lArTPC") 211 { 212 G4String name = ((*iter).first)->GetName() + "_lArTPC"; 213 lArTPCSD* alArTPCSD = new lArTPCSD(name); 214 SDman->AddNewDetector(alArTPCSD); 215 ((*iter).first)->SetSensitiveDetector(alArTPCSD); 216 if(verbose) 217 { 218 G4cout << "Attaching sensitive Detector: " << (*vit).value 219 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 220 } 221 } 222 else if((*vit).value == "Radiator") 223 { 224 G4String name = ((*iter).first)->GetName() + "_Radiator"; 225 RadiatorSD* aRadiatorSD = new RadiatorSD(name); 226 SDman->AddNewDetector(aRadiatorSD); 227 ((*iter).first)->SetSensitiveDetector(aRadiatorSD); 228 if(verbose) 229 { 230 G4cout << "Attaching sensitive Detector: " << (*vit).value 231 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 232 } 233 } 234 else if((*vit).value == "Calorimeter") 235 { 236 G4String name = ((*iter).first)->GetName() + "_Calorimeter"; 237 CalorimeterSD* aCalorimeterSD = new CalorimeterSD(name); 238 SDman->AddNewDetector(aCalorimeterSD); 239 ((*iter).first)->SetSensitiveDetector(aCalorimeterSD); 240 if(verbose) 241 { 242 G4cout << "Attaching sensitive Detector: " << (*vit).value 243 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 244 } 245 } 246 else if((*vit).value == "DRCalorimeter") 247 { 248 G4String name = ((*iter).first)->GetName() + "_DRCalorimeter"; 249 DRCalorimeterSD* aDRCalorimeterSD = new DRCalorimeterSD(name); 250 SDman->AddNewDetector(aDRCalorimeterSD); 251 ((*iter).first)->SetSensitiveDetector(aDRCalorimeterSD); 252 if(verbose) 253 { 254 G4cout << "Attaching sensitive Detector: " << (*vit).value 255 << " to Volume: " << ((*iter).first)->GetName() << G4endl; 256 } 257 } 258 } 259 else if((*vit).type == "Solid") 260 { 261 if((*vit).value == "True") 262 { 263 G4VisAttributes* visibility = new G4VisAttributes(); 264 visibility->SetForceSolid(true); 265 G4VisAttributes* visatt = new G4VisAttributes( 266 ((*iter).first)->GetVisAttributes()->GetColour()); 267 visatt->SetVisibility(true); 268 visatt->SetForceSolid(true); 269 visatt->SetForceAuxEdgeVisible(true); 270 ((*iter).first)->SetVisAttributes(visatt); 271 } 272 } 273 } 274 } 275 } 276 void DetectorConstruction::ReadGDML() 277 { 278 fReader = new ColorReader; 279 parser = new G4GDMLParser(fReader); 280 parser->Read(gdmlFile, false); 281 G4VPhysicalVolume* World = parser->GetWorldVolume(); 282 //----- GDML parser makes world invisible, this is a hack to make it 283 // visible again... 284 G4LogicalVolume* pWorldLogical = World->GetLogicalVolume(); 285 pWorldLogical->SetVisAttributes(0); 286 G4cout << World->GetTranslation() << G4endl << G4endl; 287 if(verbose) 288 { 289 G4cout << "Found World: " << World->GetName() << G4endl; 290 G4cout << "World LV: " << World->GetLogicalVolume()->GetName() << G4endl; 291 } 292 G4LogicalVolumeStore* pLVStore = G4LogicalVolumeStore::GetInstance(); 293 if(verbose) 294 { 295 G4cout << "Found " << pLVStore->size() << " logical volumes." << G4endl 296 << G4endl; 297 } 298 G4PhysicalVolumeStore* pPVStore = G4PhysicalVolumeStore::GetInstance(); 299 if(verbose) 300 { 301 G4cout << "Found " << pPVStore->size() << " physical volumes." << G4endl 302 << G4endl; 303 } 304 } 305 306 void DetectorConstruction::UpdateGeometry() 307 { 308 G4RunManager::GetRunManager()->DefineWorldVolume(Construct()); 309 } 310