14 #ifndef DD4HEP_DDG4_GEANT4FIELDTRACKINGSETUP_H
15 #define DD4HEP_DDG4_GEANT4FIELDTRACKINGSETUP_H 1
121 #endif // DD4HEP_DDG4_GEANT4FIELDTRACKINGSETUP_H
143 #include <G4TransportationManager.hh>
144 #include <G4MagIntegratorStepper.hh>
145 #include <G4Mag_EqRhs.hh>
146 #include <G4ChordFinder.hh>
147 #include <G4PropagatorInField.hh>
155 struct Geant4SetupPropertyMap {
156 const std::map<std::string,std::string>& vals;
157 Geant4SetupPropertyMap(
const std::map<std::string,std::string>&
v) : vals(
v) {}
158 std::string value(
const std::string&
key)
const;
159 double toDouble(
const std::string&
key)
const;
160 bool operator[](
const std::string&
key)
const {
return vals.find(
key) != vals.end(); }
163 std::string Geant4SetupPropertyMap::value(
const std::string&
key)
const {
164 dd4hep::Detector::PropertyValues::const_iterator iV = vals.find(
key);
165 return iV == vals.end() ?
"" : (*iV).second;
168 double Geant4SetupPropertyMap::toDouble(
const std::string&
key)
const {
192 G4ChordFinder* chordFinder;
193 G4TransportationManager* transportMgr;
194 G4PropagatorInField* propagator;
195 G4FieldManager* fieldManager;
197 G4Mag_EqRhs* mag_equation = PluginService::Create<G4Mag_EqRhs*>(
eq_typ,mag_field);
198 G4EquationOfMotion* mag_eq = mag_equation;
199 if (
nullptr == mag_eq ) {
200 mag_eq = PluginService::Create<G4EquationOfMotion*>(
eq_typ,mag_field);
201 if (
nullptr == mag_eq ) {
202 except(
"FieldSetup",
"Cannot create G4EquationOfMotion of type: %s.",
eq_typ.c_str());
205 G4MagIntegratorStepper* fld_stepper = PluginService::Create<G4MagIntegratorStepper*>(
stepper_typ,mag_eq);
206 if (
nullptr == fld_stepper ) {
207 fld_stepper = PluginService::Create<G4MagIntegratorStepper*>(
stepper_typ,mag_equation);
208 if (
nullptr == fld_stepper ) {
209 except(
"FieldSetup",
"Cannot create stepper of type: %s.",
stepper_typ.c_str());
212 chordFinder =
new G4ChordFinder(mag_field,
min_chord_step,fld_stepper);
213 transportMgr = G4TransportationManager::GetTransportationManager();
214 propagator = transportMgr->GetPropagatorInField();
215 fieldManager = transportMgr->GetFieldManager();
218 fieldManager->SetDetectorField(mag_field);
219 fieldManager->SetChordFinder(chordFinder);
228 propagator->SetMinimumEpsilonStep(
eps_min);
230 propagator->SetMaximumEpsilonStep(
eps_max);
241 const std::map<std::string,std::string>& vals)
245 Geant4SetupPropertyMap pm(values);
246 dd4hep::Detector::PropertyValues::const_iterator iV = values.find(
"min_chord_step");
247 eq_typ = pm.value(
"equation");
248 stepper_typ = pm.value(
"stepper");
249 min_chord_step =
dd4hep::_toDouble((iV==values.end()) ? std::string(
"1e-2 * mm") : (*iV).second);
250 if ( pm[
"eps_min"] ) eps_min = pm.toDouble(
"eps_min");
251 if ( pm[
"eps_max"] ) eps_max = pm.toDouble(
"eps_max");
252 if ( pm[
"delta_chord"] ) delta_chord = pm.toDouble(
"delta_chord");
253 if ( pm[
"delta_one_step"] ) delta_one_step = pm.toDouble(
"delta_one_step");
254 if ( pm[
"delta_intersection"] ) delta_intersection = pm.toDouble(
"delta_intersection");
255 if ( pm[
"largest_step"] ) largest_step = pm.toDouble(
"largest_step");
257 virtual ~XMLFieldTrackingSetup() {}
259 return setup.execute(description);
280 printout( INFO,
"FieldSetup",
"Geant4 magnetic field tracking configured.");
281 printout( INFO,
"FieldSetup",
"G4MagIntegratorStepper:%s G4Mag_EqRhs:%s",
283 printout( INFO,
"FieldSetup",
"Epsilon:[min:%f mm max:%f mm]",
eps_min,
eps_max);
284 printout( INFO,
"FieldSetup",
"Delta:[chord:%f 1-step:%f intersect:%f] LargestStep %f mm",
307 printout( INFO,
"FieldSetup",
"Geant4 magnetic field tracking configured.");
308 printout( INFO,
"FieldSetup",
"G4MagIntegratorStepper:%s G4Mag_EqRhs:%s",
310 printout( INFO,
"FieldSetup",
"Epsilon:[min:%f mm max:%f mm]",
eps_min,
eps_max);
311 printout( INFO,
"FieldSetup",
"Delta:[chord:%f 1-step:%f intersect:%f] LargestStep %f mm",