ATLAS Offline Software
Loading...
Searching...
No Matches
Simulation::GenEventBeamEffectBooster Class Reference

This tool takes a HepMC::GenEvent and applies boosts due to beam tilt, etc. More...

#include <GenEventBeamEffectBooster.h>

Inheritance diagram for Simulation::GenEventBeamEffectBooster:
Collaboration diagram for Simulation::GenEventBeamEffectBooster:

Public Member Functions

 GenEventBeamEffectBooster (const std::string &t, const std::string &n, const IInterface *p)
 Constructor with parameters.
StatusCode initialize () override final
 Athena algtool's Hooks.
StatusCode finalize () override final
 Athena algtool's Hooks.
StatusCode initializeAthenaEvent ()
StatusCode manipulate (HepMC::GenEvent &ge, const EventContext &ctx) const override final
 modifies the given GenEvent

Private Member Functions

StatusCode initializeGenEvent (CLHEP::HepLorentzRotation &transform, const EventContext &ctx) const
 calculate the transformations that we want to apply to the particles in the current GenEvent
void boostParticle (HepMC::GenParticlePtr &p, const CLHEP::HepLorentzRotation &transform) const
 apply boost to individual GenParticles

Private Attributes

ServiceHandle< IAthRNGSvcm_rndGenSvc {this, "RandomSvc", "AthRNGSvc"}
ATHRNG::RNGWrapper *m_randomEngine ATLAS_THREAD_SAFE {}
 Slot-local RNG.
Gaudi::Property< std::string > m_randomEngineName {this, "RandomStream", "BEAM"}
 Name of the random number stream.
Gaudi::Property< bool > m_applyBoost {this, "ApplyBoost", true}
Gaudi::Property< bool > m_applyDivergence {this, "ApplyDivergence", true}
Gaudi::Property< double > m_sigma_px_b1 {this, "Sigma_px_b1", 20.e-6, "angular divergence in x of beam 1 [rad]"}
Gaudi::Property< double > m_sigma_px_b2 {this, "Sigma_px_b2", 21.e-6, "angular divergence in x of beam 2 [rad]"}
Gaudi::Property< double > m_sigma_py_b1 {this, "Sigma_py_b1", 22.e-6, "angular divergence in y of beam 1 [rad]"}
Gaudi::Property< double > m_sigma_py_b2 {this, "Sigma_py_b2", 23.e-6, "angular divergence in y of beam 2 [rad]"}
Gaudi::Property< double > m_xing_x_b1 {this, "HalfXing_x_b1", 19.e-6, "half-crossing in x for beam 1 at IP1, i.e. angle between beam 1 and z-axis"}
Gaudi::Property< double > m_xing_x_b2 {this, "HalfXing_x_b2", 1.e-6, "half-crossing in x for beam 2 at IP1, i.e. angle between beam 2 and z-axis"}
Gaudi::Property< double > m_xing_y_b1 {this, "HalfXing_y_b1", 150.e-6, "half-crossing in y for beam 1 at IP1, i.e. angle between beam 1 and z-axis"}
Gaudi::Property< double > m_xing_y_b2 {this, "HalfXing_y_b2", -152.e-6, "half-crossing in y for beam 2 at IP1, i.e. angle between beam 2 and z-axis"}
Gaudi::Property< double > m_dE {this, "deltaEOverE", 1.1E-4, "Delta_E/E theoretical value"}
Gaudi::Property< double > m_pbeam1 {this, "pbeam1", 3500.0E3, "Beam 1 Momentum / MeV"}
Gaudi::Property< double > m_pbeam2 {this, "pbeam2", 3500.0E3, "Beam 2 Momentum / MeV"}
Gaudi::Property< double > m_beam1ParticleMass {this, "Beam1ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 1"}
Gaudi::Property< double > m_beam2ParticleMass {this, "Beam2ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 2"}

Detailed Description

This tool takes a HepMC::GenEvent and applies boosts due to beam tilt, etc.

based on: https://svnweb.cern.ch/trac/atlasoff/browser/Simulation/G4Atlas/G4AtlasUtilities/trunk/src/BeamEffectTransformation.cxx

Definition at line 38 of file GenEventBeamEffectBooster.h.

Constructor & Destructor Documentation

◆ GenEventBeamEffectBooster()

Simulation::GenEventBeamEffectBooster::GenEventBeamEffectBooster ( const std::string & t,
const std::string & n,
const IInterface * p )

Constructor with parameters.

Constructor.

Definition at line 23 of file GenEventBeamEffectBooster.cxx.

26 : base_class(t,n,p)
27 {
28 }

Member Function Documentation

◆ boostParticle()

void Simulation::GenEventBeamEffectBooster::boostParticle ( HepMC::GenParticlePtr & p,
const CLHEP::HepLorentzRotation & transform ) const
private

apply boost to individual GenParticles

Definition at line 151 of file GenEventBeamEffectBooster.cxx.

153 {
154 // Apply the same transformation for EVERY HepMC::GenParticle
155 const HepMC::FourVector &mom = p->momentum();
156 CLHEP::HepLorentzVector hv(mom.px(), mom.py(), mom.pz(), mom.e()); //TODO check units
157 ATH_MSG_VERBOSE("BEAMBOOST initial momentum " << hv );
158 hv.transform(transform);
159 ATH_MSG_VERBOSE("BEAMBOOST transformed momentum " << hv);
160 p->set_momentum(HepMC::FourVector(hv.px(),hv.py(),hv.pz(),hv.e())); //TODO check units
161 }
#define ATH_MSG_VERBOSE(x)

◆ finalize()

StatusCode Simulation::GenEventBeamEffectBooster::finalize ( )
finaloverride

Athena algtool's Hooks.

Definition at line 47 of file GenEventBeamEffectBooster.cxx.

48 {
49 ATH_MSG_VERBOSE("Finalizing ...");
50 return StatusCode::SUCCESS;
51 }

◆ initialize()

StatusCode Simulation::GenEventBeamEffectBooster::initialize ( )
finaloverride

Athena algtool's Hooks.

Definition at line 32 of file GenEventBeamEffectBooster.cxx.

33 {
34 ATH_MSG_VERBOSE("Initializing ...");
35 // prepare the RandonNumber generation
36 ATH_CHECK(m_rndGenSvc.retrieve());
37 m_randomEngine = m_rndGenSvc->getEngine(this, m_randomEngineName); //FIXME
38 if (!m_randomEngine) {
39 ATH_MSG_ERROR("Could not get random number engine from RandomNumberService. Abort.");
40 return StatusCode::FAILURE;
41 }
42 return StatusCode::SUCCESS;
43 }
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_ERROR(x)
Gaudi::Property< std::string > m_randomEngineName
Name of the random number stream.

◆ initializeAthenaEvent()

StatusCode Simulation::GenEventBeamEffectBooster::initializeAthenaEvent ( )

Definition at line 53 of file GenEventBeamEffectBooster.cxx.

54 {
55 // Refresh properties retrieved from the BeamCondSvc here if
56 // necessary. It may be more thread-safe to retrieve them directly
57 // from the BeamCondSvc during initializeGenEvent though?
58
59 // m_sigma_px_b1 = 20.E-6; // angular divergence in x of beam 1 [rad]
60 // m_sigma_px_b2 = 21.E-6; // angular divergence in x of beam 2 [rad]
61 // m_sigma_py_b1 = 22.E-6; // angular divergence in y of beam 1 [rad]
62 // m_sigma_py_b2 = 23.E-6; // angular divergence in y of beam 2 [rad]
63 // // Crossing angles, note the convention here is taken from online https://atlas-dcs.cern.ch/index.php?page=LHC_INS::INS_BPM
64 // m_xing_x_b1 = 19.E-6; // half-crossing in x for beam 1 at IP1, i.e. angle between beam 1 and z-axis
65 // m_xing_x_b2 = 1.E-6; // half-crossing in x for beam 2 at IP1, i.e. angle between beam 2 and z-axis
66 // m_xing_y_b1 = 150.E-6; // half-crossing in y for beam 1 at IP1, i.e. angle between beam 1 and z-axis
67 // m_xing_y_b2 = -152.E-6; // half-crossing in y for beam 2 at IP1, i.e. angle between beam 2 and z-axis
68 // m_dE = 1.1E-4; // Delta_E/E theoretical value
69 // m_pbeam1 = 3500.0E3; /// @todo Get from a service
70 // m_pbeam2 = 3500.0E3; /// @todo Get from a service
71 // m_beam1ParticleMass = CLHEP::proton_mass_c2;
72 // m_beam2ParticleMass = CLHEP::proton_mass_c2;
73
74 return StatusCode::SUCCESS;
75 }

◆ initializeGenEvent()

StatusCode Simulation::GenEventBeamEffectBooster::initializeGenEvent ( CLHEP::HepLorentzRotation & transform,
const EventContext & ctx ) const
private

calculate the transformations that we want to apply to the particles in the current GenEvent

Definition at line 77 of file GenEventBeamEffectBooster.cxx.

78 {
79 // Reset the transformation
80 transform = CLHEP::HepLorentzRotation(); //TODO drop this
81
82 // Prepare the random engine
83 m_randomEngine->setSeed( name(), ctx );
84 CLHEP::HepRandomEngine* randomEngine(m_randomEngine->getEngine(ctx));
85
86 // Create beam 1 and 2 momenta, including divergence and crossing-angle effects
87 const double px1 = m_pbeam1 * CLHEP::RandGaussZiggurat::shoot(randomEngine, m_xing_x_b2, m_sigma_px_b2);
88 const double py1 = m_pbeam1 * CLHEP::RandGaussZiggurat::shoot(randomEngine, m_xing_y_b2, m_sigma_py_b2);
89 const double pz1 = CLHEP::RandGaussZiggurat::shoot(randomEngine, sqrt(m_pbeam1*m_pbeam1 - px1*px1 - py1*py1), m_dE);
90 const double e1 = sqrt(px1*px1 + py1*py1 + pz1*pz1 + m_beam1ParticleMass*m_beam1ParticleMass);
91 CLHEP::HepLorentzVector pp1(px1, py1, pz1, e1);
92
93 const double px2 = -m_pbeam2 * CLHEP::RandGaussZiggurat::shoot(randomEngine, m_xing_x_b1, m_sigma_px_b1); // crossing angle & divergence
94 const double py2 = -m_pbeam2 * CLHEP::RandGaussZiggurat::shoot(randomEngine, m_xing_y_b1, m_sigma_py_b1);
95 const double pz2 = CLHEP::RandGaussZiggurat::shoot(randomEngine, -sqrt(m_pbeam2*m_pbeam2 - px2*px2 - py2*py2), m_dE); // longitudinal component in + direction energy smeared
96 const double e2 = sqrt(px2*px2 + py2*py2 + pz2*pz2 + m_beam2ParticleMass*m_beam2ParticleMass);
97 CLHEP::HepLorentzVector pp2(px2, py2, pz2, e2);
98
99 // Now set-up rotation-boost matrix
100 const CLHEP::HepLorentzVector psum = pp1 + pp2;
101 const CLHEP::HepLorentzVector& dir = pp1;
102 // Boost psum back on the direction of dir, adapted from bstback & fromCMframe PYTHIA8, credit to T.Sjostrand
103 const double betaX = -psum.x() / psum.t();
104 const double betaY = -psum.y() / psum.t();
105 const double betaZ = -psum.z() / psum.t();
106 const double beta2 = betaX*betaX + betaY*betaY + betaZ*betaZ;
107 const double gamma = 1. / sqrt(1. - beta2);
108 const double prod1 = betaX * dir.x() + betaY * dir.y() + betaZ * dir.z();
109 const double prod2 = gamma * (gamma * prod1 / (1. + gamma) + dir.t());
110 // Get the angle of rotation
111 const CLHEP::HepLorentzVector back(dir.x() + prod2 * betaX,
112 dir.y() + prod2 * betaY,
113 dir.z() + prod2 * betaZ,
114 gamma * (dir.t() + prod1));
115 const double thback = back.theta();
116 const double phback = back.phi();
117 // Setting up two rotation matrices, via 3x3 rep. rather than even more messy EulerAngles
118 const double sph = sin(phback), cph = cos(phback), sth = sin(thback), cth = cos(thback);
119 const CLHEP::HepRotation rot1(CLHEP::HepRep3x3(cph, sph, 0.0, -sph, cph, 0.0, 0.0, 0.0, 1.0));
120 const CLHEP::HepRotation rot2(CLHEP::HepRep3x3(cth*cph, -sph, sth*cph, cth*sph, cph, sth*sph, -sth, 0.0, cth));
121 const CLHEP::HepBoost bst(psum.px()/psum.e(), psum.py()/psum.e(), psum.pz()/psum.e());
122 // Combine the two rotations and the boost; matrix multiplication order matters
123 const CLHEP::HepRotation rot = rot2*rot1;
125 transform.set(rot,bst);
126 }
127 else {
128 if(m_applyBoost) {
129 transform.set(bst);
130 }
132 transform.set(rot);
133 }
134 }
135 return StatusCode::SUCCESS;
136 }
Amg::Vector3D transform(Amg::Vector3D &v, Amg::Transform3D &tr)
Transform a point from a Trasformation3D.
double e2(const xAOD::CaloCluster &cluster)
return the uncorrected cluster energy in 2nd sampling
double e1(const xAOD::CaloCluster &cluster)
return the uncorrected cluster energy in 1st sampling

◆ manipulate()

StatusCode Simulation::GenEventBeamEffectBooster::manipulate ( HepMC::GenEvent & ge,
const EventContext & ctx ) const
finaloverride

modifies the given GenEvent

modifies (displaces) the given GenEvent

Definition at line 139 of file GenEventBeamEffectBooster.cxx.

140 {
141 // Obtain the transformation
142 CLHEP::HepLorentzRotation transform = CLHEP::HepLorentzRotation();
143 ATH_CHECK( initializeGenEvent(transform, ctx) );
144
145 for( auto particleIter: ge) {
146 this->boostParticle(particleIter, transform);
147 }
148 return StatusCode::SUCCESS;
149 }
StatusCode initializeGenEvent(CLHEP::HepLorentzRotation &transform, const EventContext &ctx) const
calculate the transformations that we want to apply to the particles in the current GenEvent
void boostParticle(HepMC::GenParticlePtr &p, const CLHEP::HepLorentzRotation &transform) const
apply boost to individual GenParticles

Member Data Documentation

◆ ATLAS_THREAD_SAFE

ATHRNG::RNGWrapper* m_randomEngine Simulation::GenEventBeamEffectBooster::ATLAS_THREAD_SAFE {}
private

Slot-local RNG.

Definition at line 60 of file GenEventBeamEffectBooster.h.

60{};

◆ m_applyBoost

Gaudi::Property<bool> Simulation::GenEventBeamEffectBooster::m_applyBoost {this, "ApplyBoost", true}
private

Definition at line 62 of file GenEventBeamEffectBooster.h.

62{this, "ApplyBoost", true};

◆ m_applyDivergence

Gaudi::Property<bool> Simulation::GenEventBeamEffectBooster::m_applyDivergence {this, "ApplyDivergence", true}
private

Definition at line 63 of file GenEventBeamEffectBooster.h.

63{this, "ApplyDivergence", true};

◆ m_beam1ParticleMass

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_beam1ParticleMass {this, "Beam1ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 1"}
private
Todo
Get from a service

Definition at line 78 of file GenEventBeamEffectBooster.h.

78{this, "Beam1ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 1"};

◆ m_beam2ParticleMass

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_beam2ParticleMass {this, "Beam2ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 2"}
private

Definition at line 79 of file GenEventBeamEffectBooster.h.

79{this, "Beam2ParticleMass", CLHEP::proton_mass_c2, "Mass of particle used in beam 2"};

◆ m_dE

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_dE {this, "deltaEOverE", 1.1E-4, "Delta_E/E theoretical value"}
private

Definition at line 75 of file GenEventBeamEffectBooster.h.

75{this, "deltaEOverE", 1.1E-4, "Delta_E/E theoretical value"}; // Delta_E/E theoretical value

◆ m_pbeam1

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_pbeam1 {this, "pbeam1", 3500.0E3, "Beam 1 Momentum / MeV"}
private

Definition at line 76 of file GenEventBeamEffectBooster.h.

76{this, "pbeam1", 3500.0E3, "Beam 1 Momentum / MeV"};

◆ m_pbeam2

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_pbeam2 {this, "pbeam2", 3500.0E3, "Beam 2 Momentum / MeV"}
private
Todo
Get from a service

Definition at line 77 of file GenEventBeamEffectBooster.h.

77{this, "pbeam2", 3500.0E3, "Beam 2 Momentum / MeV"};

◆ m_randomEngineName

Gaudi::Property<std::string> Simulation::GenEventBeamEffectBooster::m_randomEngineName {this, "RandomStream", "BEAM"}
private

Name of the random number stream.

Definition at line 61 of file GenEventBeamEffectBooster.h.

61{this, "RandomStream", "BEAM"};

◆ m_rndGenSvc

ServiceHandle<IAthRNGSvc> Simulation::GenEventBeamEffectBooster::m_rndGenSvc {this, "RandomSvc", "AthRNGSvc"}
private

Definition at line 59 of file GenEventBeamEffectBooster.h.

59{this, "RandomSvc", "AthRNGSvc"};

◆ m_sigma_px_b1

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_sigma_px_b1 {this, "Sigma_px_b1", 20.e-6, "angular divergence in x of beam 1 [rad]"}
private

Definition at line 66 of file GenEventBeamEffectBooster.h.

66{this, "Sigma_px_b1", 20.e-6, "angular divergence in x of beam 1 [rad]"};

◆ m_sigma_px_b2

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_sigma_px_b2 {this, "Sigma_px_b2", 21.e-6, "angular divergence in x of beam 2 [rad]"}
private

Definition at line 67 of file GenEventBeamEffectBooster.h.

67{this, "Sigma_px_b2", 21.e-6, "angular divergence in x of beam 2 [rad]"};

◆ m_sigma_py_b1

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_sigma_py_b1 {this, "Sigma_py_b1", 22.e-6, "angular divergence in y of beam 1 [rad]"}
private

Definition at line 68 of file GenEventBeamEffectBooster.h.

68{this, "Sigma_py_b1", 22.e-6, "angular divergence in y of beam 1 [rad]"};

◆ m_sigma_py_b2

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_sigma_py_b2 {this, "Sigma_py_b2", 23.e-6, "angular divergence in y of beam 2 [rad]"}
private

Definition at line 69 of file GenEventBeamEffectBooster.h.

69{this, "Sigma_py_b2", 23.e-6, "angular divergence in y of beam 2 [rad]"};

◆ m_xing_x_b1

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_xing_x_b1 {this, "HalfXing_x_b1", 19.e-6, "half-crossing in x for beam 1 at IP1, i.e. angle between beam 1 and z-axis"}
private

Definition at line 71 of file GenEventBeamEffectBooster.h.

71{this, "HalfXing_x_b1", 19.e-6, "half-crossing in x for beam 1 at IP1, i.e. angle between beam 1 and z-axis"};

◆ m_xing_x_b2

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_xing_x_b2 {this, "HalfXing_x_b2", 1.e-6, "half-crossing in x for beam 2 at IP1, i.e. angle between beam 2 and z-axis"}
private

Definition at line 72 of file GenEventBeamEffectBooster.h.

72{this, "HalfXing_x_b2", 1.e-6, "half-crossing in x for beam 2 at IP1, i.e. angle between beam 2 and z-axis"};

◆ m_xing_y_b1

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_xing_y_b1 {this, "HalfXing_y_b1", 150.e-6, "half-crossing in y for beam 1 at IP1, i.e. angle between beam 1 and z-axis"}
private

Definition at line 73 of file GenEventBeamEffectBooster.h.

73{this, "HalfXing_y_b1", 150.e-6, "half-crossing in y for beam 1 at IP1, i.e. angle between beam 1 and z-axis"};

◆ m_xing_y_b2

Gaudi::Property<double> Simulation::GenEventBeamEffectBooster::m_xing_y_b2 {this, "HalfXing_y_b2", -152.e-6, "half-crossing in y for beam 2 at IP1, i.e. angle between beam 2 and z-axis"}
private

Definition at line 74 of file GenEventBeamEffectBooster.h.

74{this, "HalfXing_y_b2", -152.e-6, "half-crossing in y for beam 2 at IP1, i.e. angle between beam 2 and z-axis"};

The documentation for this class was generated from the following files: