Skip to content

Commit 9ce304b

Browse files
authored
ALICE3-TRK: detector ID used to fill Hit information correctly retrieved according to the chosen geometry (#14480)
* ALICE3-TRK: Detector.cxx modified to retrieve the correct Detector ID following the chosen indexing scheme * ALICE3-TRK: considering half staves for the staggered geometry for ML/OT * ALICE3-TRK: indexing scheme now working independently from the chosen geometry layout * minor fixes
1 parent 9cef6de commit 9ce304b

File tree

4 files changed

+203
-42
lines changed

4 files changed

+203
-42
lines changed

Detectors/Upgrades/ALICE3/TRK/base/include/TRKBase/GeometryTGeo.h

Lines changed: 18 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -60,33 +60,44 @@ class GeometryTGeo : public o2::detectors::DetMatrixCache
6060
int extractNumberOfDisksVD() const;
6161
int extractNumberOfChipsPerPetalVD() const;
6262
int extractNumberOfStavesMLOT(int lay) const;
63+
int extractNumberOfHalfStavesMLOT(int lay) const;
6364

6465
/// Extract number following the prefix in the name string
6566
int extractVolumeCopy(const char* name, const char* prefix) const;
6667

6768
int getNumberOfLayersMLOT() const { return mNumberOfLayersMLOT; }
68-
int getNumberOffActivePartsVD() const { return mNumberOfActivePartsVD; }
69+
int getNumberOfActivePartsVD() const { return mNumberOfActivePartsVD; }
70+
int getNumberOfHalfStaves(int lay) const { return mNumberOfHalfStaves[lay]; }
6971

7072
bool isOwner() const { return mOwner; }
7173
void setOwner(bool v) { mOwner = v; }
7274

7375
void Print(Option_t* opt = "") const;
74-
void PrintChipID(int index, int subDetID, int petalcase, int disk, int lay, int stave, int indexRetrieved) const;
76+
void PrintChipID(int index, int subDetID, int petalcase, int disk, int lay, int stave, int halfstave, int indexRetrieved) const;
7577

7678
int getLayer(int index) const;
7779
int getStave(int index) const;
80+
int getHalfStave(int index) const;
7881
int getSubDetID(int index) const;
7982
int getPetalCase(int index) const;
8083
int getDisk(int index) const;
8184

8285
/// This routine computes the chip index number from the subDetID, petal, disk, layer, stave /// TODO: retrieve also from chip when chips will be available
83-
/// in substave
8486
/// \param int subDetID The subdetector ID, 0 for VD, 1 for MLOT
8587
/// \param int petalcase The petal case number for VD, from 0 to 3
8688
/// \param int disk The disk number for VD, from 0 to 5
8789
/// \param int lay The layer number. Starting from 0 both for VD and MLOT
8890
/// \param int stave The stave number for MLOT. Starting from 0
89-
int getChipIndex(int subDetID, int petalcase, int disk, int lay, int stave) const;
91+
/// \param int halfstave The half stave number for MLOT. Can be 0 or 1
92+
int getChipIndex(int subDetID, int petalcase, int disk, int lay, int stave, int halfstave) const;
93+
94+
/// This routine computes the chip index number from the subDetID, volume, layer, stave /// TODO: retrieve also from chip when chips will be available
95+
/// \param int subDetID The subdetector ID, 0 for VD, 1 for MLOT
96+
/// \param int volume is needed only with the current configuration for VD where each single element is a volume. // TODO: when the geometry naming scheme will be changed, change this method
97+
/// \param int lay The layer number for the MLOT. In the current configuration for VD this is not needed. // TODO: when the geometry naming scheme will be changed, change this method
98+
/// \param int stave The stave number in each layer for MLOT. Starting from 0.
99+
/// \param int halfstave The half stave number for MLOT. Can be 0 or 1
100+
int getChipIndex(int subDetID, int volume, int lay, int stave, int halfstave) const;
90101

91102
/// This routine computes subDetID, petal, disk, layer, stave given the chip index number /// TODO: copute also from chip when chips will be available
92103
/// \param int index The chip index number, starting from 0
@@ -95,7 +106,8 @@ class GeometryTGeo : public o2::detectors::DetMatrixCache
95106
/// \param int disk The disk number for VD, from 0 to 5
96107
/// \param int lay The layer number. Starting from 0 both for VD and MLOT
97108
/// \param int stave The stave number for MLOT. Starting from 0
98-
bool getChipID(int index, int& subDetID, int& petalcase, int& disk, int& lay, int& stave) const;
109+
/// \param int halfstave The half stave number for MLOT. Can be 0 or 1
110+
bool getChipID(int index, int& subDetID, int& petalcase, int& disk, int& lay, int& stave, int& halfstave) const;
99111

100112
int getLastChipIndex(int lay) const { return mLastChipIndex[lay]; }
101113
int getFirstChipIndex(int lay, int petalcase, int subDetID) const
@@ -150,6 +162,7 @@ class GeometryTGeo : public o2::detectors::DetMatrixCache
150162
std::vector<int> mNumbersOfChipPerDiskVD; ///< numbersOfChipPerDiskVD
151163
std::vector<int> mNumberOfChipsPerPetalVD; ///< numbersOfChipPerPetalVD
152164
std::vector<int> mNumberOfStaves; ///< Number Of Staves per layer in ML/OT
165+
std::vector<int> mNumberOfHalfStaves; ///< Number Of Staves in each stave of the layer in ML/OT
153166
std::array<char, MAXLAYERS> mLayerToWrapper; ///< Layer to wrapper correspondence
154167

155168
bool mOwner = true; //! is it owned by the singleton?

Detectors/Upgrades/ALICE3/TRK/base/src/GeometryTGeo.cxx

Lines changed: 90 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -54,9 +54,9 @@ GeometryTGeo::GeometryTGeo(bool build, int loadTrans) : DetMatrixCache(detectors
5454
void GeometryTGeo::Build(int loadTrans)
5555
{
5656
///// current geometry organization:
57-
///// total elements = 258 = x staves * 8 layers ML+OT + 4 petal cases * (3 layers + 6 disks)
57+
///// total elements = x staves (*2 half staves if staggered geometry) * 8 layers ML+OT + 4 petal cases * (3 layers + 6 disks)
5858
///// indexing from 0 to 35: VD petals -> layers -> disks
59-
///// indexing from 36 to 257: MLOT staves
59+
///// indexing from 36 to y: MLOT staves
6060

6161
if (isBuilt()) {
6262
LOGP(warning, "Already built");
@@ -74,6 +74,7 @@ void GeometryTGeo::Build(int loadTrans)
7474
mNumberOfDisksVD = extractNumberOfDisksVD();
7575

7676
mNumberOfStaves.resize(mNumberOfLayersMLOT);
77+
mNumberOfHalfStaves.resize(mNumberOfLayersMLOT);
7778
mLastChipIndex.resize(mNumberOfPetalsVD + mNumberOfLayersMLOT);
7879
mLastChipIndexVD.resize(mNumberOfPetalsVD);
7980
mLastChipIndexMLOT.resize(mNumberOfLayersMLOT); /// ML and OT are part of TRK as the same detector, without disks
@@ -85,6 +86,7 @@ void GeometryTGeo::Build(int loadTrans)
8586
for (int i = 0; i < mNumberOfLayersMLOT; i++) {
8687
std::cout << "Layer MLOT: " << i << std::endl;
8788
mNumberOfStaves[i] = extractNumberOfStavesMLOT(i);
89+
mNumberOfHalfStaves[i] = extractNumberOfHalfStavesMLOT(i);
8890
}
8991

9092
int numberOfChipsTotal = 0;
@@ -99,13 +101,12 @@ void GeometryTGeo::Build(int loadTrans)
99101

100102
/// filling the information for the MLOT
101103
for (int i = 0; i < mNumberOfLayersMLOT; i++) {
102-
mNumberOfChipsPerLayerMLOT[i] = extractNumberOfStavesMLOT(i); // for the moment, considering 1 stave = 1 chip. TODO: add the final segmentation in chips
104+
mNumberOfChipsPerLayerMLOT[i] = extractNumberOfStavesMLOT(i) * extractNumberOfHalfStavesMLOT(i); // for the moment, considering 1 half stave = 1 chip. TODO: add the final segmentation in chips
103105
numberOfChipsTotal += mNumberOfChipsPerLayerMLOT[i];
104106
mLastChipIndex[i + mNumberOfPetalsVD] = numberOfChipsTotal - 1;
105107
mLastChipIndexMLOT[i] = numberOfChipsTotal - 1;
106108
}
107109

108-
// setSize(mNumberOfLayersMLOT + mNumberOfActivePartsVD); /// temporary, number of chips = number of layers and active parts
109110
setSize(numberOfChipsTotal); /// temporary, number of chips = number of staves and active parts
110111
fillMatrixCache(loadTrans);
111112
}
@@ -155,7 +156,7 @@ int GeometryTGeo::getLayer(int index) const
155156
while (index > mLastChipIndex[lay]) {
156157
lay++;
157158
}
158-
return lay - mNumberOfPetalsVD; /// numeration of MLOT layesrs starting from 1
159+
return lay - mNumberOfPetalsVD; /// numeration of MLOT layesrs starting from 0
159160
}
160161
return -1; /// -1 if not found
161162
}
@@ -170,8 +171,26 @@ int GeometryTGeo::getStave(int index) const
170171
return -1;
171172
} else if (subDetID == 1) { /// MLOT
172173
int lay = getLayer(index);
173-
index -= getFirstChipIndex(lay, petalcase, subDetID);
174-
return index; /// ||||
174+
index -= getFirstChipIndex(lay, petalcase, subDetID); // get the index of the sensing element in the layer
175+
return index / mNumberOfHalfStaves[lay];
176+
}
177+
return -1; /// not found
178+
}
179+
180+
//__________________________________________________________________________
181+
int GeometryTGeo::getHalfStave(int index) const
182+
{
183+
int subDetID = getSubDetID(index);
184+
int lay = getLayer(index);
185+
int petalcase = getPetalCase(index);
186+
int stave = getStave(index);
187+
188+
if (subDetID == 0) { /// VD
189+
return -1;
190+
} else if (subDetID == 1) { /// MLOT
191+
int lay = getLayer(index);
192+
index -= getFirstChipIndex(lay, petalcase, subDetID); // get the index of the sensing element in the layer
193+
return index % 2; /// 0 = half stave left, 1 = half stave right, as geometry is filled /// TODO: generalize once chips will be in place. Can it be working also with chips?
175194
}
176195
return -1; /// not found
177196
}
@@ -193,28 +212,49 @@ int GeometryTGeo::getDisk(int index) const
193212
}
194213

195214
//__________________________________________________________________________
196-
int GeometryTGeo::getChipIndex(int subDetID, int petalcase, int disk, int lay, int stave) const
215+
int GeometryTGeo::getChipIndex(int subDetID, int petalcase, int disk, int lay, int stave, int halfstave) const
197216
{
198217
if (subDetID == 0) { // VD
199218
if (lay == -1) { // disk
200219
return getFirstChipIndex(lay, petalcase, subDetID) + mNumberOfLayersVD + disk;
201220
} else { // layer
202221
return getFirstChipIndex(lay, petalcase, subDetID) + lay;
203222
}
204-
} else if (subDetID == 1) { // MLOT
205-
return getFirstChipIndex(lay, petalcase, subDetID) + stave;
223+
} else if (subDetID == 1) { // MLOT
224+
if (mNumberOfHalfStaves[lay] == 2) { // staggered geometry
225+
return getFirstChipIndex(lay, petalcase, subDetID) + stave * mNumberOfHalfStaves[lay] + halfstave;
226+
} else if (mNumberOfHalfStaves[lay] == 1) { // turbo geometry
227+
return getFirstChipIndex(lay, petalcase, subDetID) + stave;
228+
}
229+
}
230+
return -1; // not found
231+
}
232+
233+
//__________________________________________________________________________
234+
int GeometryTGeo::getChipIndex(int subDetID, int volume, int lay, int stave, int halfstave) const
235+
{
236+
if (subDetID == 0) { // VD
237+
return volume; /// In the current configuration for VD, each volume is the sensor element = chip. // TODO: when the geometry naming scheme will be changed, change this method
238+
239+
} else if (subDetID == 1) { // MLOT
240+
if (mNumberOfHalfStaves[lay] == 2) { // staggered geometry
241+
return getFirstChipIndex(lay, -1, subDetID) + stave * mNumberOfHalfStaves[lay] + halfstave;
242+
} else if (mNumberOfHalfStaves[lay] == 1) { // turbo geometry
243+
return getFirstChipIndex(lay, -1, subDetID) + stave;
244+
}
206245
}
207246
return -1; // not found
208247
}
209248

210249
//__________________________________________________________________________
211-
bool GeometryTGeo::getChipID(int index, int& subDetID, int& petalcase, int& disk, int& lay, int& stave) const
250+
bool GeometryTGeo::getChipID(int index, int& subDetID, int& petalcase, int& disk, int& lay, int& stave, int& halfstave) const
212251
{
213252
subDetID = getSubDetID(index);
214253
petalcase = getPetalCase(index);
215254
disk = getDisk(index);
216255
lay = getLayer(index);
217256
stave = getStave(index);
257+
halfstave = getHalfStave(index);
218258

219259
return kTRUE;
220260
}
@@ -223,13 +263,12 @@ bool GeometryTGeo::getChipID(int index, int& subDetID, int& petalcase, int& disk
223263
TString GeometryTGeo::getMatrixPath(int index) const
224264
{
225265

226-
// int lay, hba, stav, sstav, mod, chipInMod;
227-
int subDetID, petalcase, disk, lay, stave; //// TODO: add chips in a second step
228-
getChipID(index, subDetID, petalcase, disk, lay, stave);
266+
int subDetID, petalcase, disk, lay, stave, halfstave; //// TODO: add chips in a second step
267+
getChipID(index, subDetID, petalcase, disk, lay, stave, halfstave);
229268

230-
int indexRetrieved = getChipIndex(subDetID, petalcase, disk, lay, stave);
269+
int indexRetrieved = getChipIndex(subDetID, petalcase, disk, lay, stave, halfstave);
231270

232-
PrintChipID(index, subDetID, petalcase, disk, lay, stave, indexRetrieved);
271+
PrintChipID(index, subDetID, petalcase, disk, lay, stave, halfstave, indexRetrieved);
233272

234273
// TString path = Form("/cave_1/barrel_1/%s_2/", GeometryTGeo::getTRKVolPattern());
235274
TString path = "/cave_1/barrel_1/TRKV_2/TRKLayer0_1/TRKStave0_1/TRKChip0_1/TRKSensor0_1/"; /// dummy path, to be replaced
@@ -291,7 +330,7 @@ TGeoHMatrix* GeometryTGeo::extractMatrixSensor(int index) const
291330
auto path = getMatrixPath(index);
292331

293332
static TGeoHMatrix matTmp;
294-
gGeoManager->PushPath();
333+
// gGeoManager->PushPath(); // Preserve the modeler state.
295334

296335
// if (!gGeoManager->cd(path.Data())) {
297336
// gGeoManager->PopPath();
@@ -440,7 +479,6 @@ int GeometryTGeo::extractNumberOfActivePartsVD() const
440479
if (vdV == nullptr) {
441480
LOG(fatal) << getName() << " volume " << getTRKVolPattern() << " is not in the geometry";
442481
}
443-
LOG(info) << "Volume name: " << getTRKVolPattern();
444482

445483
// Loop on all TRKV nodes, count Layer volumes by checking names
446484
TObjArray* nodes = vdV->GetNodes();
@@ -470,7 +508,6 @@ int GeometryTGeo::extractNumberOfDisksVD() const
470508
if (vdV == nullptr) {
471509
LOG(fatal) << getName() << " volume " << getTRKVolPattern() << " is not in the geometry";
472510
}
473-
LOG(info) << "Volume name: " << getTRKVolPattern();
474511

475512
// Loop on all TRKV nodes, count Layer volumes by checking names
476513
TObjArray* nodes = vdV->GetNodes();
@@ -500,7 +537,6 @@ int GeometryTGeo::extractNumberOfPetalsVD() const
500537
if (vdV == nullptr) {
501538
LOG(fatal) << getName() << " volume " << getTRKVolPattern() << " is not in the geometry";
502539
}
503-
LOG(info) << "Volume name: " << getTRKVolPattern();
504540

505541
// Loop on all TRKV nodes, count Layer volumes by checking names
506542
TObjArray* nodes = vdV->GetNodes();
@@ -530,7 +566,6 @@ int GeometryTGeo::extractNumberOfLayersVD() const
530566
if (vdV == nullptr) {
531567
LOG(fatal) << getName() << " volume " << getTRKVolPattern() << " is not in the geometry";
532568
}
533-
LOG(info) << "Volume name: " << getTRKVolPattern();
534569

535570
// Loop on all TRKV nodes, count Layer volumes by checking names
536571
TObjArray* nodes = vdV->GetNodes();
@@ -560,7 +595,6 @@ int GeometryTGeo::extractNumberOfChipsPerPetalVD() const
560595
if (vdV == nullptr) {
561596
LOG(fatal) << getName() << " volume " << getTRKVolPattern() << " is not in the geometry";
562597
}
563-
LOG(info) << "Volume name: " << getTRKVolPattern();
564598

565599
// Loop on all TRKV nodes, count Layer volumes by checking names
566600
TObjArray* nodes = vdV->GetNodes();
@@ -610,7 +644,35 @@ int GeometryTGeo::extractNumberOfStavesMLOT(int lay) const
610644
}
611645

612646
//__________________________________________________________________________
613-
void GeometryTGeo::PrintChipID(int index, int subDetID, int petalcase, int disk, int lay, int stave, int indexRetrieved) const
647+
int GeometryTGeo::extractNumberOfHalfStavesMLOT(int lay) const
648+
{
649+
int numberOfHalfStaves = 0;
650+
651+
std::string staveName = Form("%s%d", getTRKStavePattern(), lay);
652+
TGeoVolume* staveV = gGeoManager->GetVolume(staveName.c_str());
653+
654+
if (staveV == nullptr) {
655+
LOG(fatal) << getName() << " volume " << getTRKStavePattern() << " is not in the geometry";
656+
}
657+
658+
// Loop on all layV nodes, count Layer volumes by checking names
659+
TObjArray* nodes = staveV->GetNodes();
660+
// std::cout << "Printing nodes for layer " << lay << std::endl;
661+
// nodes->Print();
662+
int nNodes = nodes->GetEntriesFast();
663+
664+
for (int j = 0; j < nNodes; j++) {
665+
auto nd = dynamic_cast<TGeoNode*>(nodes->At(j)); /// layer node
666+
const char* name = nd->GetName();
667+
if (strstr(name, getTRKChipPattern()) != nullptr) {
668+
numberOfHalfStaves++;
669+
}
670+
}
671+
return numberOfHalfStaves;
672+
}
673+
674+
//__________________________________________________________________________
675+
void GeometryTGeo::PrintChipID(int index, int subDetID, int petalcase, int disk, int lay, int stave, int halfstave, int indexRetrieved) const
614676
{
615677
std::cout << "\nindex = " << index << std::endl;
616678
std::cout << "subDetID = " << subDetID << std::endl;
@@ -619,7 +681,8 @@ void GeometryTGeo::PrintChipID(int index, int subDetID, int petalcase, int disk,
619681
std::cout << "disk = " << disk << std::endl;
620682
std::cout << "first chip index = " << getFirstChipIndex(lay, petalcase, subDetID) << std::endl;
621683
std::cout << "stave = " << stave << std::endl;
622-
std::cout << "chck index Retrieved = " << indexRetrieved << std::endl;
684+
std::cout << "halfstave = " << halfstave << std::endl;
685+
std::cout << "check index Retrieved = " << indexRetrieved << std::endl;
623686
}
624687

625688
//__________________________________________________________________________
@@ -641,11 +704,11 @@ void GeometryTGeo::Print(Option_t*) const
641704
for (int i = 0; i < mNumberOfPetalsVD; i++) {
642705
LOGF(info, "%d", mNumberOfChipsPerPetalVD[i]);
643706
}
644-
LOGF(info, "Number of staves per layer MLOT: ");
707+
LOGF(info, "Number of staves and half staves per layer MLOT: ");
645708
for (int i = 0; i < mNumberOfLayersMLOT; i++) {
646709
std::string mlot = "";
647-
mlot = (i < 5) ? "ML" : "OT";
648-
LOGF(info, "Layer: %d, %s, %d staves", i, mlot.c_str(), mNumberOfStaves[i]);
710+
mlot = (i < 4) ? "ML" : "OT";
711+
LOGF(info, "Layer: %d, %s, %d staves, %d half staves per stave", i, mlot.c_str(), mNumberOfStaves[i], mNumberOfHalfStaves[i]);
649712
}
650713
LOGF(info, "Total number of chips: %d", getNumberOfChips());
651714

Detectors/Upgrades/ALICE3/TRK/simulation/include/TRKSimulation/Detector.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,9 @@ namespace trk
3131
class Detector : public o2::base::DetImpl<Detector>
3232
{
3333
public:
34+
static constexpr Int_t mNumberOfVolumes = 44; /// hardcoded for the current geometry = 8 MLOT layers + 36 volumes in the VD. TODO: automatize or change according to the current geometry
35+
static constexpr Int_t mNumberOfVolumesVD = 36; /// hardcoded for the current geometry = 36 volumes in the VD. TODO: automatize or change according to the current geometry
36+
3437
Detector(bool active);
3538
Detector();
3639
~Detector();
@@ -96,6 +99,18 @@ class Detector : public o2::base::DetImpl<Detector>
9699

97100
void defineSensitiveVolumes();
98101

102+
protected:
103+
std::vector<int> mSensorID; //! layer identifiers
104+
std::vector<TString> mSensorName; //! layer names
105+
106+
public:
107+
static constexpr Int_t sNumberVDPetalCases = 4; //! Number of VD petals
108+
int getNumberOfLayers() const { return mLayers.size(); } //! Number of TRK layers
109+
int getNumberOfLayersVD() const { return mPetalCases[0].mPetalLayers.size(); }
110+
int getNumberOfDisksVD() const { return mPetalCases[0].mPetalDisks.size(); }
111+
112+
void Print(FairVolume* vol, int volume, int subDetID, int layer, int stave, int halfstave, int chipID) const;
113+
99114
template <typename Det>
100115
friend class o2::base::DetImpl;
101116
ClassDefOverride(Detector, 1);

0 commit comments

Comments
 (0)