ATLAS Offline Software
Loading...
Searching...
No Matches
CSCSensitiveDetectorCosmics Class Reference

#include <CSCSensitiveDetectorCosmics.h>

Inheritance diagram for CSCSensitiveDetectorCosmics:
Collaboration diagram for CSCSensitiveDetectorCosmics:

Public Member Functions

 CSCSensitiveDetectorCosmics (const std::string &name, const std::string &hitCollectionName)
 construction/destruction
void Initialize (G4HCofThisEvent *HCE) override final
 member functions
G4bool ProcessHits (G4Step *aStep, G4TouchableHistory *ROhist) override final

Private Member Functions

 FRIEND_TEST (CSCSensitiveDetectorCosmicstest, Initialize)
 FRIEND_TEST (CSCSensitiveDetectorCosmicstest, ProcessHits)

Private Attributes

Amg::Vector3D m_mom
double m_momMag
Amg::Vector3D m_vertex
Amg::Vector3D m_currVertex
Amg::Vector3D m_globH
double m_globalTime
std::string m_hitCollectionName
 member data
CSCSimHitCollectionm_myCSCHitColl {nullptr}
AtlasG4EventUserInfom_g4UserEventInfo {nullptr}
const CscHitIdHelperm_muonHelper

Detailed Description

Author
ketev.nosp@m.i@bn.nosp@m.l.gov

Class methods and properties

The method CSCSensitiveDetectorCosmics::ProcessHits is executed by the G4 kernel each time a charged particle (or a geantino) crosses one of the CSC Gas Gaps.

Navigating with the toucahbleHistory method GetHistoryDepth() through the hierarchy of the volumes crossed by the particles, the CSCSensitiveDetectorCosmics determinates the correct set of geometry parameters to be folded in the Simulation Identifier associated to each hit. The CSC SimIDs are 32-bit unsigned integers, built using the MuonSimEvent/CscHitIdHelper class which inherits from the MuonHitIdHelper base class.

The modified version (Daniela Rebuzzi, 16/12/2005) calculates the tof for the cosmics, using as t0 the time to the closest approach of the track to (0,0,0). This implementation works also for slow particles, since the discrimination physics event/cosmics is done relying on the G4Track vertex (not on the tof).

We describe in the following, how each field of the identifier is retrieved.

1) stationName, stationEta, stationPhi: when a volume is found in the hierarchy, whose name contains the substring "station", the stationName is extracted from the volume's name; stationPhi and stationEta are calculated starting from the volume copy number, assigned by MuonGeoModel.

2) multilayer: when a volume is found in the hierarchy, whose name contains the substring "component", the multilayer is set to 1 or to 2, according to the component number (multilayer=1 if the component copy number is 1, multilayer=3 if the component copy number is 2).

3) wireLayer: when a volume is found in the hierarchy, whose name contains the substring "CscArCO2", the wire Layer is calculated, increasing with |z| Atlas global coordinate.

notes:

1) for each hit, the time of flight (the G4 globalTime), is recorded and associated to the hit.

2) the CSCHit object contains: the SimID, the globalTime, the energy deposited, the start and end point of the step in local coordinates (chamber reference system), the particle pdg and the track identifier.

Definition at line 68 of file CSCSensitiveDetectorCosmics.h.

Constructor & Destructor Documentation

◆ CSCSensitiveDetectorCosmics()

CSCSensitiveDetectorCosmics::CSCSensitiveDetectorCosmics ( const std::string & name,
const std::string & hitCollectionName )

construction/destruction

Definition at line 22 of file CSCSensitiveDetectorCosmics.cxx.

23 : G4VSensitiveDetector( name )
24 // START OF COSMICS-SPECIFIC CODE
25 , m_momMag(0.)
26 , m_globalTime(0.)
27 // END OF COSMICS-SPECIFIC CODE
28 , m_hitCollectionName( hitCollectionName )
29{
31}
static const CscHitIdHelper * GetHelper()

Member Function Documentation

◆ FRIEND_TEST() [1/2]

CSCSensitiveDetectorCosmics::FRIEND_TEST ( CSCSensitiveDetectorCosmicstest ,
Initialize  )
private

◆ FRIEND_TEST() [2/2]

CSCSensitiveDetectorCosmics::FRIEND_TEST ( CSCSensitiveDetectorCosmicstest ,
ProcessHits  )
private

◆ Initialize()

void CSCSensitiveDetectorCosmics::Initialize ( G4HCofThisEvent * HCE)
finaloverride

member functions

Definition at line 34 of file CSCSensitiveDetectorCosmics.cxx.

35{
36 m_myCSCHitColl = nullptr;
37 if (auto* eventInfo = AtlasG4EventUserInfo::GetEventUserInfo()) {
38 m_myCSCHitColl = eventInfo->GetHitCollectionMap()->Find<CSCSimHitCollection>(m_hitCollectionName);
39 m_g4UserEventInfo = eventInfo;
40 }
41 // START OF COSMICS-SPECIFIC CODE
42 m_mom = Amg::Vector3D(0.,0.,0.);
43 m_globH = Amg::Vector3D(0.,0.,0.);
44 // END OF COSMICS-SPECIFIC CODE
45}
AtlasHitsVector< CSCSimHit > CSCSimHitCollection
static AtlasG4EventUserInfo * GetEventUserInfo()
Eigen::Matrix< double, 3, 1 > Vector3D

◆ ProcessHits()

G4bool CSCSensitiveDetectorCosmics::ProcessHits ( G4Step * aStep,
G4TouchableHistory * ROhist )
finaloverride

CSCs sensitive to charged particle only; plus energy threshold

attributes of the CSC identifier construction

hit information to be recorded

the track id

scan geometry tree to identify the gas layer

station: name, eta and phi (-> chamber!)

station name, station eta and station phi

station name

station eta and station phi

chamber layer

chamber layer

the wire layer number

get the particle ID

record global time

energy deposit

get the transformation

local position of HitStart and HitEnd

get the end of the step as return by G4 - could be at the beginning of the next volume

construct the hit identifier

insert hit in collection

Definition at line 47 of file CSCSensitiveDetectorCosmics.cxx.

47 {
48
49 if (!m_myCSCHitColl) {
50 G4Exception("CSCSensitiveDetectorCosmics::ProcessHits", "CSCCosmicHitCollectionMissing", FatalException,
51 "Hit collection not initialized; did SetupEvent run?");
52 return false;
53 }
54
55 G4Track* currentTrack = aStep->GetTrack();
56
58 auto trackDef = currentTrack->GetDefinition();
59 if (trackDef->GetPDGCharge() == 0.0) {
60 if (trackDef != G4Geantino::GeantinoDefinition()) return true;
61 else if (trackDef == G4ChargedGeantino::ChargedGeantinoDefinition()) return true;
62 }
63
64 const G4TouchableHistory* touchHist = static_cast<const G4TouchableHistory*>(aStep->GetPreStepPoint()->GetTouchable());
65 G4ThreeVector startPos=aStep->GetPreStepPoint()->GetPosition();
66 G4ThreeVector endPos=aStep->GetPostStepPoint()->GetPosition();
67 double kinEnergy = aStep->GetPreStepPoint()->GetKineticEnergy();
68
70
71 std::string stationName="";
72 int stationEta=0;
73 int stationPhi=0;
74 int multiLayer=0;
75 int wireLayer=0;
76
78
79 Amg::Vector3D HitStart = Amg::Vector3D(-1000,-1000,-1000);
80 Amg::Vector3D HitEnd = Amg::Vector3D(-1000,-1000,-1000);
81 double globalTime = -1;
82 double energyDeposit= -1;
83 G4int lundcode = -1;
85 //const int trackid(aStep->GetTrack()->GetTrackID());
86
87 // START OF COSMICS-SPECIFIC CODE
88 // global coordinates
89 Amg::Vector3D globVrtx = Amg::Hep3VectorToEigen( aStep->GetPreStepPoint()->GetPosition() );
90
91 // distance of the hit from (0,0,0) vertex - calculated from the PreStepPoint (approximation)
92 const double dist = globVrtx.mag();
93 const double lightspeed = 299.792458; /* in vacuo speed of light [mm/ns] */ //FIXME this should be taken from standard headers
94 const double tOrigin = dist / lightspeed;
95
96 m_currVertex = Amg::Hep3VectorToEigen( aStep->GetTrack()->GetVertexPosition() );
97
98 // for cosmics: only primary muon tracks - track momentum when first entering the spectrometer (one muon per event)
99 if ((m_currVertex != m_vertex) && (aStep->GetTrack()->GetTrackID() == 1)) {
100 // after calculationg the momentum magnidude, normalize it
101 m_mom = Amg::Hep3VectorToEigen( currentTrack->GetMomentum() );
102 m_momMag = m_mom.mag();
103 m_mom.normalize();
104 // the direction of the primary mu is used to calculate the t0, the position to the t0, m_globH, is ONE for a track
105 Amg::Vector3D globVrtxFix = globVrtx;
106 const double AlphaGlobal = -1*(globVrtxFix[0]*m_mom[0] + globVrtxFix[1]*m_mom[1] + globVrtxFix[2]*m_mom[2])/(m_mom[0]*m_mom[0] + m_mom[1]*m_mom[1] + m_mom[2]*m_mom[2]);
107 m_globH = globVrtxFix + AlphaGlobal*m_mom;
108 // G4cout << "COSMICS MAIN TRACK IN THES CSC!" << G4endl;
109 }
110 const double globalDist = sqrt((m_globH[0] - globVrtx[0])*(m_globH[0] - globVrtx[0]) +
111 (m_globH[1] - globVrtx[1])*(m_globH[1] - globVrtx[1]) +
112 (m_globH[2] - globVrtx[2])*(m_globH[2] - globVrtx[2]));
113 double tof = globalDist / lightspeed;
114 // END OF COSMICS SPECIFIC CODE
115
117
118 bool isAssembly = false;
119 for (int i = touchHist->GetHistoryDepth(); i>=0; --i) {
120 std::string::size_type npos;
121 std::string volName = touchHist->GetVolume(i)->GetName();
122
124 if ((npos = volName.find("av_")) != std::string::npos &&
125 (npos = volName.find("impr_")) != std::string::npos) isAssembly = true;
126
127 if ((npos = volName.find("station")) != std::string::npos && (!isAssembly)) {
128
130 volName.resize(npos-2);
131 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
132 stationName = volName;
133 //stationEta = volCopyNo/100;
134 // bug fix for 14.2.0 to cope with non-mirrored chambers as proposed by
135 // S.Spagnolo (ported from CSCSensitiveDetector.cxx for rel 20.3.3)
136 stationEta = (volCopyNo%1000)/100;
137 stationPhi = abs(volCopyNo%100);
138
139 } else if ((npos = volName.find("CSC")) != std::string::npos && isAssembly ) {
140 // vol name for Assembly components are
141 // av_WWW_impr_XXX_Muon::BMSxMDTxx_pv_ZZZ_NAME
142 // where WWW is ass. istance nr.
143 // XXX is comp. imprint nr.
144 // BMSxMDTxx is the name of the comp. log.Vol.
145 // x station sub-type; xx technology subtype
146 // ZZZ is No of order of this daugther
147 // NAME is the comp. tag (geoIdentifierTag)
148 // for CSCs it is cl[1] or cl[2]
149 // copy numbers for Ass.components are =
150 // CopyNoBase(= geoIdentifierTag of the assembly) + geoIdentifierTag of the component
151 // geoIdentifierTag of the component = Job
152 // geoIdentifierTag of the assembly = (sideC*10000 +
153 // mirsign*1000 + abs(zi)*100 + fi+1)*100000;
154 // mirsign*1000 + abs(zi)*100 + fi+1)*100000;
155
157 std::string::size_type loc1,loc2;
158 if ((loc1 = volName.find("Muon::")) != std::string::npos) {
159 stationName = volName.substr(loc1+6,3); //type only
160 }
161
163 int volCopyNo = touchHist->GetVolume(i)->GetCopyNo();
164 int copyNrBase = int(volCopyNo/100000);
165 int sideC = int(copyNrBase/10000);
166 int zi = int((copyNrBase%1000)/100);
167 // int mirfl = int((copyNrBase%10000)/1000);
168 int fi = int(copyNrBase%100);
169 if (sideC == 1) zi = -zi;
170 stationEta = zi;
171 stationPhi = fi;
172
173 // now get the geoIdentifierTag of the rpc components
174 int gmID = 0;
175 if ((loc1 = volName.find('[')) != std::string::npos) {
176 if ((loc2 = volName.find(']', loc1+1)) != std::string::npos) {
177 std::istringstream istrvar(volName.substr(loc1+1,loc2-loc1-1));
178 istrvar>>gmID;
179 }
180 }
182 multiLayer = gmID;
183 } else if ((npos = volName.find("component")) != std::string::npos && (!isAssembly)) {
184
186 multiLayer = touchHist->GetVolume(i)->GetCopyNo();
187 if(multiLayer==3) multiLayer=2; //multilayer index
188 // G4cout << "CSC:::::: multiLayer "<<multiLayer << G4endl;
189 } else if ((npos = volName.find("CscArCO2")) != std::string::npos) {
190
192 wireLayer=touchHist->GetVolume(i)->GetCopyNo();
193 wireLayer+=1;
194 if(wireLayer==4) wireLayer=1;
195 else if(wireLayer==3) wireLayer=2;
196 else if(wireLayer==2) wireLayer=3;
197 else if(wireLayer==1) wireLayer=4;
198 // G4cout << "CSC:::::: wireLayer "<<wireLayer << G4endl;
199
201 G4String particle=aStep->GetTrack()->GetDefinition()->GetParticleName();
202 // http://www.slac.stanford.edu/BFROOT/www/Computing/Environment/NewUser/htmlbug/node51.html #GEANT code
203 if (particle=="gamma") lundcode=1; // FIXME was photon, but changed to gamma to match CSCSensitiveDetctor
204 else if (particle=="e+") lundcode=2;
205 else if (particle=="e-") lundcode=3;
206 else if (particle=="mu+") lundcode=5;
207 else if (particle=="mu-") lundcode=6;
208 else if (particle=="pi+") lundcode=8;
209 else if (particle=="pi-") lundcode=9;
210 else if (particle=="kaon+") lundcode=11;
211 else if (particle=="kaon-") lundcode=12;
212 else if (particle=="proton") lundcode=14;
213 else if (particle=="anti_proton") lundcode=15;
214 else if (particle=="sigma+") lundcode=19;
215 else if (particle=="sigma-") lundcode=21;
216 else if (particle=="anti_sigma-") lundcode=27;
217 else if (particle=="anti_sigma+") lundcode=29;
218 else if (particle=="deuteron") lundcode=45;
219 else if (particle=="geantino") lundcode=999;
220 else lundcode=0;
221
223 globalTime = aStep->GetPreStepPoint()->GetGlobalTime();
224
226 energyDeposit = aStep->GetTotalEnergyDeposit();
227
229 const G4AffineTransform transform = touchHist->GetHistory()->GetTopTransform();
230
232 HitStart = Amg::Hep3VectorToEigen( transform.TransformPoint(startPos) );
233
236 HitEnd = Amg::Hep3VectorToEigen( transform.TransformPoint(endPos) );
237
238 }
239 }
240
241 // START OF COSMICS SPECIFIC CODE
242 m_vertex = Amg::Hep3VectorToEigen( aStep->GetTrack()->GetVertexPosition() );
243 // if the track vertex is far from (0,0,0), takes the tof, otherwise take the "usual" g4 globalTime
244 (((m_vertex.mag() < 100) || ((fabs(globalTime - tOrigin)) < 0.1) ) ? (m_globalTime = globalTime)
245 : (m_globalTime = tof));
246 // if m_globalTime != globalTime and m_globalTime != tof in the output, this is due to multiple hits
247 // before founding the good one (small approximation)
248 // END OF COSMICS SPECIFIC CODE
249
250 TrackHelper trHelp(aStep->GetTrack());
251
253 HitID CSCid = m_muonHelper->BuildCscHitId(stationName, stationPhi,
254 stationEta, multiLayer, wireLayer);
255
257 m_myCSCHitColl->Emplace(CSCid, m_globalTime, energyDeposit,
258 HitStart, HitEnd, lundcode,
259 trHelp.GenerateParticleLink(m_g4UserEventInfo ? m_g4UserEventInfo->GetEventStore() : nullptr), kinEnergy);
260
261 // #ifndef CSCG4_DEBUG
262 //
263 // // printouts for cosmics
264 // G4cout << "------------------CSC------------------" << G4endl;
265 // G4cout << "Track "<<aStep->GetTrack()->GetTrackID() << G4endl;
266 // G4cout << "Track m_vertex "<<m_vertex[0]<<" " <<m_vertex[1]<<" " <<m_vertex[2] << G4endl;
267// G4cout << "Global position of the hit " << globVrtx[0] <<" " << globVrtx[1] <<" " << globVrtx[2] << G4endl;
268// G4cout << "Distance from (0,0,0) and time " << dist << " " <<tOrigin << G4endl;
269// G4cout << "Momentum "<<m_momMag << G4endl;
270// G4cout << "Momentum director cosines " <<m_mom[0]<<" " <<m_mom[1]<<" " <<m_mom[2] << G4endl;
271// G4cout << "Eta and phi "<<m_mom.eta()<<" " <<m_mom.phi() << G4endl;
272// G4cout << "Closest approach position and distance from (0,0,0) "
273// << m_globH[0] <<" "<<m_globH[1]<<" "<<m_globH[2]<<" "
274// << sqrt(m_globH[0]*m_globH[0] + m_globH[1]*m_globH[1] + m_globH[2]*m_globH[2]) << G4endl;
275// G4cout << "Distance from t0 and tof " << globalDist <<" " <<tof << G4endl;
276// G4cout << "g4 globalTime " << globalTime << G4endl;
277// G4cout << "Time " << m_globalTime << G4endl;
278//
279// G4cout << "TUB "<<m_muonHelper->GetStationName(CSCid)
280// << " "<<m_muonHelper->GetFieldValue("PhiSector")
281// << " "<<m_muonHelper->GetFieldValue("ZSector")
282// << " "<<m_muonHelper->GetFieldValue("ChamberLayer")
283// << " "<<m_muonHelper->GetFieldValue("WireLayer") << G4endl;
284//
285// G4cout << m_muonHelper->GetStationName(CSCid)<<" "<<newHit->print() << G4endl;
286//
287// #endif
288
289 return true;
290}
int HitID
Amg::Vector3D Hep3VectorToEigen(const CLHEP::Hep3Vector &CLHEPvector)
Converts a CLHEP-based CLHEP::Hep3Vector into an Eigen-based Amg::Vector3D.
Amg::Vector3D transform(Amg::Vector3D &v, Amg::Transform3D &tr)
Transform a point from a Trasformation3D.
constexpr uint8_t stationPhi
station Phi 1 to 8
unsigned int constexpr sideC
Definition RPDUtils.h:15
constexpr ParticleHypothesis particle[PARTICLEHYPOTHESES]
the array of masses
@ energyDeposit
@ loc2
generic first and second local coordinate
Definition ParamDefs.h:35
@ loc1
Definition ParamDefs.h:34

Member Data Documentation

◆ m_currVertex

Amg::Vector3D CSCSensitiveDetectorCosmics::m_currVertex
private

Definition at line 83 of file CSCSensitiveDetectorCosmics.h.

◆ m_g4UserEventInfo

AtlasG4EventUserInfo* CSCSensitiveDetectorCosmics::m_g4UserEventInfo {nullptr}
private

Definition at line 90 of file CSCSensitiveDetectorCosmics.h.

90{nullptr};

◆ m_globalTime

double CSCSensitiveDetectorCosmics::m_globalTime
private

Definition at line 85 of file CSCSensitiveDetectorCosmics.h.

◆ m_globH

Amg::Vector3D CSCSensitiveDetectorCosmics::m_globH
private

Definition at line 84 of file CSCSensitiveDetectorCosmics.h.

◆ m_hitCollectionName

std::string CSCSensitiveDetectorCosmics::m_hitCollectionName
private

member data

Definition at line 88 of file CSCSensitiveDetectorCosmics.h.

◆ m_mom

Amg::Vector3D CSCSensitiveDetectorCosmics::m_mom
private

Definition at line 80 of file CSCSensitiveDetectorCosmics.h.

◆ m_momMag

double CSCSensitiveDetectorCosmics::m_momMag
private

Definition at line 81 of file CSCSensitiveDetectorCosmics.h.

◆ m_muonHelper

const CscHitIdHelper* CSCSensitiveDetectorCosmics::m_muonHelper
private

Definition at line 91 of file CSCSensitiveDetectorCosmics.h.

◆ m_myCSCHitColl

CSCSimHitCollection* CSCSensitiveDetectorCosmics::m_myCSCHitColl {nullptr}
private

Definition at line 89 of file CSCSensitiveDetectorCosmics.h.

89{nullptr};

◆ m_vertex

Amg::Vector3D CSCSensitiveDetectorCosmics::m_vertex
private

Definition at line 82 of file CSCSensitiveDetectorCosmics.h.


The documentation for this class was generated from the following files: