Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-04-01 07:50:52

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 /// \file DetectorConstruction.cc
0027 /// \brief Implementation of the DetectorConstruction class
0028 
0029 #include "DetectorConstruction.hh"
0030 
0031 #include "DetectorMessenger.hh"
0032 #include "PrimaryGeneratorAction.hh"
0033 
0034 #include "G4Box.hh"
0035 #include "G4GeometryManager.hh"
0036 #include "G4LogicalVolume.hh"
0037 #include "G4LogicalVolumeStore.hh"
0038 #include "G4Material.hh"
0039 #include "G4NistManager.hh"
0040 #include "G4PVPlacement.hh"
0041 #include "G4PhysicalConstants.hh"
0042 #include "G4PhysicalVolumeStore.hh"
0043 #include "G4RunManager.hh"
0044 #include "G4SolidStore.hh"
0045 #include "G4Sphere.hh"
0046 #include "G4SystemOfUnits.hh"
0047 #include "G4ThreeVector.hh"
0048 #include "globals.hh"
0049 
0050 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0051 
0052 DetectorConstruction::DetectorConstruction()
0053   : fMaterialTracker(nullptr),
0054     fMaterialEmCalo(nullptr),
0055     fMaterialHadCalo(nullptr),
0056     fExperimentalHall_log(nullptr),
0057     fExperimentalHall_phys(nullptr),
0058     fLogicTrackerShell(nullptr),
0059     fPhysiTrackerShell(nullptr),
0060     fLogicEmCaloShell(nullptr),
0061     fPhysiEmCaloShell(nullptr),
0062     fLogicHadCaloShell(nullptr),
0063     fPhysiHadCaloShell(nullptr),
0064     fLogicScoringTrackerShell(nullptr),
0065     fPhysiScoringTrackerShell(nullptr),
0066     fLogicScoringEmCaloShell(nullptr),
0067     fPhysiScoringEmCaloShell(nullptr),
0068     fLogicScoringHadCaloShell(nullptr),
0069     fPhysiScoringHadCaloShell(nullptr),
0070     fDetectorMessenger(nullptr),
0071     fInnerRadiusTracker(10.0 * cm),
0072     fOuterRadiusTracker(20.0 * cm),  //***LOOKHERE*** Default radii
0073     fInnerRadiusEmCalo(30.0 * cm),
0074     fOuterRadiusEmCalo(60.0 * cm),
0075     fInnerRadiusHadCalo(70.0 * cm),
0076     fOuterRadiusHadCalo(170.0 * cm)
0077 {
0078   // G4cout << " BEGIN  DetectorConstruction::DetectorConstruction()" << G4endl;
0079   fMaterialTracker = G4NistManager::Instance()->FindOrBuildMaterial("G4_Si");  //***LOOKHERE***
0080                                                                                // Default material
0081   fMaterialEmCalo = G4NistManager::Instance()->FindOrBuildMaterial("G4_PbWO4");
0082   fMaterialHadCalo = G4NistManager::Instance()->FindOrBuildMaterial("G4_Fe");
0083   fDetectorMessenger = new DetectorMessenger(this);
0084   // G4cout << " END  DetectorConstruction::DetectorConstruction()" << G4endl;
0085 }
0086 
0087 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0088 
0089 DetectorConstruction::~DetectorConstruction()
0090 {
0091   delete fDetectorMessenger;
0092 }
0093 
0094 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0095 
0096 G4VPhysicalVolume* DetectorConstruction::Construct()
0097 {
0098   // G4cout << " BEGIN  DetectorConstruction::Construct()" << G4endl;
0099   return ConstructDetector();
0100 }
0101 
0102 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0103 
0104 G4VPhysicalVolume* DetectorConstruction::ConstructDetector()
0105 {
0106   // G4cout << " BEGIN  DetectorConstruction::ConstructDetector()" << G4endl;
0107 
0108   // Clean old geometry, if any.
0109   G4GeometryManager::GetInstance()->OpenGeometry();
0110 
0111   G4PhysicalVolumeStore::GetInstance()->Clean();
0112   G4LogicalVolumeStore::GetInstance()->Clean();
0113   G4SolidStore::GetInstance()->Clean();
0114 
0115   // Check that the radii are resonable
0116   G4bool isOK = true;
0117   if (fInnerRadiusTracker < 0.0 || fOuterRadiusTracker < fInnerRadiusTracker
0118       || fInnerRadiusEmCalo < fOuterRadiusTracker + fScoringThickness
0119       || fOuterRadiusEmCalo < fInnerRadiusEmCalo
0120       || fInnerRadiusHadCalo < fOuterRadiusEmCalo + fScoringThickness
0121       || fOuterRadiusHadCalo < fInnerRadiusHadCalo)
0122   {
0123     isOK = false;
0124   }
0125   if (!isOK) {
0126     G4cerr << G4endl << "ERROR: the radii are inconsistent !" << G4endl
0127            << " InnerRadiusTracker = " << fInnerRadiusTracker << " mm" << G4endl
0128            << " OuterRadiusTracker = " << fOuterRadiusTracker << " mm" << G4endl
0129            << " InnerRadiusEmCalo  = " << fInnerRadiusEmCalo << " mm" << G4endl
0130            << " OuterRadiusEmCalo  = " << fOuterRadiusEmCalo << " mm" << G4endl
0131            << " InnerRadiusHadCalo = " << fInnerRadiusHadCalo << " mm" << G4endl
0132            << " OuterRadiusHadCalo = " << fOuterRadiusHadCalo << " mm" << G4endl
0133            << " ScoringThickness   = " << fScoringThickness << " mm" << G4endl << G4endl;
0134     return nullptr;
0135   }
0136 
0137   // The detector consists of 3 concentric full spherical shells (G4Sphere),
0138   // positioned at the center, (0.0, 0.0, 0.0).
0139   // The world volume (experimental hall) is a box 10% bigger than the outmost
0140   // spherical shell.
0141   // and it is filled of "G4_Galactic" material.
0142 
0143   G4double expHall_x = 1.1 * fOuterRadiusHadCalo;  // half dimension along x
0144   G4double expHall_y = 1.1 * fOuterRadiusHadCalo;  // half dimension along y
0145   G4double expHall_z = 1.1 * fOuterRadiusHadCalo;  // half dimension along z
0146 
0147   G4Material* vacuum = G4NistManager::Instance()->FindOrBuildMaterial("G4_Galactic");
0148 
0149   G4Box* experimentalHall_box = new G4Box("expHall_box", expHall_x, expHall_y, expHall_z);
0150 
0151   fExperimentalHall_log = new G4LogicalVolume(experimentalHall_box,  // solid
0152                                               vacuum,  // material
0153                                               "expHall_log",  // name
0154                                               0,  // field manager
0155                                               0,  // sensitive detector
0156                                               0);  // user limits
0157 
0158   fExperimentalHall_phys = new G4PVPlacement(0,  // rotation
0159                                              G4ThreeVector(),  // translation
0160                                              "expHall",  // name
0161                                              fExperimentalHall_log,  // logical volume
0162                                              0,  // mother physical volume
0163                                              false,  // boolean operation
0164                                              0);  // copy number
0165 
0166   // 1st (innermost) spherical shell: Tracker
0167   G4Sphere* solidTrackerShell = new G4Sphere("solidTrackerShell",  // name
0168                                              fInnerRadiusTracker,  // Inner radius
0169                                              fOuterRadiusTracker,  // Outer radius
0170                                              0.0,  // Starting Phi angle of the
0171                                                    // segment in radians
0172                                              2.0 * CLHEP::pi,  // Delta Phi angle of the
0173                                                                // segment in radians
0174                                              0.0,  // Starting Theta angle of
0175                                                    // the segment in radians
0176                                              CLHEP::pi);  // Delta Theta angle of the
0177                                                           // segment in radians
0178   fLogicTrackerShell = new G4LogicalVolume(solidTrackerShell,  // solid
0179                                            fMaterialTracker,  // material
0180                                            "logicTrackerShell",  // name
0181                                            0,  // field manager
0182                                            0,  // sensitive detector
0183                                            0);  // user limits
0184   fPhysiTrackerShell = new G4PVPlacement(0,  // rotation
0185                                          G4ThreeVector(),  // translation
0186                                          "physiTrackerShell",  // name
0187                                          fLogicTrackerShell,  // logical volume
0188                                          fExperimentalHall_phys,  // mother physical volume
0189                                          false,  // boolean operation
0190                                          0);  // copy number
0191 
0192   // Scoring tracker shell (a thin vacuum layer, immediately outside the Tracker shell)
0193   G4Sphere* solidScoringTrackerShell =
0194     new G4Sphere("solidScoringTrackerShell",  // name
0195                  fOuterRadiusTracker,  // Inner radius
0196                  fOuterRadiusTracker + fScoringThickness,  // Outer radius
0197                  0.0,  // Starting Phi angle of the segment
0198                        // in radians
0199                  2.0 * CLHEP::pi,  // Delta Phi angle of the segment
0200                                    // in radians
0201                  0.0,  // Starting Theta angle of the segment
0202                        // in radians
0203                  CLHEP::pi);  // Delta Theta angle of the segment
0204                               // in radians
0205   fLogicScoringTrackerShell = new G4LogicalVolume(solidScoringTrackerShell,  // solid
0206                                                   vacuum,  // material
0207                                                   "logicScoringTrackerShell",  // name
0208                                                   0,  // field manager
0209                                                   0,  // sensitive
0210                                                       // detector
0211                                                   0);  // user limits
0212   fPhysiScoringTrackerShell = new G4PVPlacement(0,  // rotation
0213                                                 G4ThreeVector(),  // translation
0214                                                 "physiScoringTrackerShell",  // name
0215                                                 fLogicScoringTrackerShell,  // logical volume
0216                                                 fExperimentalHall_phys,  // mother physical
0217                                                                          // volume
0218                                                 false,  // boolean
0219                                                         // operation
0220                                                 0);  // copy number
0221 
0222   // 2nd (middle) spherical shell: EM Calo
0223   G4Sphere* solidEmCaloShell = new G4Sphere("solidEmCaloShell",  // name
0224                                             fInnerRadiusEmCalo,  // Inner radius
0225                                             fOuterRadiusEmCalo,  // Outer radius
0226                                             0.0,  // Starting Phi angle of the
0227                                                   // segment in radians
0228                                             2.0 * CLHEP::pi,  // Delta Phi angle of the
0229                                                               // segment in radians
0230                                             0.0,  // Starting Theta angle of the
0231                                                   // segment in radians
0232                                             CLHEP::pi);  // Delta Theta angle of the
0233                                                          // segment in radians
0234   fLogicEmCaloShell = new G4LogicalVolume(solidEmCaloShell,  // solid
0235                                           fMaterialEmCalo,  // material
0236                                           "logicEmCaloShell",  // name
0237                                           0,  // field manager
0238                                           0,  // sensitive detector
0239                                           0);  // user limits
0240   fPhysiEmCaloShell = new G4PVPlacement(0,  // rotation
0241                                         G4ThreeVector(),  // translation
0242                                         "physiEmCaloShell",  // name
0243                                         fLogicEmCaloShell,  // logical volume
0244                                         fExperimentalHall_phys,  // mother physical volume
0245                                         false,  // boolean operation
0246                                         0);  // copy number
0247 
0248   // Scoring EmCalo shell (a thin vacuum layer, immediately outside the EmCalo shell)
0249   G4Sphere* solidScoringEmCaloShell =
0250     new G4Sphere("solidScoringEmCaloShell",  // name
0251                  fOuterRadiusEmCalo,  // Inner radius
0252                  fOuterRadiusEmCalo + fScoringThickness,  // Outer radius
0253                  0.0,  // Starting Phi angle of the segment
0254                        // in radians
0255                  2.0 * CLHEP::pi,  // Delta Phi angle of the segment
0256                                    // in radians
0257                  0.0,  // Starting Theta angle of the
0258                        // segment in radians
0259                  CLHEP::pi);  // Delta Theta angle of the segment
0260                               // in radians
0261   fLogicScoringEmCaloShell = new G4LogicalVolume(solidScoringEmCaloShell,  // solid
0262                                                  vacuum,  // material
0263                                                  "logicScoringEmCaloShell",  // name
0264                                                  0,  // field manager
0265                                                  0,  // sensitive
0266                                                      // detector
0267                                                  0);  // user limits
0268   fPhysiScoringEmCaloShell = new G4PVPlacement(0,  // rotation
0269                                                G4ThreeVector(),  // translation
0270                                                "physiScoringEmCaloShell",  // name
0271                                                fLogicScoringEmCaloShell,  // logical volume
0272                                                fExperimentalHall_phys,  // mother physical
0273                                                                         // volume
0274                                                false,  // boolean operation
0275                                                0);  // copy number
0276 
0277   // 3rd (outmost) spherical shell: HAD Calo
0278   G4Sphere* solidHadCaloShell = new G4Sphere("solidHadCaloShell",  // name
0279                                              fInnerRadiusHadCalo,  // Inner radius
0280                                              fOuterRadiusHadCalo,  // Outer radius
0281                                              0.0,  // Starting Phi angle of the
0282                                                    // segment in radians
0283                                              2.0 * CLHEP::pi,  // Delta Phi angle of the
0284                                                                // segment in radians
0285                                              0.0,  // Starting Theta angle of
0286                                                    // the segment in radians
0287                                              CLHEP::pi);  // Delta Theta angle of the
0288                                                           // segment in radians
0289   fLogicHadCaloShell = new G4LogicalVolume(solidHadCaloShell,  // solid
0290                                            fMaterialHadCalo,  // material
0291                                            "logicHadCaloShell",  // name
0292                                            0,  // field manager
0293                                            0,  // sensitive detector
0294                                            0);  // user limits
0295   fPhysiHadCaloShell = new G4PVPlacement(0,  // rotation
0296                                          G4ThreeVector(),  // translation
0297                                          "physiHadCaloShell",  // name
0298                                          fLogicHadCaloShell,  // logical volume
0299                                          fExperimentalHall_phys,  // mother physical volume
0300                                          false,  // boolean operation
0301                                          0);  // copy number
0302 
0303   // Scoring HadCalo shell (a thin vacuum layer, immediately outside the HadCalo shell)
0304   G4Sphere* solidScoringHadCaloShell =
0305     new G4Sphere("solidScoringHadCaloShell",  // name
0306                  fOuterRadiusHadCalo,  // Inner radius
0307                  fOuterRadiusHadCalo + fScoringThickness,  // Outer radius
0308                  0.0,  // Starting Phi angle of the
0309                        // segment in radians
0310                  2.0 * CLHEP::pi,  // Delta Phi angle of the segment
0311                                    // in radians
0312                  0.0,  // Starting Theta angle of the
0313                        // segment in radians
0314                  CLHEP::pi);  // Delta Theta angle of the segment
0315                               // in radians
0316   fLogicScoringHadCaloShell = new G4LogicalVolume(solidScoringHadCaloShell,  // solid
0317                                                   vacuum,  // material
0318                                                   "logicScoringHadCaloShell",  // name
0319                                                   0,  // field manager
0320                                                   0,  // sensitive
0321                                                       // detector
0322                                                   0);  // user limits
0323   fPhysiScoringHadCaloShell = new G4PVPlacement(0,  // rotation
0324                                                 G4ThreeVector(),  // translation
0325                                                 "physiScoringHadCaloShell",  // name
0326                                                 fLogicScoringHadCaloShell,  // logical volume
0327                                                 fExperimentalHall_phys,  // mother physical
0328                                                                          // volume
0329                                                 false,  // boolean
0330                                                         // operation
0331                                                 0);  // copy number
0332 
0333   G4cout << "DetectorConstruction::ConstructSphere() : " << G4endl
0334          << "\t World (box) size: " << G4endl << "\t \t x : -/+ " << expHall_x << " mm ;"
0335          << "\t y : -/+ " << expHall_y << " mm ;"
0336          << "\t z : -/+ " << expHall_z << " mm ;" << G4endl << G4endl;
0337   PrintParameters();
0338   // G4cout << " END  DetectorConstruction::ConstructDetector()
0339 
0340   return fExperimentalHall_phys;
0341 }
0342 
0343 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0344 
0345 void DetectorConstruction::SetMaterialTracker(const G4String name)
0346 {
0347   fMaterialTracker = G4NistManager::Instance()->FindOrBuildMaterial(name);
0348   if (!fMaterialTracker) {
0349     G4cout << G4endl << G4endl << "WARNING: the name of the material has not been recognized!"
0350            << G4endl << "     ===> the default  * G4_Si *  will be used." << G4endl << G4endl;
0351     fMaterialTracker = G4NistManager::Instance()->FindOrBuildMaterial("G4_Si");
0352   }
0353   if (fLogicTrackerShell) fLogicTrackerShell->SetMaterial(fMaterialTracker);
0354 }
0355 
0356 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0357 
0358 void DetectorConstruction::SetMaterialEmCalo(const G4String name)
0359 {
0360   fMaterialEmCalo = G4NistManager::Instance()->FindOrBuildMaterial(name);
0361   if (!fMaterialEmCalo) {
0362     G4cout << G4endl << G4endl << "WARNING: the name of the material has not been recognized!"
0363            << G4endl << "     ===> the default  * G4_Pb *  will be used." << G4endl << G4endl;
0364     fMaterialEmCalo = G4NistManager::Instance()->FindOrBuildMaterial("G4_Pb");
0365   }
0366   if (fLogicEmCaloShell) fLogicEmCaloShell->SetMaterial(fMaterialEmCalo);
0367 }
0368 
0369 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0370 
0371 void DetectorConstruction::SetMaterialHadCalo(const G4String name)
0372 {
0373   fMaterialHadCalo = G4NistManager::Instance()->FindOrBuildMaterial(name);
0374   if (fMaterialHadCalo == nullptr) {
0375     G4cout << G4endl << G4endl << "WARNING: the name of the material has not been recognized!"
0376            << G4endl << "     ===> the default  * G4_Fe *  will be used." << G4endl << G4endl;
0377     fMaterialHadCalo = G4NistManager::Instance()->FindOrBuildMaterial("G4_Fe");
0378   }
0379   if (fLogicHadCaloShell) fLogicHadCaloShell->SetMaterial(fMaterialHadCalo);
0380 }
0381 
0382 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0383 
0384 void DetectorConstruction::UpdateGeometry()
0385 {
0386   // G4cout << " BEGIN  DetectorConstruction::UpdateGeometry" << G4endl;
0387   G4RunManager::GetRunManager()->ReinitializeGeometry();
0388   PrintParameters();
0389   // Update also the position of the gun
0390   const PrimaryGeneratorAction* pPrimaryAction = dynamic_cast<const PrimaryGeneratorAction*>(
0391     G4RunManager::GetRunManager()->GetUserPrimaryGeneratorAction());
0392   if (pPrimaryAction) pPrimaryAction->SetGunPosition();
0393   // G4cout << " END  DetectorConstruction::UpdateGeometry" << G4endl;
0394 }
0395 
0396 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
0397 
0398 void DetectorConstruction::PrintParameters()
0399 {
0400   G4cout << G4endl << " ------  DetectorConstruction::PrintParameters() ------ " << G4endl
0401          << " MaterialTracker = " << fMaterialTracker->GetName() << G4endl
0402          << " MaterialEmCalo  = " << fMaterialEmCalo->GetName() << G4endl
0403          << " MaterialHadCalo = " << fMaterialHadCalo->GetName() << G4endl
0404          << " InnerRadiusTracker = " << fInnerRadiusTracker << " mm" << G4endl
0405          << " OuterRadiusTracker = " << fOuterRadiusTracker << " mm" << G4endl
0406          << " InnerRadiusEmCalo  = " << fInnerRadiusEmCalo << " mm" << G4endl
0407          << " OuterRadiusEmCalo  = " << fOuterRadiusEmCalo << " mm" << G4endl
0408          << " InnerRadiusHadCalo = " << fInnerRadiusHadCalo << " mm" << G4endl
0409          << " OuterRadiusHadCalo = " << fOuterRadiusHadCalo << " mm" << G4endl
0410          << " ScoringThickness   = " << fScoringThickness << " mm" << G4endl
0411          << " -------------------------------------------------------- " << G4endl << G4endl;
0412 }
0413 
0414 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......