BOSS 7.1.0
BESIII Offline Software System
Loading...
Searching...
No Matches
SingleParticleGun.cxx
Go to the documentation of this file.
1// ------------------------------------------
2// File: SingleParticleGun/SingleParticleGun.cpp
3// Description:
4// Allows the user to "shoot" Monte Carlo particles and store the result
5// in the Transient Store.
6// -------------------------------------------------------------
7
10
11// Framework Related Headers:-
12#include "GaudiKernel/MsgStream.h"
13
14// Other classes used by this class:-
15#include <math.h>
16#include "CLHEP/Units/PhysicalConstants.h"
17
18#include "CLHEP/Random/RandFlat.h"
19#include "CLHEP/Random/RandGauss.h"
21
22#include "HepPDT/ParticleDataTable.hh"
23#include "HepPDT/ParticleData.hh"
24#ifndef ENABLE_BACKWARDS_COMPATIBILITY
25typedef double HepDouble;
26#endif
27using HepMC::GenVertex;
28using HepMC::GenParticle;
29
30DECLARE_COMPONENT(SingleParticleGun)
31// File scope declarations:-
32
33//--------------------------------------------------------------------------
34SingleParticleGun::SingleParticleGun(const std::string& name, ISvcLocator* pSvcLocator)
35 : GenModule(name,pSvcLocator)
36{
37//--------------------------------------------------------------------------
38 declareProperty("Mode",m_Emode = SingleEnergyMode::PtMode);
39 // in PtMode user specifies Pt theta and phi
40 // in EMode user specifies E, theta and phi
41 // defaults are set so that something is always generated
42
43 declareProperty("Pt",m_requestedPt = 5.0);
44 declareProperty("E",m_requestedE = 5.0);
45 declareProperty("Phi",m_requestedPhi = 0.0);
46 declareProperty("Theta",m_requestedTheta = 3.14/4.0);
47
48 declareProperty("VertexX",m_requestedX = 0.0);
49 declareProperty("VertexY",m_requestedY = 0.0);
50 declareProperty("VertexZ",m_requestedZ = 0.0);
51 declareProperty("Time",m_requestedT = 0.0);
52
53 declareProperty("MinPt",m_minPt = 1.);
54 declareProperty("MinE",m_minE = 1.);
55 declareProperty("MinTheta",m_minTheta = 0.);
56 declareProperty("MinPhi",m_minPhi = 0.);
57
58 declareProperty("MaxPt",m_maxPt = 100.);
59 declareProperty("MaxE",m_maxE = 100.);
60 declareProperty("MaxTheta",m_maxTheta=CLHEP::pi);
61 declareProperty("MaxPhi",m_maxPhi = CLHEP::twopi);
62
63 declareProperty("SigmaPt",m_sigmaPt = 0.1);
64 declareProperty("SigmaE",m_sigmaE = 0.1);
65
66 declareProperty("SigmaTheta",m_sigmaTheta= 0.1);
67 declareProperty("SigmaPhi",m_sigmaPhi = 0.1);
68
69 declareProperty("ModePt",m_PtGenMode = SingleParticleGunGenMode::FixedMode);
70 declareProperty("ModeE",m_EGenMode = SingleParticleGunGenMode::FixedMode);
71 declareProperty("ModeTheta",m_ThetaGenMode=SingleParticleGunGenMode::FixedMode);
72
73 declareProperty("ModePhi",m_PhiGenMode=SingleParticleGunGenMode::FixedMode);
74 // specifies type of distribution
75
76 declareProperty("PdgCode",m_pdgCode=211);
77}
78
79//--------------------------------------------------------------------------
81//--------------------------------------------------------------------------
82// if(m_pFlatGenerator) delete m_pFlatGenerator;
83// if(m_pGaussGenerator) delete m_pGaussGenerator;
84}
85
86//---------------------------------------------------------------------------
88//---------------------------------------------------------------------------
89
90 // Create the flat and gaussian generators
91 //
92
93 MsgStream log(messageService(), name());
94
95 static const bool CREATEIFNOTTHERE(true);
96 StatusCode RndmStatus = service("BesRndmGenSvc", p_BesRndmGenSvc, CREATEIFNOTTHERE);
97 if (!RndmStatus.isSuccess() || 0 == p_BesRndmGenSvc)
98 {
99 log << MSG::ERROR << " Could not initialize Random Number Service" << endreq;
100 return RndmStatus;
101 }
102
103 // Get the mass of the particle to be generated
104 //
105 const HepPDT::ParticleData* particle = m_particleTable->particle(HepPDT::ParticleID(abs(m_pdgCode)));
106 // Some particle can't be found in HepPDT, such as geantino
107 m_mass = particle?particle->mass().value():0;
108
109 //
110 // Make sure the parameters are in a sensible range...
111 //
112 switch (m_Emode){
114 if(!m_PtGenMode && (m_minPt > m_requestedPt || m_maxPt < m_requestedPt)
115 || m_maxPt < m_minPt ) {
116 log << MSG:: ERROR << " Pt min and max out of range. \n" <<
117 " Will set Pt mode to Fixed!!!" << endreq;
119 }
120 if(!m_ThetaGenMode && (m_minTheta > m_requestedTheta || m_maxTheta < m_requestedTheta)
121 || m_maxTheta < m_minTheta ) {
122 log << MSG:: ERROR << " Theta min and max out of range. \n" <<
123 " Will set Theta mode to Fixed!!!" << endreq;
125 }
126 if(!m_PhiGenMode && (m_minPhi > m_requestedPhi || m_maxPhi < m_requestedPhi)
127 || m_maxPhi < m_minPhi ) {
128 log << MSG:: ERROR << " Phi min and max out of range. \n" <<
129 " Will set Phi mode to Fixed!!!" << endreq;
131 }
132 break;
134 if(!m_EGenMode && (m_minE > m_requestedE || m_maxE < m_requestedE)
135 || m_maxE < m_minE ) {
136 log << MSG:: ERROR << " E min and max out of range. \n" <<
137 " Will set E mode to Fixed!!!" << endreq;
139 }
140 if(!m_ThetaGenMode && (m_minTheta > m_requestedTheta || m_maxTheta < m_requestedTheta)
141 || m_maxTheta < m_minTheta ) {
142 log << MSG:: ERROR << " Theta min and max out of range. \n" <<
143 " Will set Theta mode to Fixed!!!" << endreq;
145 }
146 if(!m_PhiGenMode && (m_minPhi > m_requestedPhi || m_maxPhi < m_requestedPhi)
147 || m_maxPhi < m_minPhi ) {
148 log << MSG:: ERROR << " Phi min and max out of range. \n" <<
149 " Will set Phi mode to Fixed!!!" << endreq;
151 }break;
152 }
153 m_events = 0;
154 return StatusCode::SUCCESS;
155}
156
157//---------------------------------------------------------------------------
159//---------------------------------------------------------------------------
160
161 ++m_events;
162 // Save the random number seeds in the event
163 CLHEP::HepRandomEngine* engine = p_BesRndmGenSvc->GetEngine("SINGLE");
164 const long* s = engine->getSeeds();
165 m_seeds.clear();
166 m_seeds.push_back(s[0]);
167 m_seeds.push_back(s[1]);
168
169 // Generate values for pt, theta and phi
170 //
171 double pt,phi,theta,E,px,py,pz,p;
172 switch(m_Emode){
173
175 pt = generateValue(m_PtGenMode,m_requestedPt, m_sigmaPt,
176 m_minPt, m_maxPt);
177 theta = generateValue(m_ThetaGenMode,m_requestedTheta, m_sigmaTheta,
178 m_minTheta, m_maxTheta);
179 phi = generateValue(m_PhiGenMode,m_requestedPhi, m_sigmaPhi,
180 m_minPhi, m_maxPhi);
181
182 // Transform to x,y,z coordinates
183 //
184 px = pt*cos(phi);
185 py = pt*sin(phi);
186 pz = pt/tan(theta);
187 m_fourMom.setVectM(CLHEP::Hep3Vector(px,py,pz),m_mass);
188 m_fourPos.set(m_requestedX,m_requestedY,m_requestedZ,m_requestedT);
189 return StatusCode::SUCCESS;
190
192 E = generateValue(m_EGenMode,m_requestedE, m_sigmaE,
193 m_minE, m_maxE);
194 theta = generateValue(m_ThetaGenMode,m_requestedTheta, m_sigmaTheta,
195 m_minTheta, m_maxTheta);
196 phi = generateValue(m_PhiGenMode,m_requestedPhi, m_sigmaPhi,
197 m_minPhi, m_maxPhi);
198
199 // Transform to x,y,z coordinates
200 //
201 if(E*E-m_mass*m_mass < 0.){
202 MsgStream log(messageService(), name());
203 log << MSG::ERROR << "You have Generated a Tachyon!! Increase energy or change particle ID" << endreq;
204return StatusCode::FAILURE;
205 }
206 p=sqrt(E*E-m_mass*m_mass);
207 px = p*sin(theta)*cos(phi);
208 py = p*sin(theta)*sin(phi);
209 pz = p*cos(theta);
210
211 m_fourMom.setVectM(CLHEP::Hep3Vector(px,py,pz),m_mass);
212 m_fourPos.set(m_requestedX,m_requestedY,m_requestedZ,m_requestedT);
213 return StatusCode::SUCCESS;
214}
215 return StatusCode::SUCCESS;
216}
217
218//---------------------------------------------------------------------------
220//---------------------------------------------------------------------------
221 return StatusCode::SUCCESS;
222}
223
224//---------------------------------------------------------------------------
225StatusCode SingleParticleGun::fillEvt(GenEvent* evt) {
226//---------------------------------------------------------------------------
227 // Note: The vertex is owned by the event so the event is responsible
228 // for deleting its memory
229 evt->set_event_number(m_events); // Set the event number
230 GenVertex* v1 = new GenVertex(m_fourPos);
231
232 std::cout << " SingleParticleGun::fillEvt --> " <<std::endl;
233 std::cout << " Event number:: " << m_events << std::endl;
234 std::cout << " vertex.x = " << m_fourPos.x()
235 << " vertex.y = " << m_fourPos.y()
236 << " vertex.z = " << m_fourPos.z()
237 << " vertex.t = " << m_fourPos.t() << std::endl;
238
239 std::cout << " momentum.x = " << m_fourMom.x()
240 << " momentum.y = " << m_fourMom.y()
241 << " momentum.z = " << m_fourMom.z()
242 << " momentum.t = " << m_fourMom.t() << std::endl;
243
244 evt->add_vertex( v1 );
245
246
247 v1->add_particle_out( new GenParticle( m_fourMom, m_pdgCode,1) );
248
249 std::cout << " particles_size = " << evt->particles_size()
250 << " vertices_size = " << evt->vertices_size()
251 << std::endl;
252
253 evt->set_signal_process_id(SINGLE);
254 evt->set_random_states(m_seeds);
255
256 return StatusCode::SUCCESS;
257}
258
259//---------------------------------------------------------------------------
260double SingleParticleGun::generateValue(int mode, double val, double sigma,
261 double min, double max) {
262//---------------------------------------------------------------------------
263 double tmp;
264 int i = 0;
265 CLHEP::HepRandomEngine* engine = p_BesRndmGenSvc->GetEngine("SINGLE");
266 const int maxtries = 100;
267 switch (mode) {
269 return val;
271 tmp = max+1.0;
272 i = 0;
273 do{
274// tmp = m_pGaussGenerator->fire((HepDouble) val,(HepDouble) sigma);
275 tmp = CLHEP::RandGauss::shoot(engine, (HepDouble) val,(HepDouble) sigma);
276 i++;
277 } while ( (tmp<min) || (tmp > max) && (i < maxtries));
278 if(i>maxtries) {
279 MsgStream log(messageService(), name());
280 log << MSG::ERROR << "Cant generate value in range (min, max) "
281 << val << "\t" << min << "\t" << max << endreq;
282 }
283 return tmp;
285// tmp = m_pFlatGenerator->fire((HepDouble) min,(HepDouble) max);
286 tmp = CLHEP::RandFlat::shoot(engine, (HepDouble) min,(HepDouble) max);
287 return tmp;
288 default:
289 MsgStream log(messageService(), name());
290 log << MSG::ERROR << "Unknown Generation Mode" << endreq;
291 return 0.;
292 }
293}
double tan(const BesAngle a)
Definition: BesAngle.h:216
double sin(const BesAngle a)
Definition: BesAngle.h:210
double cos(const BesAngle a)
Definition: BesAngle.h:213
TTree * sigma
double HepDouble
Definition: EvtVub.cc:37
@ SINGLE
Definition: GeneratorName.h:12
XmlRpcServer s
Definition: HelloServer.cpp:11
double HepDouble
HepPDT::ParticleDataTable * m_particleTable
Definition: GenModule.h:73
virtual CLHEP::HepRandomEngine * GetEngine(const std::string &StreamName)=0
Interface to the CLHEP engine.
virtual StatusCode fillEvt(GenEvent *evt)
virtual StatusCode genFinalize()
virtual StatusCode genInitialize()
virtual StatusCode callGenerator()