File indexing completed on 2025-01-18 09:11:36
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include "ActsExamples/Geant4/Geant4Manager.hpp"
0010
0011 #include "ActsExamples/Geant4/MaterialPhysicsList.hpp"
0012 #include "ActsExamples/Geant4/PhysicsListFactory.hpp"
0013
0014 #include <memory>
0015 #include <stdexcept>
0016
0017 #include <FTFP_BERT.hh>
0018 #include <FTFP_BERT_ATL.hh>
0019 #include <G4EmParameters.hh>
0020 #include <G4HadronicParameters.hh>
0021 #include <G4HadronicProcessStore.hh>
0022 #include <G4RunManager.hh>
0023 #include <G4RunManagerFactory.hh>
0024 #include <G4UserEventAction.hh>
0025 #include <G4UserRunAction.hh>
0026 #include <G4UserSteppingAction.hh>
0027 #include <G4UserTrackingAction.hh>
0028 #include <G4VUserDetectorConstruction.hh>
0029 #include <G4VUserPhysicsList.hh>
0030 #include <G4VUserPrimaryGeneratorAction.hh>
0031 #include <G4Version.hh>
0032
0033 namespace ActsExamples {
0034
0035 Geant4Handle::Geant4Handle(std::unique_ptr<G4RunManager> _runManager,
0036 std::unique_ptr<G4VUserPhysicsList> _physicsList,
0037 std::string _physicsListName)
0038 : runManager(std::move(_runManager)),
0039 physicsList(_physicsList.release()),
0040 physicsListName(std::move(_physicsListName)) {
0041 if (runManager == nullptr) {
0042 std::invalid_argument("runManager cannot be null");
0043 }
0044 if (physicsList == nullptr) {
0045 std::invalid_argument("physicsList cannot be null");
0046 }
0047
0048
0049 runManager->SetUserInitialization(physicsList);
0050 }
0051
0052 Geant4Handle::~Geant4Handle() = default;
0053
0054 void Geant4Handle::tweakLogging(int level) const {
0055 Geant4Manager::tweakLogging(*runManager, level);
0056 }
0057
0058 Geant4Manager& Geant4Manager::instance() {
0059 static Geant4Manager manager;
0060 return manager;
0061 }
0062
0063 void Geant4Manager::tweakLogging(G4RunManager& runManager, int level) {
0064 runManager.SetVerboseLevel(level);
0065 G4EventManager::GetEventManager()->SetVerboseLevel(level);
0066 G4EventManager::GetEventManager()->GetTrackingManager()->SetVerboseLevel(
0067 level);
0068 G4EventManager::GetEventManager()->GetStackManager()->SetVerboseLevel(level);
0069
0070
0071 #if G4VERSION_NUMBER >= 1100
0072 G4HadronicParameters::Instance()->SetVerboseLevel(0);
0073 G4HadronicProcessStore::Instance()->SetVerbose(0);
0074 G4EmParameters::Instance()->SetIsPrintedFlag(true);
0075 #endif
0076 }
0077
0078 std::shared_ptr<Geant4Handle> Geant4Manager::currentHandle() const {
0079 return m_handle.lock();
0080 }
0081
0082 std::shared_ptr<Geant4Handle> Geant4Manager::createHandle(
0083 const std::string& physicsList) {
0084 return createHandle(createPhysicsList(physicsList), physicsList);
0085 }
0086
0087 std::shared_ptr<Geant4Handle> Geant4Manager::createHandle(
0088 std::unique_ptr<G4VUserPhysicsList> physicsList,
0089 std::string physicsListName) {
0090 if (!m_handle.expired()) {
0091 throw std::runtime_error("creating a second handle is prohibited");
0092 }
0093 if (m_created) {
0094 throw std::runtime_error(
0095 "creating a new handle is prohibited. you have to hold onto the "
0096 "first one.");
0097 }
0098
0099 auto runManager = std::unique_ptr<G4RunManager>(
0100 G4RunManagerFactory::CreateRunManager(G4RunManagerType::SerialOnly));
0101
0102 auto handle = std::make_shared<Geant4Handle>(std::move(runManager),
0103 std::move(physicsList),
0104 std::move(physicsListName));
0105
0106 m_created = true;
0107 m_handle = handle;
0108 return handle;
0109 }
0110
0111 void Geant4Manager::registerPhysicsListFactory(
0112 std::string name,
0113 std::shared_ptr<Geant4::PhysicsListFactory> physicsListFactory) {
0114 if (m_physicsListFactories.contains(name)) {
0115 throw std::invalid_argument("name already mapped");
0116 }
0117 m_physicsListFactories.emplace(std::move(name),
0118 std::move(physicsListFactory));
0119 }
0120
0121 std::unique_ptr<G4VUserPhysicsList> Geant4Manager::createPhysicsList(
0122 const std::string& name) const {
0123 auto it = m_physicsListFactories.find(name);
0124 if (it == m_physicsListFactories.end()) {
0125 throw std::invalid_argument("name not mapped");
0126 }
0127 return it->second->factorize();
0128 }
0129
0130 const std::unordered_map<std::string,
0131 std::shared_ptr<Geant4::PhysicsListFactory>>&
0132 Geant4Manager::getPhysicsListFactories() const {
0133 return m_physicsListFactories;
0134 }
0135
0136 Geant4Manager::Geant4Manager() {
0137 registerPhysicsListFactory(
0138 "FTFP_BERT", std::make_shared<Geant4::PhysicsListFactoryFunction>(
0139 []() { return std::make_unique<FTFP_BERT>(); }));
0140 registerPhysicsListFactory(
0141 "FTFP_BERT_ATL", std::make_shared<Geant4::PhysicsListFactoryFunction>(
0142 []() { return std::make_unique<FTFP_BERT_ATL>(); }));
0143 registerPhysicsListFactory(
0144 "MaterialPhysicsList",
0145 std::make_shared<Geant4::PhysicsListFactoryFunction>(
0146 []() { return std::make_unique<Geant4::MaterialPhysicsList>(); }));
0147 }
0148
0149 Geant4Manager::~Geant4Manager() = default;
0150
0151 }