1212// / \file SegmentationMosaix.h
1313// / \brief Definition of the SegmentationMosaix class
1414// / \author felix.schlepper@cern.ch
15+ // / \author chunzheng.wang@cern.ch
1516
1617#ifndef ALICEO2_ITS3_SEGMENTATIONMOSAIX_H_
1718#define ALICEO2_ITS3_SEGMENTATIONMOSAIX_H_
1819
19- #include < type_traits>
20-
2120#include " MathUtils/Cartesian.h"
2221#include " ITS3Base/SpecsV2.h"
2322
@@ -43,24 +42,22 @@ class SegmentationMosaix
4342 // 3. The detector coordinate system. Defined by the row and column segmentation
4443 // defined at the upper edge in the flat coord.
4544
46- // row,col=0
47- // |
48- // v
49- // x----------------------x
50- // | | |
51- // | | |
52- // | | | ^ x
53- // | | | |
54- // | | | |
55- // | | | |
56- // |-----------X----------| X marks (x,z)=(0,0) X----> z
57- // | | |
45+ // O----------------------|
5846 // | | |
47+ // | | | ^ x
48+ // | | | |
49+ // | | | |
50+ // | | | |
51+ // | | | X----> z X marks (x,z)=(0,0)
52+ // |-----------X----------|
53+ // | | | O----> col O marks (row,col)=(0,0)
54+ // | | | |
55+ // | | | |
56+ // | | | v
57+ // | | | row
5958 // | | |
60- // | | |
61- // | | |
62- // | | |
63- // x----------------------x
59+ // |----------------------|
60+
6461 public:
6562 constexpr SegmentationMosaix (int layer) : mRadius(static_cast <float >(constants::radiiMiddle[layer])) {}
6663 constexpr ~SegmentationMosaix () = default ;
@@ -79,7 +76,6 @@ class SegmentationMosaix
7976 static constexpr float PitchCol{constants::pixelarray::pixels::mosaix::pitchZ};
8077 static constexpr float PitchRow{constants::pixelarray::pixels::mosaix::pitchX};
8178 static constexpr float SensorLayerThickness{constants::totalThickness};
82- static constexpr float NominalYShift{constants::nominalYShift};
8379
8480 // / Transformation from the curved surface to a flat surface.
8581 // / Additionally a shift in the flat coordinates must be applied because
@@ -102,10 +98,10 @@ class SegmentationMosaix
10298 // stack
10399 float dist = std::hypot (xCurved, yCurved);
104100 float phi = std::atan2 (yCurved, xCurved);
105- xFlat = (mRadius * phi) - WidthH;
106101 // the y position is in the silicon volume however we need the chip volume (silicon+metalstack)
107102 // this is accounted by a y shift
108- yFlat = dist - mRadius + NominalYShift;
103+ xFlat = WidthH - mRadius * phi;
104+ yFlat = dist - mRadius ;
109105 }
110106
111107 // / Transformation from the flat surface to a curved surface
@@ -122,11 +118,12 @@ class SegmentationMosaix
122118 {
123119 // MUST align the flat surface with the curved surface with the original pixel array is on and account for metal
124120 // stack
121+ float dist = yFlat + mRadius ;
122+ float phi = (WidthH - xFlat) / mRadius ;
125123 // the y position is in the chip volume however we need the silicon volume
126124 // this is accounted by a -y shift
127- float dist = yFlat - NominalYShift + mRadius ;
128- xCurved = dist * std::cos ((xFlat + WidthH) / mRadius );
129- yCurved = dist * std::sin ((xFlat + WidthH) / mRadius );
125+ xCurved = dist * std::cos (phi);
126+ yCurved = dist * std::sin (phi);
130127 }
131128
132129 // / Transformation from Geant detector centered local coordinates (cm) to
@@ -142,8 +139,11 @@ class SegmentationMosaix
142139 // / \param int iCol Detector z cell coordinate.
143140 constexpr bool localToDetector (float const xRow, float const zCol, int & iRow, int & iCol) const noexcept
144141 {
142+ if (!isValidLoc (xRow, zCol)) {
143+ return false ;
144+ }
145145 localToDetectorUnchecked (xRow, zCol, iRow, iCol);
146- if (!isValid (iRow, iCol)) {
146+ if (!isValidDet (iRow, iCol)) {
147147 iRow = iCol = -1 ;
148148 return false ;
149149 }
@@ -167,49 +167,54 @@ class SegmentationMosaix
167167 // / center of the sensitive volume.
168168 // / If iRow and or iCol is outside of the segmentation range a value of -0.5*Dx()
169169 // / or -0.5*Dz() is returned.
170- constexpr bool detectorToLocal (int const iRow, int const iCol , float & xRow, float & zCol) const noexcept
170+ bool detectorToLocal (float const row, float const col , float & xRow, float & zCol) const noexcept
171171 {
172- if (!isValid (iRow, iCol )) {
172+ if (!isValidDet (row, col )) {
173173 return false ;
174174 }
175- detectorToLocalUnchecked (iRow, iCol , xRow, zCol);
176- return isValid (xRow, zCol);
175+ detectorToLocalUnchecked (row, col , xRow, zCol);
176+ return isValidLoc (xRow, zCol);
177177 }
178178
179179 // Same as detectorToLocal w.o. checks.
180180 // We position ourself in the middle of the pixel.
181- constexpr void detectorToLocalUnchecked (int const iRow, int const iCol , float & xRow, float & zCol) const noexcept
181+ void detectorToLocalUnchecked (float const row, float const col , float & xRow, float & zCol) const noexcept
182182 {
183- xRow = -(static_cast < float >(iRow) + 0 .5f ) * PitchRow + WidthH;
184- zCol = (static_cast < float >(iCol) + 0 .5f ) * PitchCol - LengthH;
183+ xRow = -(row + 0 .5f ) * PitchRow + WidthH;
184+ zCol = (col + 0 .5f ) * PitchCol - LengthH;
185185 }
186186
187- bool detectorToLocal (int const row, int const col, math_utils::Point3D<float >& loc) const noexcept
187+ bool detectorToLocal (float const row, float const col, math_utils::Point3D<float >& loc) const noexcept
188188 {
189189 float xRow{0 .}, zCol{0 .};
190190 if (!detectorToLocal (row, col, xRow, zCol)) {
191191 return false ;
192192 }
193- loc.SetCoordinates (xRow, NominalYShift , zCol);
193+ loc.SetCoordinates (xRow, 0 . 0f , zCol);
194194 return true ;
195195 }
196196
197- void detectorToLocalUnchecked (int const row, int const col, math_utils::Point3D<float >& loc) const noexcept
197+ void detectorToLocalUnchecked (float const row, float const col, math_utils::Point3D<float >& loc) const noexcept
198198 {
199199 float xRow{0 .}, zCol{0 .};
200200 detectorToLocalUnchecked (row, col, xRow, zCol);
201- loc.SetCoordinates (xRow, NominalYShift , zCol);
201+ loc.SetCoordinates (xRow, 0 . 0f , zCol);
202202 }
203203
204204 private:
205+ // Check local coordinates (cm) validity.
205206 template <typename T>
206- [[nodiscard]] constexpr bool isValid (T const row , T const col ) const noexcept
207+ constexpr bool isValidLoc (T const x , T const z ) const noexcept
207208 {
208- if constexpr (std::is_floating_point_v<T>) { // compares in local coord.
209- return (-WidthH < row && row < WidthH && -LengthH < col && col < LengthH);
210- } else { // compares in rows/cols
211- return !static_cast <bool >(row < 0 || row >= static_cast <int >(NRows) || col < 0 || col >= static_cast <int >(NCols));
212- }
209+ return (-WidthH < x && x < WidthH && -LengthH < z && z < LengthH);
210+ }
211+
212+ // Check detector coordinates validity.
213+ template <typename T>
214+ constexpr bool isValidDet (T const row, T const col) const noexcept
215+ {
216+ return (row >= 0 && row < static_cast <T>(NRows) &&
217+ col >= 0 && col < static_cast <T>(NCols));
213218 }
214219
215220 float mRadius ;
0 commit comments