BmnRoot 26.10.0-18-g4e3414f9
Software framework of the BM@N experiment
Loading...
Searching...
No Matches
MpdUnigenGenerator.cxx
Go to the documentation of this file.
2
3#include "constants.h"
4
7 , fEventNumber(0)
8 , fInFile(nullptr)
9 , fInTree(nullptr)
10 , fEvent(nullptr)
11 , fRun(nullptr)
12 , fParticle(nullptr)
14 , fPhiMin(0.)
15 , fPhiMax(0.)
17{}
18
21 , fEventNumber(0)
22 , fInFile(nullptr)
23 , fInTree(nullptr)
24 , fEvent(nullptr)
25 , fRun(nullptr)
26 , fParticle(nullptr)
27 , fPhiMin(0.)
28 , fPhiMax(0.)
30{
31 std::cout << "-I MpdUnigenGenerator: Opening input file " << fileName.Data() << std::endl;
32
33 fInFile = new TFile(fileName, "read");
34 if (!fInFile) {
35 Fatal("MpdUnigenGenerator", "Cannot open input file.");
36 exit(1);
37 }
38
39 fInTree = (TTree*)fInFile->Get("events");
40 fNEntries = fInTree->GetEntries();
41 fRun = dynamic_cast<URun*>(fInFile->Get("run"));
42 Double_t mProt = 0.938272;
43
44 Double_t pTarg = fRun->GetPTarg(); // target momentum per nucleon
45 Double_t pProj = fRun->GetPProj(); // projectile momentum per nucleon
46
47 Double_t eTarg = TMath::Sqrt(pTarg * pTarg + mProt * mProt);
48 Double_t eProj = TMath::Sqrt(pProj * pProj + mProt * mProt);
49
50 if (TMath::Abs(pTarg) < 1e-10) {
51 // Case 1: target at rest, boost from lab to CM
52 fBetaCM = pProj / (eProj + mProt);
53
54 } else if (TMath::Abs(pTarg + pProj) < 1e-10) {
55 // Case 2: pTarg = -pProj (system in CM), boost from CM to lab (target at rest)
56 fBetaCM = -pTarg / eTarg; // velocity of target in CM frame
57
58 } else {
59 Fatal("MpdUnigenGenerator", "Unsupported momentum configuration: pTarg = %f, pProj = %f", pTarg, pProj);
60 exit(2);
61 }
62
63 fGammaCM = 1. / TMath::Sqrt(1. - fBetaCM * fBetaCM);
64
65 Double_t pBeam = fGammaCM * (pProj - fBetaCM * eProj);
66 LOG(info) << GetName() << ": sqrt(s_NN) = " << fRun->GetNNSqrtS() << " GeV, p_beam = " << pBeam << " GeV/u";
67 LOG(info) << GetName() << ": Lorentz transformation to lab system: " << " beta " << fBetaCM << ", gamma "
68 << fGammaCM;
69
70 if (!fInTree) {
71 Fatal("MpdUnigenGenerator", "Cannot open TTree from the file.");
72 exit(1);
73 }
74
75 fSpectatorsON = isSpectator;
76 if (fSpectatorsON)
77 std::cout << "-I MpdUnigenGenerator: Spectators ON" << std::endl;
78
79 Long64_t nEntries = fInTree->GetEntries();
80 std::cout << "-I MpdUnigenGenerator: Number of entries in tree: " << nEntries << std::endl;
81 fInTree->SetBranchAddress("event", &fEvent);
82
83 if (fSpectatorsON) {
85 }
86}
87
88Bool_t MpdUnigenGenerator::ReadEvent(FairPrimaryGenerator* primGen)
89{
90 // Check for input file
91 using namespace std;
92 if (!fInFile) {
93 cout << "-E- MpdUnigenGenerator: Input file not open! " << endl;
94 return kFALSE;
95 }
96
97 // Check for primary generator
98 if (!primGen) {
99 cout << "-E- MpdUnigenGenerator::ReadEvent: "
100 << "No PrimaryGenerator!" << endl;
101 return kFALSE;
102 }
103
104 // Check if current event exists in tree
105 if (fEventNumber >= fNEntries) {
106 cout << "-E- MpdUnigenGenerator::ReadEvent: "
107 << "Reached the of the tree" << endl;
108 return kFALSE;
109 }
110
111 fInTree->GetEntry(fEventNumber);
112 std::cout << "-I- MpdUnigenGenerator: Event " << fEventNumber << std::endl;
113
114 Double_t phi = fEvent->GetPhi();
115 Double_t dphi = 0.;
116 // ---> Generate rotation angle
117 std::cout << "Rotation of EP will be performed " << fEventPlaneSet << std::endl;
118 if (fEventPlaneSet) {
119 // gRandom->SetSeed(0);
120
122 // dphi = gRandom->Uniform(fPhiMin, fPhiMax);
123 std::cout << "EP is rotated to " << dphi << std::endl;
124 phi += dphi;
125 }
126
127 FairMCEventHeader* header = primGen->GetEvent();
128 if (header && (!header->IsSet())) {
129 header->SetEventID(fEvent->GetEventNr());
130 header->SetB(fEvent->GetB());
131 header->MarkSet(kTRUE);
132 header->SetRotZ(phi);
133 }
134
135 UInt_t nTracks = fEvent->GetNpa();
136 Int_t ionPdg;
137 for (UInt_t iTrack = 0; iTrack < nTracks; iTrack++) {
138 fParticle = fEvent->GetParticle(iTrack);
139 if (!fParticle)
140 continue;
141
142 Double_t px = fParticle->Px();
143 Double_t py = fParticle->Py();
144 Double_t pz = fParticle->Pz();
145 Double_t mass = fParticle->GetMomentum().M();
146
147 Double_t e = sqrt(mass * mass + px * px + py * py + pz * pz);
149 pz = fGammaCM * (pz + fBetaCM * e);
150
151 if (fEventPlaneSet) {
152 Double_t pt = TMath::Sqrt(px * px + py * py);
153 Double_t azim = TMath::ATan2(py, px);
154 azim += dphi;
155 px = pt * TMath::Cos(azim);
156 py = pt * TMath::Sin(azim);
157 }
158
159 if (fParticle->GetPdg() < 1e9) {
160 primGen->AddTrack(fParticle->GetPdg(), px, py, pz, 0., 0., 0.);
161 } else {
162 // Since hyper-nuclei are not (yet) supported by FairRoot, their PDG
163 // is replaced by that of the non-strange analogue.
164 ionPdg = fParticle->GetPdg();
165 if (GetIonLambdas(fParticle->GetPdg())) {
166 ionPdg = fParticle->GetPdg() - GetIonLambdas(fParticle->GetPdg()) * kPdgLambda;
167 std::cout << "-W- MpdUnigenGenerator: Replacing hypernucleus (PDG " << fParticle->GetPdg()
168 << ") by PDG " << ionPdg << std::endl;
169 }
170 // Charged ions can be registered
171 if (GetIonCharge(ionPdg) > 0) {
172 primGen->AddTrack(ionPdg, px, py, pz, 0., 0., 0.);
173 } else {
174 // Neutral ions are not supported by GEANT4.
175 // They are thus decomposed into neutrons (as an approximation)
176 Int_t neutralFragmentMass = GetIonMass(ionPdg);
177 for (Int_t iNeutron = 0; iNeutron < neutralFragmentMass; iNeutron++) {
178 Double_t pxNeutron = px / (Double_t)neutralFragmentMass;
179 Double_t pyNeutron = py / (Double_t)neutralFragmentMass;
180 Double_t pzNeutron = pz / (Double_t)neutralFragmentMass;
181 // Double_t eNeutron = fParticle->E()/(Double_t)neutralFragmentMass;
182
183 primGen->AddTrack(2112, pxNeutron, pyNeutron, pzNeutron, 0., 0., 0.);
184 }
185 std::cout << "-W- MpdUnigenGenerator: Neutral fragment (PDG " << ionPdg << ") is split into "
186 << neutralFragmentMass << " neutrons." << std::endl;
187 } // Neutral ion ?
188 } // ion ?
189 }
190 fEventNumber++;
191 return kTRUE;
192}
193
195{
196 std::cout << "-I- MpdUnigenGenerator: Registering ions..." << std::endl;
197 UParticle* particle{nullptr};
198 Int_t nIons{0};
199 fIonMap.clear();
200
201 for (Int_t iEvent = 0; iEvent < fInTree->GetEntries(); iEvent++) {
202 fInTree->GetEntry(iEvent);
203
204 for (Int_t iParticle = 0; iParticle < fEvent->GetNpa(); iParticle++) {
205 particle = fEvent->GetParticle(iParticle);
206
207 Int_t pdgCode = particle->GetPdg();
208 if (pdgCode > 1e9) { // ion
209 // For ions the PDG code is +-10LZZZAAAI,
210 // where A = n_Lambda + n_proton + n_neutron, Z = n_proton, L = n_Lambda
211 // and I = 0 - ground state, I>0 - excitations
212 const Int_t nLambda = GetIonLambdas(pdgCode);
213 const Int_t chrg = GetIonCharge(pdgCode);
214 const Int_t mass = GetIonMass(pdgCode);
215
216 // Neutral ions are skipped (not present in G4IonTable)
217 if (chrg == 0)
218 continue;
219
220 // Add ion to ion map
221 TString ionName = Form("Ion_%d_%d_%d", mass, chrg, nLambda);
222 if (fIonMap.find(ionName) == fIonMap.end()) { // new ion
223 fIonMap[ionName] = new FairIon(ionName, chrg, mass, chrg);
224
225 std::cout << "-I- MpdUnigenGenerator: Added new ion with PDG " << pdgCode << " (Charge " << chrg
226 << ", Mass " << mass << ", nLambda " << nLambda << ") from event " << iEvent
227 << " at index " << iParticle << std::endl;
228
229 nIons++;
230 } // new ion ?
231 } // ion ?
232 } // particle loop
233 } // event loop
234
235 // Adding new ions to FairRunSim instance
236 for (const auto& entry : fIonMap) {
237 FairRunSim::Instance()->AddNewIon(entry.second);
238 }
239
240 return fIonMap.size();
241}
bool Bool_t
int Int_t
unsigned int UInt_t
constexpr Bool_t kFALSE
double Double_t
long long Long64_t
constexpr Bool_t kTRUE
void Fatal(const char *location, const char *msgfmt,...)
char * Form(const char *fmt,...)
std::mt19937 random_engine_
Int_t GetIonCharge(Int_t pdgCode) const
Int_t GetIonLambdas(Int_t pdgCode)
Bool_t ReadEvent(FairPrimaryGenerator *primGen) override
Int_t GetIonMass(Int_t pdgCode)
static const Int_t kPdgLambda
std::map< TString, FairIon * > fIonMap
Map from ion name to FairIon.
std::uniform_real_distribution< double > uniform_real_distribution_
const char * Data() const
unigen particle
Definition UParticle.h:14
Int_t GetPdg() const
Definition UParticle.h:145
Definition URun.h:8
const CoordinateSystem gCoordinateSystem
Definition constants.h:6
@ sysLaboratory
Definition constants.h:4
RVec< PromoteType< T > > sqrt(const RVec< T > &v)
Double_t ATan2(Double_t y, Double_t x)
Double_t Sqrt(Double_t x)
Double_t Cos(Double_t)
Double_t Abs(Double_t d)
Double_t Sin(Double_t)
Definition json.hpp:4446