#include "hgeantmergesource.h"
#include "hades.h"
#include "hrecevent.h"
#include "heventheader.h"
#include "hgeantheader.h"
#include "hpartialevent.h"
#include "hcategory.h"
#include "hlinearcategory.h"
#include "hmatrixcategory.h"
#include "hgeantmaxtrk.h"
#include "hgeantdef.h"
#include <iostream>
#include <iomanip>
#include <limits.h>
#include <unistd.h>
#include "TKey.h"
using namespace std;
ClassImp(HGeantMergeSource)
HGeantMergeSource::HGeantMergeSource(Bool_t fPers, Bool_t fMerg)
{
fInput = 0;
fEventInFile = 0;
fCursor = 0;
fCurrentRunId = INT_MIN;
fCurrentRefId = -1;
fGlobalRefId = -1;
fDirectory = "./";
fPersistency = fPers;
fMerge = fMerg;
fEventList = 0;
fLastRunId = -1;
overwriteVersion = kFALSE;
replaceVersion = 0;
}
HGeantMergeSource::~HGeantMergeSource(void)
{
Clear();
}
Bool_t HGeantMergeSource::createGeantEvent(HRecEvent* fCurrentEvent){
HPartialEvent* geantEvt = fCurrentEvent->getPartialEvent(catSimul);
if(!geantEvt){
fCurrentEvent->addPartialEvent(catSimul,"Simul","Simulated event");
HPartialEvent* pKine = fCurrentEvent->getPartialEvent(catSimul);
pKine->setSubHeader(new HGeantHeader);
pKine->addCategory(catGeantKine,new HLinearCategory("HGeantKine",MAXTRKKINE) );
Int_t iniMdc[4]={6,4,7,MAXTRKMDC};
pKine->addCategory(catMdcGeantRaw,new HMatrixCategory("HGeantMdc",4,iniMdc,0.1) );
Int_t iniRich[2]={6,MAXCKOVRICH};
pKine->addCategory(catRichGeantRaw,new HMatrixCategory("HGeantRichPhoton",2,iniRich,0.1) );
Int_t ini1Rich[2]={6,MAXPARTRICH};
pKine->addCategory(catRichGeantRaw+1,new HMatrixCategory("HGeantRichDirect",2,ini1Rich,0.1) );
Int_t ini2Rich[2]={6,MAXMIRRRICH};
pKine->addCategory(catRichGeantRaw+2,new HMatrixCategory("HGeantRichMirror",2,ini2Rich,0.1) );
Int_t iniRpc[2]={6,MAXTRKRPC};
pKine->addCategory(catRpcGeantRaw,new HMatrixCategory("HGeantRpc",2,iniRpc,0.5) );
Int_t iniTof[2]={6,MAXTRKTOF};
pKine->addCategory(catTofGeantRaw,new HMatrixCategory("HGeantTof",2,iniTof,0.1) );
Int_t iniShower[2]={6,MAXTRKSHOW};
pKine->addCategory(catShowerGeantRaw,new HMatrixCategory("HGeantShower",2,iniShower,0.1) );
pKine->addCategory(catWallGeantRaw,new HLinearCategory("HGeantWall",MAXTRKWALL) );
Int_t iniStart=MAXTRKSTART*0.1;
pKine->addCategory(catStartGeantRaw,new HLinearCategory("HGeantStart",iniStart) );
Int_t iniEmc[2]={6,MAXTRKEMC};
pKine->addCategory(catEmcGeantRaw,new HMatrixCategory("HGeantEmc",2,iniEmc,0.1) );
return kTRUE;
}
return kFALSE;
}
Bool_t HGeantMergeSource::init(void)
{
Bool_t r = kTRUE;
if (fEventInFile != 0)
{
HRecEvent* fCurrentEvent = (HRecEvent*)gHades->getCurrentEvent();
if (fCurrentEvent != 0) {
if (fMerge) {
Warning("init","Merging with predefined event structure");
((HRecEvent*)fEventInFile)->merge(fCurrentEvent);
} else {
Warning("init","Using predefined event structure");
}
} else {
gHades->setEvent(fEventInFile);
}
if ( fInput!=0)
{
Char_t sl=*(strchr(fInput->GetTitle(),'.')+1);
switch (sl) {
case '0' : fSplitLevel = 0;
break;
case '1' : fSplitLevel = 1;
break;
case '2' : fSplitLevel = 2;
break;
default : fSplitLevel = 0;
}
fInput->SetBranchStatus("*",kFALSE);
gHades->activateTree(fInput);
if (fEventList) {
fEntries = fEventList->GetN();
} else {
fEntries=fInput->GetEntries();
}
if (fCursor >= fEntries) {
Error("init","Entry not existing %i",fCursor);
return kFALSE;
}
if (fEventList) {
fInput->GetEvent(fEventList->GetEntry(fCursor));
} else {
fInput->GetEvent(fCursor);
}
fCurrentRunId = gHades->getCurrentEvent()->getHeader()->getEventRunNumber();
fLastRunId = fCurrentRunId;
if(overwriteVersion)
{
gHades->getCurrentEvent()->getHeader()->setVersion(replaceVersion);
}
if (fRefIds.find(fCurrentRunId) != fRefIds.end()) {
fCurrentRefId = fRefIds[fCurrentRunId];
} else {
fCurrentRefId = fGlobalRefId;
}
if (fPersistency == kFALSE) {
for(Int_t i = 0; i < 16; i ++) {
HPartialEvent* fPar = ((HRecEvent*)fEventInFile)->getPartialEvent(i<<kBitCategorySize);
if (fPar) { fPar->setPersistency(kFALSE); }
}
}
setCursorToPreviousEvent();
r = kTRUE;
} else {
Warning("init","Not input");
Clear();
r = kFALSE;
}
} else {
r = kFALSE;
}
return r;
}
EDsState HGeantMergeSource::getNextEvent(Bool_t doUnpack)
{
Int_t bread = 0;
if (fInput)
{
if (fSplitLevel < 2) (*fEventAddr)->clearAll(fSplitLevel);
if (fCursor < fEntries)
{
Int_t entry = fCursor;
if (fEventList) {
entry = fEventList->GetEntry(fCursor) ;
bread = fInput->GetEvent(entry);
} else {
bread = fInput->GetEvent(fCursor);
}
if(bread > 0)
{
Bool_t status = kTRUE;
for(UInt_t i=0;i<fAdditionalInputs.size();i++){
HParallelEvent* evt = fAdditionalInputs[i];
if(evt->getEntry(entry) < 0 ) {
status = kFALSE;
break;
}
evt->mergeGeantEvent((HRecEvent*)gHades->getCurrentEvent());
}
if(status == kFALSE) bread = 0;
}
if (bread == 0) { return kDsEndData; }
fCursor ++;
fCurrentRunId = gHades->getCurrentEvent()->getHeader()->getEventRunNumber();
if(overwriteVersion)
{
gHades->getCurrentEvent()->getHeader()->setVersion(replaceVersion);
}
if (fCurrentRunId != fLastRunId)
{
if (fRefIds.find(fCurrentRunId) != fRefIds.end()) {
fCurrentRefId = fRefIds[fCurrentRunId];
} else {
fCurrentRefId = fGlobalRefId;
}
fLastRunId = fCurrentRunId;
return kDsEndFile;
}
} else { return kDsEndData; }
} else { return kDsError; }
return kDsOk;
}
Bool_t HGeantMergeSource::getEvent(Int_t eventN) {
if (fInput) {
Bool_t status = kFALSE;
Int_t entry = eventN ;
if (fEventList) {
entry = fEventList->GetEntry(eventN) ;
}
if(fInput->GetEvent(entry) > 0)
{
status = kTRUE;
for(UInt_t i=0;i<fAdditionalInputs.size();i++){
HParallelEvent* evt = fAdditionalInputs[i];
if(evt->getEntry(entry) < 0 ) {
status = kFALSE;
break;
}
evt->mergeGeantEvent((HRecEvent*)gHades->getCurrentEvent());
}
}
return status;
}
return kFALSE;
}
void HGeantMergeSource::Clear(void)
{
if (fInput) {
delete fInput;
fInput = 0;
for(UInt_t i=0;i<fAdditionalInputs.size();i++){
HParallelEvent* evt = fAdditionalInputs[i];
evt->closeInputFile();
delete evt;
}
}
}
Bool_t HGeantMergeSource::addFile(const Text_t *file,Bool_t print)
{
Text_t treeName[] = "T";
TString fname = getFileName(file);
if (fileExists(fname))
{
if (!fInput)
{
TFile *fileTemp;
TKey *key = 0;
TString title;
if(print)Info("addFile()","Add file %s",fname.Data());
fileTemp = getFile(fname.Data());
key = fileTemp->GetKey(treeName);
fEventInFile = (HEvent *)fileTemp->Get("Event");
fCurrentRunId = fEventInFile->getHeader()->getEventRunNumber();
if (fRefIds.find(fCurrentRunId) != fRefIds.end()) {
fCurrentRefId = fRefIds[fCurrentRunId];
} else {
fCurrentRefId = fGlobalRefId;
}
title = key->GetTitle();
fileTemp->Close();
delete fileTemp;
fInput = new TChain(treeName,title.Data());
}
fInput->Add(fname.Data());
} else {
Warning("addFile","File %s not found",fname.Data());
return kFALSE;
}
return kTRUE;
}
Bool_t HGeantMergeSource::addMultFiles(TString commaSeparatedList)
{
commaSeparatedList.ReplaceAll(" ","");
if(commaSeparatedList==""){
Error("addMultFiles()","No input file specified!");
return kFALSE;
}
TObjArray* ar = commaSeparatedList.Tokenize(",");
if(ar){
Bool_t ok = kFALSE;
TString infile;
if(ar->GetEntries()>0) {
infile = ((TObjString*)ar->At(0))->GetString();
Info("addMultFiles()","Add file %s",infile.Data());
ok = addFile((const Text_t*) infile.Data(),kFALSE);
}
if(ok){
for(Int_t i = 1; i < ar->GetEntries();i++){
infile = ((TObjString*)ar->At(i))->GetString();
Info("addMultFiles()","Add file %s",infile.Data());
ok = addAdditionalInput(infile,kFALSE);
if(!ok) break;
}
}
delete ar;
return ok;
}
return kFALSE;
}
Bool_t HGeantMergeSource::addAdditionalInput(TString filename,Bool_t print)
{
HParallelEvent* evt = new HParallelEvent(filename,filename);
Bool_t ok = evt->setInputFile(filename,print);
if(!ok) {
delete evt;
return kFALSE;
}
fAdditionalInputs.push_back(evt);
return kTRUE;
}