48#include "G4RunManager.hh"
49#include "G4SDManager.hh"
50#include "G4HCofThisEvent.hh"
52#include "G4ThreeVector.hh"
53#include "G4UnitsTable.hh"
55#include "Randomize.hh"
69#include "GaudiKernel/IMessageSvc.h"
70#include "GaudiKernel/MsgStream.h"
71#include "GaudiKernel/ISvcLocator.h"
72#include "GaudiKernel/Bootstrap.h"
73#include "GaudiKernel/SmartIF.h"
74#include "GaudiKernel/Property.h"
75#include "GaudiKernel/IJobOptionsSvc.h"
88 collectionName.insert(
"BesCgemHitsCollection");
89 collectionName.insert(
"BesCgemTruthCollection");
92 ISvcLocator* iface = Gaudi::svcLocator();
93 SmartIF<IJobOptionsSvc> jos(iface->service(
"JobOptionsSvc"));
94 const std::vector<const Property*>* ppp = jos->getProperties(
"BesCgemSD");
101 for (std::vector<const Property*>::const_iterator it = ppp->begin();
102 it != ppp->end(); ++it) {
103 if ( (*it)->name() ==
"outputFile") {
104 outputFile = (*it)->toString();
109 Gaudi::svcLocator() -> service(
"MessageSvc",
msgSvc);
110 MsgStream log(
msgSvc,
"BesCgemSD::BesCgemSD():BesSensitiveDetector()");
113 if (m_F_outputTruth == 1)
115 log<< MSG::INFO <<
"CgemSim::BesCgemSD::Initialize(), McTruth Hit will be output to a txt file!"
117 <<
"outputFile Path: " << outputFile << endreq;
119 m_outputTruth.open(outputFile.c_str(), ios::out);
121 if (!m_outputTruth.good())
123 log<< MSG::ERROR <<
"CgemSim::BesCgemSD::Initialize(), Fail to open McTruth output file: "
124 << outputFile << endreq;
133 m_outputTruth.close();
166 static G4int HLID=-1;
169 HLID = G4SDManager::GetSDMpointer()->GetCollectionID(collectionName[1]);
172 G4HCofThisEvent *HCE = f_event->GetHCofThisEvent();
175 Gaudi::svcLocator() -> service(
"MessageSvc",
msgSvc);
176 MsgStream log(
msgSvc,
"BesCgemSD::EndOfTruthEvent()");
180 HCE->AddHitsCollection(HLID, m_collection_truth);
183 if (m_F_printTruth==1 or m_F_outputTruth==1)
186 if (m_F_printTruth == 1)
188 log<< MSG::INFO <<
"-------------------------------------------------------------------------------"
190 log<< MSG::INFO <<
"CgemSim::BesCgemSD::EndOfTruthEvent(), McTruth information: " << endreq;
191 log<< MSG::INFO << left <<
"Track " << left <<
"Layer " << left <<
"PDG "
192 << left << setw(12) <<
"R_Pre "
193 << left << setw(12) <<
"R_Post "
194 << left << setw(40) <<
"pos_Pre "
195 << left << setw(40) <<
"pos_Post "
196 << left << setw(12) <<
"P_Pre "
197 << left << setw(12) <<
"P_Post "
198 << left << setw(16) <<
"StepL "
199 << left << setw(16) <<
"Time "
205 for (G4int ii=0; ii<m_collection_truth->entries(); ii++)
207 BesCgemHit *lv_truth = (*m_collection_truth)[ii];
210 if (m_F_printTruth == 1)
212 G4cout << left << setw( 6) << lv_truth-> GetTrackID ()
213 << left << setw( 6) << lv_truth-> GetLayerID ()
214 << left << setw( 6) << lv_truth-> GetPDGCode ()
215 << left << setw(12) << lv_truth-> GetPositionOfPrePoint ().rho()
216 << left << setw(12) << lv_truth-> GetPositionOfPostPoint ().rho()
217 << left << lv_truth-> GetPositionOfPrePoint()
218 << left << lv_truth-> GetPositionOfPostPoint()
219 << left << setw(12) << lv_truth-> GetMomentumOfPrePoint().mag()
220 << left << setw(12) << lv_truth-> GetMomentumOfPostPoint().mag()
221 << left << setw(16) << lv_truth-> GetStepLength ()
222 << left << setw(16) << lv_truth-> GetGlobalTime ()
223 << left << setw(16) << lv_truth-> GetTotalEnergyDeposit ()
228 if (m_F_outputTruth == 1)
230 m_outputTruth << left << setw( 5) << lv_truth->
GetTrackID()
259 bool printFlag=
false;
262 Gaudi::svcLocator() -> service(
"MessageSvc",
msgSvc);
263 MsgStream log(
msgSvc,
"BesCgemSD::ProcessHits()");
266 G4Track *lv_track = f_step->GetTrack();
270 G4double charge = lv_track->GetDefinition()->GetPDGCharge();
274 log<< MSG::WARNING <<
"CgemSim::BesCgemSD::ProcessHits(), Track is neutral, skip the track" << endreq;
277 G4int lvi_pdg_code = lv_track->GetDefinition()->GetPDGEncoding();
280 G4double lvd_global_time = lv_track->GetGlobalTime();
281 if (isnan(lvd_global_time))
284 log<< MSG::WARNING <<
"CgemSim::BesCgemSD::ProcessHits(), Gloabal time is nan" << endreq;
288 if (lvd_global_time > 2000)
291 log<< MSG::WARNING <<
"CgemSim::BesCgemSD::ProcessHits(), Time window is >2000" << endreq;
304 G4double lvd_L_step = f_step->GetStepLength();
305 if (lvd_L_step == 0.)
308 log<< MSG::WARNING <<
"CgemSim::BesCgemSD::ProcessHits(), Step length is 0, skip track" << endreq;
313 G4StepPoint *lv_step_pre = f_step->GetPreStepPoint();
314 G4StepPoint *lv_step_post = f_step->GetPostStepPoint();
315 G4TrackStatus currentTrackStatus = lv_track->GetTrackStatus();
318 G4int lvi_RdtElectron = 0;
319 G4String process_name=
"Generator";
320 if (NULL != lv_track->GetCreatorProcess()){
321 process_name = lv_track->GetCreatorProcess()->GetProcessName();
322 if (process_name ==
"hIoni" || process_name ==
"ionIoni" || process_name ==
"conv" || process_name ==
"compt" || process_name ==
"muIoni" || process_name ==
"eIoni" || process_name ==
"phot" || process_name ==
"muMinusCaptureAtRest" ) lvi_RdtElectron = 1;
329 if(lvi_RdtElectron)
return false;
347 G4int primTrackIdx = 0;
349 G4int primG4TrackId = 0;
356 G4TrackId = lv_track->GetTrackID();
361 G4int lvi_ID_layer = 0;
363 G4int lvi_ID_parent = lv_track->GetParentID();
364 G4double lvd_E_deposit = f_step->GetTotalEnergyDeposit();
366 G4ThreeVector lv3_XYZ_pre = lv_step_pre ->GetPosition();
367 G4ThreeVector lv3_XYZ_post = lv_step_post->GetPosition();
369 G4ThreeVector lv3_P_pre = lv_step_pre ->GetMomentum();
370 G4ThreeVector lv3_P_post = lv_step_post->GetMomentum();
373 log<< MSG::INFO <<
"..............................................................................." << endreq;
374 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Process a hit at track="
375 << primTrackIdx << endreq;
383 G4StepStatus lv_status_pre = lv_step_pre ->GetStepStatus();
384 G4StepStatus lv_status_post = lv_step_post->GetStepStatus();
387 const G4VTouchable *lv_TOUCHABLE = lv_step_pre ->GetTouchable();
389 G4String lvs_volume_name = lv_TOUCHABLE ->GetVolume(0)->GetLogicalVolume()->GetName();
396 if (lvs_volume_name ==
"Gap_D_logic0" or lvs_volume_name ==
"Gap_D_logic1" or lvs_volume_name ==
"Gap_D_logic2")
398 G4double trkLen = lv_track->GetTrackLength();
400 lvi_ID_layer = lv_TOUCHABLE->GetVolume(1)->GetCopyNo();
404 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Track enters the SD volume: "
405 << lvs_volume_name << endreq;
412 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Create a hit at layer="
413 << lvi_ID_layer <<
" track=" << primTrackIdx << endreq;
419 l_new_hit->
SetRdtEl ( lvi_RdtElectron );
423 G4int isSecondary = (G4TrackId==primG4TrackId)? 0:1;
434 double x_pre_glo = lv3_XYZ_pre.x();
435 double y_pre_glo = lv3_XYZ_pre.y();
436 double z_pre_glo = lv3_XYZ_pre.z();
437 double x_post_glo = lv3_XYZ_post.x();
438 double y_post_glo = lv3_XYZ_post.y();
439 double z_post_glo = lv3_XYZ_post.z();
440 double r_pre = sqrt(x_pre_glo*x_pre_glo+y_pre_glo*y_pre_glo);
441 double r_post = sqrt(x_post_glo*x_post_glo+y_post_glo*y_post_glo);
444 HepPoint3D pos_pre(x_pre_glo, y_pre_glo, z_pre_glo);
445 HepPoint3D pos_post(x_post_glo, y_post_glo, z_post_glo);
454 double distLineGlo = fabs(line_glo.
dr());
455 if(fabs(distLineGlo) > rDrift_inn){
456 crossPoint_pre = line_loc.
xAtR(r_post, -1);
457 crossPoint_post = line_loc.
xAtR(r_post, 1);
458 }
else if(r_pre < r_post){
459 crossPoint_pre = line_loc.
xAtR(r_pre, 1);
460 crossPoint_post = line_loc.
xAtR(r_post, 1);
462 crossPoint_pre = line_loc.
xAtR(r_pre, -1);
463 crossPoint_post = line_loc.
xAtR(r_post, -1);
466 G4ThreeVector lv3_XYZ_pre_align(crossPoint_pre.x(), crossPoint_pre.y(), crossPoint_pre.z());
467 G4ThreeVector lv3_XYZ_post_align(crossPoint_post.x(), crossPoint_post.y(), crossPoint_post.z());
481 m_collection_hit->insert(l_new_hit);
484 hit_ID_vector.push_back(lvi_ID_hit);
497 KeyType lv_key(primTrackIdx, lvi_ID_layer);
499 if (m_collection_truth)
504 m_map_truth_it = m_map_truth.find(lv_key);
505 if (m_map_truth_it == m_map_truth.end())
507 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Create a Truth at layer="
508 << lvi_ID_layer <<
" track=" << primTrackIdx << endreq;
529 for(
int ii =0; ii < hit_ID_vector.size();ii++){
530 tmp[ii] = hit_ID_vector[ii];
533 hit_ID_vector.clear();
537 m_collection_truth->insert(l_new_truth);
539 m_map_truth[lv_key] = m_collection_truth->entries() - 1;
541 if (lv_step_pre->GetStepStatus() == fGeomBoundary)
543 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Truth starts from boundry!!!"
548 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Truth doesn't start from boundry!!!"
555 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Add a step to Truth at layer="
556 << lvi_ID_layer <<
" track=" << primTrackIdx << endreq;
558 G4int lvi_ID_truth = (*m_map_truth_it).second;
559 G4int primTrackIdx_pre = (*m_collection_truth)[lvi_ID_truth]->GetTrackID();
560 G4double lvd_E_pre = (*m_collection_truth)[lvi_ID_truth]->GetTotalEnergyDeposit();
561 G4double lvd_L_step_pre = (*m_collection_truth)[lvi_ID_truth]->GetStepLength();
563 (*m_collection_truth)[lvi_ID_truth]->SetTotalEnergyDeposit(lvd_E_deposit + lvd_E_pre);
564 (*m_collection_truth)[lvi_ID_truth]->SetStepLength(lvd_L_step + lvd_L_step_pre);
565 (*m_collection_truth)[lvi_ID_truth]->SetPositionOfPostPoint(lv3_XYZ_post);
566 (*m_collection_truth)[lvi_ID_truth]->SetPositionOfPostPointAlign(lv3_XYZ_post_align);
567 (*m_collection_truth)[lvi_ID_truth]->SetMomentumOfPostPoint(lv3_P_post);
573 if (lv_step_post->GetStepStatus() == fGeomBoundary)
575 log<< MSG::INFO <<
"CgemSim::BesCgemSD::ProcessHits(), Finish a Truth at layer="
576 << lvi_ID_layer <<
" track=" << primTrackIdx << endreq;
581 if(myCgemTruth==NULL)
585 cout<<
"creat a new myCgemTruth, prePos is Boundary: "<<(lv_status_pre==fGeomBoundary)<<
" trkID="<<primTrackIdx<<
", LayerID="<<lvi_ID_layer<<endl;
601 myCgemTruth->
SetRdtEl ( lvi_RdtElectron );
623 cout<<
"update myCgemTruth: prePos is Boundary: "<<(lv_status_pre==fGeomBoundary)<<
", postPos is Boundary:"<<(lv_status_post==fGeomBoundary)<<
", trkID="<<primTrackIdx<<
", LayerID="<<lvi_ID_layer<<endl;
625 if( myCgemTruth && (currentTrackStatus==fStopAndKill || lv_status_post==fGeomBoundary) )
629 for(
int ii =0; ii < hit_ID_vector.size();ii++){
630 tmp[ii] = hit_ID_vector[ii];
636 m_collection_truth->insert(myCgemTruth);
640 hit_ID_vector.clear();
644 cout<<
"save a myCgemTruth: prePos is Boundary: "<<(lv_status_pre==fGeomBoundary)<<
", postPos is Boundary:"<<(lv_status_post==fGeomBoundary)<<
", trkID="<<primTrackIdx<<
", LayerID="<<lvi_ID_layer<<endl;
658 Gaudi::svcLocator() -> service(
"MessageSvc",
msgSvc);
659 MsgStream log(
msgSvc,
"BesCgemSD::EndOfEvent()");
661 bool printFlag=
false;
668 static G4int HCID = -1;
671 HCID = G4SDManager::GetSDMpointer()->GetCollectionID(collectionName[0]);
677 log<< MSG::INFO <<
"-------------------------------------------------------------------------------" << endreq;
678 log<< MSG::INFO <<
"CgemSim::BesCgemSD::EndOfEvent(), Entries of hits collection is "
679 << m_collection_hit->entries() << endreq;
682 HCE->AddHitsCollection(HCID, m_collection_hit);
684 if (verboseLevel > 0)
686 m_collection_hit->PrintAllHits();
G4THitsCollection< BesCgemHit > BesCgemHitsCollection
void SetTotalEnergyDeposit(G4double f_E_deposit)
void SetIsSecondary(G4int isSec)
void SetGlobalTime(G4double f_global_time)
G4ThreeVector GetPositionOfPrePoint() const
void AddIdentifier(G4int f_ID_Identifier[2000], G4int N_dim)
G4ThreeVector GetMomentumOfPostPoint() const
void SetMomentumOfPostPoint(G4ThreeVector f_P_post)
void SetHitID(G4int f_ID_hit)
void SetPDGCode(G4int f_pdg_code)
G4double GetStepLength() const
void SetLayerID(G4int f_ID_layer)
void SetRdtEl(G4int f_RdtElectron)
void SetParentID(G4int f_ID_parent)
void SetFlightLengthPostPoint(G4double len)
void SetTrackID(G4int f_ID_track)
G4ThreeVector GetPositionOfPostPoint() const
void SetPositionOfPrePoint(G4ThreeVector f_XYZ_pre)
G4double GetTotalEnergyDeposit() const
void SetMomentumOfPrePoint(G4ThreeVector f_P_pre)
G4ThreeVector GetMomentumOfPrePoint() const
void SetCreatorProcess(G4String proName)
void SetPositionOfPostPointAlign(G4ThreeVector f_XYZ_post)
void SetPositionOfPrePointAlign(G4ThreeVector f_XYZ_pre)
void SetPositionOfPostPoint(G4ThreeVector f_XYZ_post)
void SetStepLength(G4double f_L_step)
void EndOfTruthEvent(const G4Event *)
void EndOfEvent(G4HCofThisEvent *)
G4bool ProcessHits(G4Step *, G4TouchableHistory *)
void BeginOfTruthEvent(const G4Event *)
void Initialize(G4HCofThisEvent *)
void GetCurrentTrackIndex(G4int &trackIndex, G4int &g4TrackId) const
StraightLine StraightLineConversion(int layer_vir, StraightLine lineOriginal)
double getOuterROfGapD() const
double getInnerROfGapD() const
CgemGeoLayer * getCgemLayer(int i) const
CgemGeoAlign * getAlignPtr() const
HepPoint3D xAtR(double R, int direction=1) const
double dr(void) const
returns an element of parameters.