// ExR05RootPersistency.cc // 29-Sep-2000 Bill Seligman // This is an example class for booking histograms of hit information // in GEANT4. #include "ExR05RootPersistency.hh" // Include files for ROOT. #include "Rtypes.h" #include "TROOT.h" #include "TFile.h" #include "TTable.h" #include "TStopwatch.h" #include "ExR05StarHit.h" #include "ExR05StarEvent.h" // Needed to convert numbers to strings #include #include // Include files for the G4 classes #include "globals.hh" #include "G4Run.hh" #include "G4Event.hh" // Classes needed for access and convert hit information. #include "G4RunManager.hh" #include "G4SDManager.hh" #include "G4HCofThisEvent.hh" #include "ExN02TrackerHit.hh" //_____________________________________________________________________________ ExR05RootPersistency::ExR05RootPersistency() { // Since we're not creating the TROOT object in the same scope as we're // creating our histogram objects, we must declare it to be static. // Otherwise, the TROOT object will go away when the constructor is over. // Note: an alternative would be to create rootBase in the main program // (exampleR05.cc). But if we did that, the main program would "know" that // ROOT is being used to make histograms (as opposed to HBOOK, LHC++, etc.). // I'd rather keep that information internal to this class. static TROOT rootBase("simple","Test of ROOT persistent I/O"); m_runWatch = new TStopwatch(); m_eventWatch = new TStopwatch(); // Open a new ROOT file. m_runWatch->Start(kFALSE); m_rootFile = new TFile("exampleR08.root","RECREATE","Demo ROOT file with eventss"); m_runWatch->Stop(); } //_____________________________________________________________________________ ExR05RootPersistency::~ExR05RootPersistency() { // Close the file. Note that this is automatically done when you leave // the application. m_rootFile->Close(); // We created the file with "new", so we have to destroy it with "delete": delete m_rootFile; m_runWatch->Print(); m_eventWatch->Print(); delete m_eventWatch; delete m_runWatch; } //_____________________________________________________________________________ void ExR05RootPersistency::RecordBeginOfRun(const G4Run *) { printf(" ----------- > RecordBeginOfRun <---------" ); m_eventWatch->Print(); m_eventWatch->Start(kFALSE); } //_____________________________________________________________________________ void ExR05RootPersistency::RecordEndOfRun(const G4Run* a_run) { // Save the histogram, then delete it. m_runWatch->Start(kFALSE); m_rootFile->Write(); m_runWatch->Stop(); m_runWatch->Print(); } //_____________________________________________________________________________ void ExR05RootPersistency::RecordEndOfEvent(const G4Event* a_event) { // Convert a G4 event into a ROOT-compatible event. m_runWatch->Start(kFALSE); RecordEvent(a_event); m_runWatch->Stop(); m_runWatch->Print(); } //_____________________________________________________________________________ void ExR05RootPersistency::RecordEvent(const G4Event* a_event) { // Here's the meat inside the wrapper: How to convert a G4Event into // our sample root event. G4RunManager* rm = G4RunManager::GetRunManager(); //------------- Create event root straucture --------------- TDataSet eventSet = TDataSet("LarEvent"); //------------- Create event data container --------------- ExR05StarEvent *eventData = new ExR05StarEvent("event",1); event_t event; event.runNumber = rm->GetCurrentRun()->GetRunID(); event.eventNumber = a_event->GetEventID(); eventData->AddAt(&event); eventSet.Add(eventData); // Add run /even description to the current set // Access the Hit Collection of this event // (from section 3.12.4.2 of the Geant4 Users' Guide). // First, get the pointer to the singleton Sensitive Detector Manager. G4SDManager* fSDM = G4SDManager::GetSDMpointer(); // Get the collection ID number for the particular type of hit // we're interested in. "trackerCollection" was defined to be the // name of a hit collection in ExN02TrackerSD.cc. If there were // many types of hits (e.g., calorimeter hits, chamber hits, etc.) // then the following code could be repeated as needed for each // type. G4int collectionID = fSDM->GetCollectionID("trackerCollection"); // Get the pointer to the hit collections of this event. G4HCofThisEvent* HCofEvent = a_event->GetHCofThisEvent(); // Get the hit collection that corresponds to the particular collection ID number. // Note the type cast that converts the "G4VHitsCollection*" returned by GetHC // into a pointer to our custom type of hit collection. ExN02TrackerHitsCollection* trackerHC = (ExN02TrackerHitsCollection*) (HCofEvent->GetHC(collectionID)); // For this example, we want to loop through all the tracker hits. // Get the number of hits in this hit collection. G4int numberHits = trackerHC->entries(); //------------- Create hit container --------------- if (numberHits) { ExR05StarHit *hitData = new ExR05StarHit("hits",numberHits); eventSet.Add(hitData); hit_t *starHit = hitData->GetTable(); for (G4int i = 0; i < numberHits; i++,starHit++) { // Get the "i-th" hit in the collection. ExN02TrackerHit* hit = (*trackerHC)[i]; starHit->energy = hit->GetEdep() / GeV; G4ThreeVector position = hit->GetPos(); starHit->xyz[0] = position.x() / cm ; starHit->xyz[1] = position.y() / cm ; starHit->xyz[2] = position.z() / cm ; } hitData->SetNRows(numberHits); } eventSet.Write(); }