Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Geant4Manager.cpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file Geant4Manager.cpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2023 CERN for the benefit of the Acts project
4 //
5 // This Source Code Form is subject to the terms of the Mozilla Public
6 // License, v. 2.0. If a copy of the MPL was not distributed with this
7 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 
10 
12 
13 #include <memory>
14 #include <stdexcept>
15 
16 #include <FTFP_BERT.hh>
17 #include <FTFP_BERT_ATL.hh>
18 #include <G4EmParameters.hh>
19 #include <G4HadronicParameters.hh>
20 #include <G4HadronicProcessStore.hh>
21 #include <G4Profiler.hh>
22 #include <G4RunManager.hh>
23 #include <G4RunManagerFactory.hh>
24 #include <G4UserEventAction.hh>
25 #include <G4UserRunAction.hh>
26 #include <G4UserSteppingAction.hh>
27 #include <G4UserTrackingAction.hh>
28 #include <G4VUserDetectorConstruction.hh>
29 #include <G4VUserPhysicsList.hh>
30 #include <G4VUserPrimaryGeneratorAction.hh>
31 #include <G4Version.hh>
32 
33 namespace ActsExamples {
34 
36  std::unique_ptr<G4RunManager> _runManager,
37  std::unique_ptr<G4VUserPhysicsList> _physicsList,
38  std::string _physicsListName)
39  : logLevel(_logLevel),
40  runManager(std::move(_runManager)),
41  physicsList(_physicsList.release()),
42  physicsListName(std::move(_physicsListName)) {
43  if (runManager == nullptr) {
44  std::invalid_argument("runManager cannot be null");
45  }
46  if (physicsList == nullptr) {
47  std::invalid_argument("physicsList cannot be null");
48  }
49 
50  // Set physics list
51  runManager->SetUserInitialization(physicsList);
52 }
53 
54 Geant4Handle::~Geant4Handle() = default;
55 
58 }
59 
61  static Geant4Manager manager;
62  return manager;
63 }
64 
65 void Geant4Manager::tweakLogging(G4RunManager& runManager, int level) {
66  runManager.SetVerboseLevel(level);
67  G4EventManager::GetEventManager()->SetVerboseLevel(level);
68  G4EventManager::GetEventManager()->GetTrackingManager()->SetVerboseLevel(
69  level);
70  G4EventManager::GetEventManager()->GetStackManager()->SetVerboseLevel(level);
71 
72  // Suppress the printing of physics information.
73 #if G4VERSION_NUMBER >= 1100
74  G4HadronicParameters::Instance()->SetVerboseLevel(0);
75  G4HadronicProcessStore::Instance()->SetVerbose(0);
76  G4EmParameters::Instance()->SetIsPrintedFlag(true);
77 #endif
78 }
79 
80 std::shared_ptr<Geant4Handle> Geant4Manager::currentHandle() const {
81  return m_handle.lock();
82 }
83 
84 std::shared_ptr<Geant4Handle> Geant4Manager::createHandle(
85  int logLevel, const std::string& physicsList) {
86  return createHandle(logLevel, createPhysicsList(physicsList), physicsList);
87 }
88 
89 std::shared_ptr<Geant4Handle> Geant4Manager::createHandle(
90  int logLevel, std::unique_ptr<G4VUserPhysicsList> physicsList,
91  std::string physicsListName) {
92  if (!m_handle.expired()) {
93  throw std::runtime_error("creating a second handle is prohibited");
94  }
95  if (m_created) {
96  throw std::runtime_error(
97  "creating a new handle is prohibited. you have to hold onto the "
98  "first one.");
99  }
100 
101  auto runManager = std::unique_ptr<G4RunManager>(
102  G4RunManagerFactory::CreateRunManager(G4RunManagerType::SerialOnly));
103 
104  auto handle = std::make_shared<Geant4Handle>(logLevel, std::move(runManager),
105  std::move(physicsList),
106  std::move(physicsListName));
107 
108  m_created = true;
109  m_handle = handle;
110  return handle;
111 }
112 
114  std::string name, std::shared_ptr<PhysicsListFactory> physicsListFactory) {
115  if (m_physicsListFactories.find(name) != m_physicsListFactories.end()) {
116  throw std::invalid_argument("name already mapped");
117  }
118  m_physicsListFactories.emplace(std::move(name),
119  std::move(physicsListFactory));
120 }
121 
122 std::unique_ptr<G4VUserPhysicsList> Geant4Manager::createPhysicsList(
123  const std::string& name) const {
124  auto it = m_physicsListFactories.find(name);
125  if (it == m_physicsListFactories.end()) {
126  throw std::invalid_argument("name not mapped");
127  }
128  return it->second->factorize();
129 }
130 
131 const std::unordered_map<std::string, std::shared_ptr<PhysicsListFactory>>&
133  return m_physicsListFactories;
134 }
135 
138  "FTFP_BERT", std::make_shared<PhysicsListFactoryFunction>(
139  []() { return std::make_unique<FTFP_BERT>(); }));
141  "FTFP_BERT_ATL", std::make_shared<PhysicsListFactoryFunction>(
142  []() { return std::make_unique<FTFP_BERT_ATL>(); }));
143 }
144 
146 
147 } // namespace ActsExamples