CbmRoot
Loading...
Searching...
No Matches
CbmStsSimSensor.cxx
Go to the documentation of this file.
1/* Copyright (C) 2013-2020 GSI Helmholtzzentrum fuer Schwerionenforschung, Darmstadt
2 SPDX-License-Identifier: GPL-3.0-only
3 Authors: Volker Friese [committer] */
4
11#include "CbmStsSimSensor.h"
12
13#include "CbmStsAddress.h"
14#include "CbmStsElement.cxx"
15#include "CbmStsPoint.h"
16#include "CbmStsSensorPoint.h"
17
18#include <FairField.h>
19#include <FairRun.h>
20
21#include <TGeoBBox.h>
22
23using std::vector;
24
26
27
28 // ----- Constructor ---------------------------------------------------
30 : fElement(element)
31{
32}
33// -------------------------------------------------------------------------
34
35
36// ----- Get the unique address from the sensor name (static) ----------
38{
39
40 Int_t unit = 10 * (name[5] - '0') + name[6] - '0' - 1;
41 Int_t ladder = 10 * (name[9] - '0') + name[10] - '0' - 1;
42 Int_t hLadder = (name[11] == 'U' ? 0 : 1);
43 Int_t module = 10 * (name[14] - '0') + name[15] - '0' - 1;
44 Int_t sensor = 10 * (name[18] - '0') + name[19] - '0' - 1;
45
46 return CbmStsAddress::GetAddress(unit, ladder, hLadder, module, sensor);
47}
48// -------------------------------------------------------------------------
49
50
51// ----- Get the sensor Id within the module ---------------------------
57// -------------------------------------------------------------------------
58
59
60// ----- Process a CbmStsPoint ------------------------------------------
61Int_t CbmStsSimSensor::ProcessPoint(const CbmStsPoint* point, Double_t eventTime, const CbmLink& link)
62{
63
64 // --- Physical node
65 assert(fElement);
66 TGeoPhysicalNode* node = fElement->GetPnode();
67
68 // --- Set current link
69 fCurrentLink = link;
70
71 // --- Transform start coordinates into local C.S.
72 Double_t global[3];
73 Double_t local[3];
74 global[0] = point->GetXIn();
75 global[1] = point->GetYIn();
76 global[2] = point->GetZIn();
77 node->GetMatrix()->MasterToLocal(global, local);
78 Double_t x1 = local[0];
79 Double_t y1 = local[1];
80 Double_t z1 = local[2];
81
82 // --- Transform stop coordinates into local C.S.
83 global[0] = point->GetXOut();
84 global[1] = point->GetYOut();
85 global[2] = point->GetZOut();
86 node->GetMatrix()->MasterToLocal(global, local);
87 Double_t x2 = local[0];
88 Double_t y2 = local[1];
89 Double_t z2 = local[2];
90
91 // --- Average track direction in local c.s.
92 Double_t tXav = 0.;
93 Double_t tYav = 0.;
94 // Int_t tZav = 0;
95 if (abs(z2 - z1) > 0.000001) {
96 tXav = (x2 - x1) / (z2 - z1);
97 tYav = (y2 - y1) / (z2 - z1);
98 // tZav = 1;
99 }
100
101 // --- Normally, the entry and exit coordinates are slightly outside of
102 // --- the active node, which is a feature of the transport engine.
103 // --- We correct here for this, in case a track was entering or
104 // --- exiting the sensor (not for tracks newly created or stopped
105 // --- in the sensor volume).
106 // --- We here consider only the case of tracks leaving through the front
107 // --- or back plane. The rare case of tracks leaving through the sensor
108 // --- sides is caught by the digitisation procedure.
109 Double_t dZ = dynamic_cast<TGeoBBox*>(node->GetShape())->GetDZ();
110
111 // --- Correct start coordinates in case of entry step
112 if (point->IsEntry()) {
113
114 // Get track direction in local c.s.
115 global[0] = point->GetPx();
116 global[1] = point->GetPy();
117 global[2] = point->GetPz();
118 Double_t* rot;
119 rot = node->GetMatrix()->GetRotationMatrix();
120 TGeoHMatrix rotMat;
121 rotMat.SetRotation(rot);
122 rotMat.MasterToLocal(global, local);
123 if (local[2] != 0.) {
124 ; // should always be; else no correction
125 Double_t tX = local[0] / local[2]; // px/pz
126 Double_t tY = local[1] / local[2]; // py/pz
127
128 // New start coordinates
129 Double_t xNew = 0.;
130 Double_t yNew = 0.;
131 Double_t zNew = 0.;
132 if (z1 > 0.) zNew = dZ - 1.e-4; // front plane, safety margin 1 mum
133 else
134 zNew = 1.e-4 - dZ; // back plane, safety margin 1 mum
135 xNew = x1 + tX * (zNew - z1);
136 yNew = y1 + tY * (zNew - z1);
137
138 x1 = xNew;
139 y1 = yNew;
140 z1 = zNew;
141 } //? pz != 0.
142
143 } //? track has entered
144
145 // --- Correct stop coordinates in case of being outside the sensor
146 if (TMath::Abs(z2) > dZ) {
147
148 // Get track direction in local c.s.
149 global[0] = point->GetPxOut();
150 global[1] = point->GetPyOut();
151 global[2] = point->GetPzOut();
152 Double_t* rot;
153 rot = node->GetMatrix()->GetRotationMatrix();
154 TGeoHMatrix rotMat;
155 rotMat.SetRotation(rot);
156 rotMat.MasterToLocal(global, local);
157 Double_t tX = 0.;
158 Double_t tY = 0.;
159 // Use momentum components for track direction, if available
160 if (local[2] != 0.) {
161 tX = local[0] / local[2]; // px/pz
162 tY = local[1] / local[2]; // py/pz
163 }
164 // Sometimes, a track is stopped outside the sensor volume.
165 // Then we take the average track direction as best approximation.
166 // Note that there may be cases where entry and exit coordinates are
167 // the same. In this case, tXav = tYav = 0; there will be no correction
168 // of the coordinates.
169 else {
170 tX = tXav; // (x2-x1)/(z2-z1) or 0 if z2 = z1
171 tY = tYav; // (y2-y1)/(z2-z1) or 0 if z2 = z1
172 }
173
174 // New coordinates
175 Double_t xNew = 0.;
176 Double_t yNew = 0.;
177 Double_t zNew = 0.;
178 if (z2 > 0.) zNew = dZ - 1.e-4; // front plane, safety margin 1 mum
179 else
180 zNew = 1.e-4 - dZ; // back plane, safety margin 1 mum
181 xNew = x2 + tX * (zNew - z2);
182 yNew = y2 + tY * (zNew - z2);
183
184 x2 = xNew;
185 y2 = yNew;
186 z2 = zNew;
187
188 } //? track step outside sensor
189
190
191 // --- Momentum magnitude
192 Double_t px = 0.5 * (point->GetPx() + point->GetPxOut());
193 Double_t py = 0.5 * (point->GetPy() + point->GetPyOut());
194 Double_t pz = 0.5 * (point->GetPz() + point->GetPzOut());
195 Double_t p = TMath::Sqrt(px * px + py * py + pz * pz);
196
197 // --- Get magnetic field
198 global[0] = 0.5 * (point->GetXIn() + point->GetXOut());
199 global[1] = 0.5 * (point->GetYIn() + point->GetYOut());
200 global[2] = 0.5 * (point->GetZIn() + point->GetZOut());
201 Double_t bField[3] = {0., 0., 0.};
202 if (FairRun::Instance()->GetField()) FairRun::Instance()->GetField()->Field(global, bField);
203
204 // --- Absolute time of StsPoint
205 Double_t pTime = eventTime + point->GetTime();
206
207 // --- Create SensorPoint
208 // Note: there is a conversion from kG to T in the field values.
209 CbmStsSensorPoint* sPoint = new CbmStsSensorPoint(x1, y1, z1, x2, y2, z2, p, point->GetEnergyLoss(), pTime,
210 bField[0] / 10., bField[1] / 10., bField[2] / 10., point->GetPid());
211
212 // --- Calculate the detector response
213 Int_t result = CalculateResponse(sPoint);
214 delete sPoint;
215
216 return result;
217}
218// -------------------------------------------------------------------------
@ kStsSensor
ClassImp(CbmStsSimSensor) CbmStsSimSensor
Class representing an element of the STS setup.
Int_t GetAddress() const
TGeoPhysicalNode * GetPnode() const
double GetPxOut() const
Definition CbmStsPoint.h:79
int32_t GetPid() const
Definition CbmStsPoint.h:82
bool IsEntry() const
Definition CbmStsPoint.h:84
double GetZOut() const
Definition CbmStsPoint.h:78
double GetPzOut() const
Definition CbmStsPoint.h:81
double GetXOut() const
Definition CbmStsPoint.h:76
double GetYIn() const
Definition CbmStsPoint.h:74
double GetXIn() const
Definition CbmStsPoint.h:73
double GetPyOut() const
Definition CbmStsPoint.h:80
double GetZIn() const
Definition CbmStsPoint.h:75
double GetYOut() const
Definition CbmStsPoint.h:77
Container class for a local point in a STS sensor.
Class for the simulation of a sensor in the CBM-STS.
CbmStsSimSensor(CbmStsElement *element=nullptr)
Standard constructor.
Int_t GetSensorId() const
Sensor ID.
Int_t ProcessPoint(const CbmStsPoint *point, Double_t eventTime, const CbmLink &link)
Process one MC Point.
CbmStsElement * fElement
static UInt_t GetAddressFromName(TString name)
Get the address from the sensor name (static)
virtual Int_t CalculateResponse(CbmStsSensorPoint *point)=0
Link to currently processed MCPoint.
int32_t GetAddress(uint32_t unit=0, uint32_t ladder=0, uint32_t halfladder=0, uint32_t module=0, uint32_t sensor=0, uint32_t side=0, uint32_t version=kCurrentVersion)
Construct address.
uint32_t GetElementId(int32_t address, int32_t level)
Get the index of an element.