Project
Loading...
Searching...
No Matches
Detector.cxx
Go to the documentation of this file.
1// Copyright 2019-2020 CERN and copyright holders of ALICE O2.
2// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders.
3// All rights not expressly granted are reserved.
4//
5// This software is distributed under the terms of the GNU General Public
6// License v3 (GPL Version 3), copied verbatim in the file "COPYING".
7//
8// In applying this license CERN does not waive the privileges and immunities
9// granted to it by virtue of its status as an Intergovernmental Organization
10// or submit itself to any jurisdiction.
11
12#include <FairVolume.h>
13
14#include <TVirtualMC.h>
15#include <TVirtualMCStack.h>
16#include <TGeoVolume.h>
17#include <TGeoTube.h>
18#include <TGeoManager.h>
19
20#include "DetectorsBase/Stack.h"
24
25using o2::itsmft::Hit;
26
27namespace o2::mi3
28{
29
31 : o2::base::DetImpl<Detector>("MI3", true),
32 mTrackData(),
33 mHits(o2::utils::createSimVector<o2::itsmft::Hit>())
34{
35}
36
38 : o2::base::DetImpl<Detector>("MI3", true),
39 mTrackData(),
40 mHits(o2::utils::createSimVector<o2::itsmft::Hit>())
41{
42 auto& midPars = MIDBaseParam::Instance();
43}
44
46{
47 if (mHits) {
49 }
50}
51
57
59{
60 int ifield = 2; // ?
61 float fieldm = 10.0; // ?
63
64 float tmaxfdPolys = 0.1; // .10000E+01; // Degree
65 float stemaxPolys = .10000E+01; // cm
66 float deemaxPolys = 0.1; // 0.30000E-02; // Fraction of particle's energy 0<deemax<=1
67 float epsilPolys = 1.0E-4; // .10000E+01;
68 float stminPolys = 0.0; // cm "Default value used"
69
70 // Materials
71 // Air
72 float aAir[4] = {12.0107, 14.0067, 15.9994, 39.948};
73 float zAir[4] = {6., 7., 8., 18.};
74 float wAir[4] = {0.000124, 0.755267, 0.231781, 0.012827};
75 float dAir = 1.20479E-3;
76 float dAir1 = 1.20479E-10;
77
78 o2::base::Detector::Mixture(0, "AIR", aAir, zAir, dAir, 4, wAir);
79 o2::base::Detector::Medium(0, "AIR", 0, 0, ifield, fieldm, tmaxfdPolys, stemaxPolys, deemaxPolys, epsilPolys, stminPolys);
80
81 // Polystyrene (C6H5CHCH2)n https://pdg.lbl.gov/2023/AtomicNuclearProperties/HTML/polystyrene.html
82 float aPolys[2] = {1.0080, 12.0107};
83 float zPolys[2] = {1.f, 6};
84 float wPolys[2] = {0.077418, 0.922582};
85 float dPolys = 1.060; // g/cm3
86
87 o2::base::Detector::Mixture(1, "POLYSTYRENE", aPolys, zPolys, dPolys, 2, wPolys);
88 o2::base::Detector::Medium(1, "POLYSTYRENE", 1, 0, ifield, fieldm, tmaxfdPolys, stemaxPolys, deemaxPolys, epsilPolys, stminPolys);
89}
90
92{
93 LOG(info) << "Initialize MID O2Detector";
94 mGeometryTGeo = GeometryTGeo::Instance();
95 // defineSensitiveVolumes();
96}
97
99
101{
102 // This will create a branch in the output tree called Hit, setting the last
103 // parameter to kFALSE means that this collection will not be written to the file,
104 // it will exist only during the simulation
105
106 if (FairRootManager::Instance()) {
107 FairRootManager::Instance()->RegisterAny(addNameTo("Hit").data(), mHits, true);
108 }
109}
110
112{
113 LOGP(info, "Creating MID geometry");
114
115 TGeoManager* geoManager = gGeoManager;
116 TGeoVolume* vALIC = geoManager->GetVolume("barrel");
117 if (!vALIC) {
118 LOGP(fatal, "Could not find barrel volume while constructing MID geometry");
119 }
120 new TGeoVolumeAssembly(GeometryTGeo::getMIDVolPattern());
121 TGeoVolume* vMID = geoManager->GetVolume(GeometryTGeo::getMIDVolPattern());
122 vALIC->AddNode(vMID, 2, new TGeoTranslation(0, 30., 0));
123
124 char vstrng[100] = "MIDVol";
125 vMID->SetTitle(vstrng);
126
127 // Build the MID
128 mLayers.resize(2);
129 mLayers[0] = MIDLayer(0, GeometryTGeo::composeSymNameLayer(0), 301.f, 500.f);
130 mLayers[1] = MIDLayer(1, GeometryTGeo::composeSymNameLayer(1), 311.f, 520.f); // arbitrarily reduced to get multiple of 5.2f
131
132 for (auto& layer : mLayers) {
133 layer.createLayer(vMID);
134 }
135}
136
138{
139 if (!o2::utils::ShmManager::Instance().isOperational()) {
140 mHits->clear();
141 }
142}
143
144bool Detector::ProcessHits(FairVolume* vol)
145{
146 // This method is called from the MC stepping
147 if (!(fMC->TrackCharge())) {
148 return false;
149 }
150
151 int lay = vol->getVolumeId();
152 int volID = vol->getMCid();
153
154 // Is it needed to keep a track reference when the outer ITS volume is encountered?
155 auto stack = (o2::data::Stack*)fMC->GetStack();
156 if (fMC->IsTrackExiting() && (lay == 0)) {
157 o2::TrackReference tr(*fMC, GetDetId());
158 tr.setTrackID(stack->GetCurrentTrackNumber());
159 tr.setUserId(lay);
160 stack->addTrackReference(tr);
161 }
162 bool startHit = false, stopHit = false;
163 unsigned char status = 0;
164 if (fMC->IsTrackEntering()) {
165 status |= Hit::kTrackEntering;
166 }
167 if (fMC->IsTrackInside()) {
168 status |= Hit::kTrackInside;
169 }
170 if (fMC->IsTrackExiting()) {
171 status |= Hit::kTrackExiting;
172 }
173 if (fMC->IsTrackOut()) {
174 status |= Hit::kTrackOut;
175 }
176 if (fMC->IsTrackStop()) {
177 status |= Hit::kTrackStopped;
178 }
179 if (fMC->IsTrackAlive()) {
180 status |= Hit::kTrackAlive;
181 }
182
183 // track is entering or created in the volume
184 if ((status & Hit::kTrackEntering) || (status & Hit::kTrackInside && !mTrackData.mHitStarted)) {
185 startHit = true;
186 } else if ((status & (Hit::kTrackExiting | Hit::kTrackOut | Hit::kTrackStopped))) {
187 stopHit = true;
188 }
189
190 // increment energy loss at all steps except entrance
191 if (!startHit) {
192 mTrackData.mEnergyLoss += fMC->Edep();
193 }
194 if (!(startHit | stopHit)) {
195 return false; // do noting
196 }
197
198 if (startHit) {
199 mTrackData.mEnergyLoss = 0.;
200 fMC->TrackMomentum(mTrackData.mMomentumStart);
201 fMC->TrackPosition(mTrackData.mPositionStart);
202 mTrackData.mTrkStatusStart = status;
203 mTrackData.mHitStarted = true;
204 }
205 if (stopHit) {
206 TLorentzVector positionStop;
207 fMC->TrackPosition(positionStop);
208 // Retrieve the indices with the volume path
209 int stave(0), halfstave(0), chipinmodule(0), module;
210 fMC->CurrentVolOffID(1, chipinmodule);
211 fMC->CurrentVolOffID(2, module);
212 fMC->CurrentVolOffID(3, halfstave);
213 fMC->CurrentVolOffID(4, stave);
214
215 Hit* p = addHit(stack->GetCurrentTrackNumber(), lay, mTrackData.mPositionStart.Vect(), positionStop.Vect(),
216 mTrackData.mMomentumStart.Vect(), mTrackData.mMomentumStart.E(), positionStop.T(),
217 mTrackData.mEnergyLoss, mTrackData.mTrkStatusStart, status);
218 // p->SetTotalEnergy(vmc->Etot());
219
220 // RS: not sure this is needed
221 // Increment number of Detector det points in TParticle
222 stack->addHit(GetDetId());
223 }
224
225 return true;
226}
227
228o2::itsmft::Hit* Detector::addHit(int trackID, int detID, const TVector3& startPos, const TVector3& endPos,
229 const TVector3& startMom, double startE, double endTime, double eLoss, unsigned char startStatus,
230 unsigned char endStatus)
231{
232 mHits->emplace_back(trackID, detID, startPos, endPos, startMom, startE, endTime, eLoss, startStatus, endStatus);
233 return &(mHits->back());
234}
235} // namespace o2::mi3
Definition of the Stack class.
Definition of the ITSMFT Hit class.
ClassImp(IdPath)
uint32_t stack
Definition RawData.h:1
void setUserId(Int_t userId)
void setTrackID(Int_t track)
void Mixture(Int_t imat, const char *name, Float_t *a, Float_t *z, Float_t dens, Int_t nlmat, Float_t *wmat)
Definition Detector.cxx:66
void Medium(Int_t numed, const char *name, Int_t nmat, Int_t isvol, Int_t ifield, Float_t fieldm, Float_t tmaxfd, Float_t stemax, Float_t deemax, Float_t epsil, Float_t stmin, Float_t *ubuf=nullptr, Int_t nbuf=0)
Definition Detector.cxx:72
static void initFieldTrackingParams(int &mode, float &maxfield)
Definition Detector.cxx:143
std::string addNameTo(const char *ext) const
Definition Detector.h:150
std::vector< MIDLayer > mLayers
Definition Detector.h:84
void createMaterials()
Definition Detector.cxx:58
o2::itsmft::Hit * addHit(int trackID, int detID, const TVector3 &startPos, const TVector3 &endPos, const TVector3 &startMom, double startE, double endTime, double eLoss, unsigned char startStatus, unsigned char endStatus)
Definition Detector.cxx:228
void ConstructGeometry() override
Definition Detector.cxx:52
void EndOfEvent() override
Definition Detector.cxx:98
bool ProcessHits(FairVolume *v=nullptr) override
Definition Detector.cxx:144
void InitializeO2Detector() override
Definition Detector.cxx:91
void Reset() override
Definition Detector.cxx:137
void Register() override
Definition Detector.cxx:100
static const char * getMIDVolPattern()
static const char * composeSymNameLayer(const int layer)
static GeometryTGeo * Instance()
static ShmManager & Instance()
Definition ShmManager.h:61
GLboolean * data
Definition glcorearb.h:298
GLenum GLuint GLint GLint layer
Definition glcorearb.h:1310
void freeSimVector(std::vector< T > *ptr)
a couple of static helper functions to create timestamp values for CCDB queries or override obsolete ...
Common utility functions.
LOG(info)<< "Compressed in "<< sw.CpuTime()<< " s"