ATLAS Offline Software
Loading...
Searching...
No Matches
TGCSensitiveDetector.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2022 CERN for the benefit of the ATLAS collaboration
3*/
4
9#include "G4Exception.hh"
10#include "G4Geantino.hh"
11#include "G4ChargedGeantino.hh"
12
13#include <string>
14
16
17// construction/destruction
18TGCSensitiveDetector::TGCSensitiveDetector(const std::string& name, const std::string& hitCollectionName)
19 : G4VSensitiveDetector( name )
20 , m_hitCollectionName( hitCollectionName )
21{
23}
24
25// Implemenation of member functions
27{
28 m_myTGCHitColl = nullptr;
29 if (auto* eventInfo = AtlasG4EventUserInfo::GetEventUserInfo()) {
30 m_myTGCHitColl = eventInfo->GetHitCollectionMap()->Find<TGCSimHitCollection>(m_hitCollectionName);
31 m_g4UserEventInfo = eventInfo;
32 }
33}
34
35G4bool TGCSensitiveDetector::ProcessHits(G4Step* aStep,G4TouchableHistory*) {
36
37 if (!m_myTGCHitColl) {
38 G4Exception("TGCSensitiveDetector::ProcessHits", "TGCHitCollectionMissing", FatalException,
39 "Hit collection not initialized; did SetupEvent run?");
40 return false;
41 }
42
43 G4Track* track = aStep->GetTrack();
44
45 if (track->GetDefinition()->GetPDGCharge() == 0.0) {
46 if (track->GetDefinition()!=G4Geantino::GeantinoDefinition()) return true;
47 else if (track->GetDefinition()==G4ChargedGeantino::ChargedGeantinoDefinition()) return true;
48 }
49 const G4TouchableHistory* touchHist = static_cast<const G4TouchableHistory*>(aStep->GetPreStepPoint()->GetTouchable());
50 G4ThreeVector position = aStep->GetPreStepPoint()->GetPosition();
51 const G4AffineTransform trans = track->GetTouchable()->GetHistory()->GetTopTransform();
52
53 // fields for the TGC identifier construction
54 std::string stationName;
55 int stationEta(0);
56 int stationPhi(0);
57 int gasGap = 0;
58
59 // TGC hit information
60 double globalTime = aStep->GetPreStepPoint()->GetGlobalTime();
61 Amg::Vector3D localPosition = Amg::Hep3VectorToEigen( trans.TransformPoint(position) );
62 G4ThreeVector direcos = aStep->GetPreStepPoint()->GetMomentumDirection();
63 Amg::Vector3D localDireCos = Amg::Hep3VectorToEigen( trans.TransformAxis(direcos) );
64
65 // scan geometry tree to identify hit channel
66 int zside(0);
67 bool isAssembly = false;
68 for (int i=touchHist->GetHistoryDepth();i>=0;i--) {
69
70 std::string::size_type npos;
71 std::string::size_type nposStat;
72 std::string volName = touchHist->GetVolume(i)->GetName();
73
74 // check if this station is an assembly
75 if ((npos = volName.find("av_")) != std::string::npos &&
76 (npos = volName.find("impr_")) != std::string::npos) isAssembly = true;
77
78 // stationName and stationPhi
79 if ((npos = volName.find("station")) != std::string::npos && (!isAssembly)) {
80
81 stationName = volName.substr(0,npos-2);
82 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
83 if (volCopyNo > 0) {
84 zside = 1;
85 } else {
86 zside = -1;
87 }
88 if (stationName.at(2) == 'F') {
89
90 stationPhi = (abs(volCopyNo%100)-1)*3;
91 if (abs(volCopyNo/100) > 3) {
92 stationPhi += abs(volCopyNo/100)-3;
93 } else {
94 stationPhi += abs(volCopyNo/100);
95 }
96
97 stationPhi -= 1;
98 if (stationPhi <= 0) {
99 stationPhi = 24 - stationPhi;
100 }
101
102 } else if (stationName.at(2) == 'E') {
103 if (stationName.at(1) == '4') {
104
105 stationPhi = (abs(volCopyNo%100)-1)*3+abs(volCopyNo/100);
106
107 if (abs(volCopyNo%100) < 4) {
108 stationPhi = stationPhi - 1;
109 if (stationPhi <= 0) {
110 stationPhi = 21 - stationPhi;
111 }
112 } else if(abs(volCopyNo%100) < 7) {
113 stationPhi = stationPhi - 1 - 1;
114 } else {
115 stationPhi = stationPhi - 2 - 1;
116 }
117
118 } else {
119
120 stationPhi = (abs(volCopyNo%100)-1)*6+abs(volCopyNo/100);
121
122 stationPhi -= 2;
123 if (stationPhi <= 0) {
124 stationPhi = 48 - stationPhi;
125 }
126 }
127 }
128 } else if ((nposStat = volName.find("impr_")) != std::string::npos &&
129 (npos = volName.find("TGC")) != std::string::npos && isAssembly ) {
130 // vol name for Assembly components are
131 // av_WWW_impr_XXX_Muon::BMSxMDTxx_pv_ZZZ_NAME
132 // where WWW is ass. istance nr.
133 // XXX is comp. imprint nr.
134 // BMSxMDTxx is the name of the comp. log.Vol.
135 // x station sub-type; xx technology subtype
136 // ZZZ is No of order of this daugther
137 // NAME is the comp. tag (geoIdentifierTag)
138 // for TGCs it is stPhiJob[aaa] with
139 // aaa = 1000*stationPhi+Job;
140 // copy numbers for Ass.components are =
141 // CopyNoBase(= geoIdentifierTag of the assembly) + geoIdentifierTag of the component
142 // geoIdentifierTag of the component = Job
143 // geoIdentifierTag of the assembly = (sideC*10000 +
144 // mirsign*1000 + abs(zi)*100 + fi+1)*100000;
145 // mirsign*1000 + abs(zi)*100 + fi+1)*100000;
146 // mirsign = 1 if zi<0 and !mirrored; otherwise 0
147 std::string::size_type loc1,loc2;
148 if ((loc1 = volName.find("Muon::")) != std::string::npos) {
149 stationName = volName.substr(loc1+6,3); //type only
150 }
151
152 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
153 int copyNrBase = int(volCopyNo/100000);
154 int sideC = int(copyNrBase/10000);
155 int zi = int((copyNrBase%1000)/100);
156 if (sideC == 1) zi = -zi;
157 if (sideC) {
158 zside = -1;
159 } else {
160 zside = 1;
161 }
162 if (stationName.at(2) == 'F') {
163
164 stationPhi = (abs(copyNrBase%100)-1)*3;
165 if (abs(copyNrBase/100) > 3) {
166 stationPhi += abs(copyNrBase/100)-3;
167 } else {
168 stationPhi += abs(copyNrBase/100);
169 }
170
171 stationPhi -= 1;
172 if (stationPhi <= 0) {
173 stationPhi = 24 - stationPhi;
174 }
175
176 } else if (stationName.at(2) == 'E') {
177 if (stationName.at(1) == '4') {
178
179 stationPhi = (abs(copyNrBase%100)-1)*3+abs(copyNrBase/100);
180
181 if (abs(copyNrBase%100) < 4) {
182 stationPhi = stationPhi - 1;
183 if (stationPhi <= 0) {
184 stationPhi = 21 - stationPhi;
185 }
186 } else if(abs(copyNrBase%100) < 7) {
187 stationPhi = stationPhi - 1 - 1;
188 } else {
189 stationPhi = stationPhi - 2 - 1;
190 }
191 } else {
192
193 stationPhi = (abs(copyNrBase%100)-1)*6+abs(copyNrBase/100);
194
195 stationPhi -= 2;
196 if (stationPhi <= 0) {
197 stationPhi = 48 - stationPhi;
198 }
199 }
200 }
201
202 // now get the geoIdentifierTag of the rpc components
203 int gmID = 0;
204 if ((loc1 = volName.find('[')) != std::string::npos) {
205 if ((loc2 = volName.find(']', loc1+1)) != std::string::npos) {
206 std::istringstream istrvar(volName.substr(loc1+1,loc2-loc1-1));
207 istrvar>>gmID;
208 }
209 }
210 // stationEta, stationPhi
211 stationEta = zside*int(gmID%100);
212 if (gmID > 999) stationPhi = gmID/1000;
213
214 // stationEta
215 } else if ((npos = volName.find("tgccomponent")) != std::string::npos && (!isAssembly)) {
216 int volCopyNo = abs(touchHist->GetVolume(i)->GetCopyNo());
217 stationEta = zside*volCopyNo%100;
218 if (volCopyNo > 1000) { // stationPhi overridden by the number assigned by MuonGeoModel
219 stationPhi = volCopyNo/1000;
220 }
221 // gasGap
222 } else if ((npos = volName.find("Gas Volume Layer")) != std::string::npos) {
223 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
224 int iStation = atoi(stationName.substr(1,1).c_str());
225 if (zside < 0) {
226 if (iStation == 1)
227 gasGap = 3-(volCopyNo-3)/4;
228 else
229 gasGap = 2-(volCopyNo-3)/4;
230 } else {
231// if (iStation == 1)
232 gasGap = (volCopyNo-3)/4+1;
233// else
234// gasGap = (volCopyNo-3)/4+1;
235 }
236 } else if ((npos = volName.find("TGCGas")) != std::string::npos) {
237
238 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
239
240 if (volCopyNo != 0)
241 gasGap = volCopyNo;
242 }
243
244 }
245
246 //construct the hit identifier
247 HitID TGCid = m_muonHelper->BuildTgcHitId(stationName,
248 stationPhi,
249 stationEta,
250 gasGap);
251 //m_muonHelper->Print(TGCid);
252
253 // construct new tgc hit
254 TrackHelper trHelp(aStep->GetTrack());
255
256 m_myTGCHitColl->Emplace(TGCid,
257 globalTime,
258 localPosition,
259 localDireCos,
260 trHelp.GenerateParticleLink(m_g4UserEventInfo ? m_g4UserEventInfo->GetEventStore() : nullptr),
261 aStep->GetTotalEnergyDeposit(),
262 aStep->GetStepLength(),
263 track->GetDefinition()->GetPDGEncoding(),
264 aStep->GetPreStepPoint()->GetKineticEnergy());
265 return true;
266}
int HitID
AtlasHitsVector< TGCSimHit > TGCSimHitCollection
static AtlasG4EventUserInfo * GetEventUserInfo()
G4bool ProcessHits(G4Step *aStep, G4TouchableHistory *ROHist) override final
TGCSensitiveDetector(const std::string &name, const std::string &hitCollectionName)
construction/destruction
std::string m_hitCollectionName
member data
const TgcHitIdHelper * m_muonHelper
TGCSimHitCollection * m_myTGCHitColl
AtlasG4EventUserInfo * m_g4UserEventInfo
void Initialize(G4HCofThisEvent *HCE) override final
member functions
static const TgcHitIdHelper * GetHelper()
HepMcParticleLink GenerateParticleLink()
Generates a creates new HepMcParticleLink object on the stack based on GetUniqueID(),...
Definition TrackHelper.h:52
Amg::Vector3D Hep3VectorToEigen(const CLHEP::Hep3Vector &CLHEPvector)
Converts a CLHEP-based CLHEP::Hep3Vector into an Eigen-based Amg::Vector3D.
Eigen::Matrix< double, 3, 1 > Vector3D