#include "AliMUONTracker.h"
#include "AliCodeTimer.h"
#include "AliESDEvent.h"
#include "AliESDMuonTrack.h"
#include "AliESDVertex.h"
#include "AliLog.h"
#include "AliMUONClusterStoreV2.h"
#include "AliMUONESDInterface.h"
#include "AliMUONLegacyClusterServer.h"
#include "AliMUONRecoParam.h"
#include "AliMUONReconstructor.h"
#include "AliMUONTrack.h"
#include "AliMUONTrackExtrap.h"
#include "AliMUONTrackHitPattern.h"
#include "AliMUONTrackParam.h"
#include "AliMUONTrackReconstructor.h"
#include "AliMUONTrackReconstructorK.h"
#include "AliMUONTrackStoreV1.h"
#include "AliMUONTriggerTrackStoreV1.h"
#include "AliMUONTriggerTrack.h"
#include "AliMUONLocalTrigger.h"
#include "AliMUONVClusterServer.h"
#include "AliMUONVDigitStore.h"
#include "AliMUONVTriggerStore.h"
#include "AliMUONTriggerUtilities.h"
#include <Riostream.h>
#include <TRandom.h>
#include <TTree.h>
#include "AliLog.h"
ClassImp(AliMUONTracker)
AliMUONTracker::AliMUONTracker(const AliMUONRecoParam* recoParam,
AliMUONVClusterServer* clusterServer,
AliMUONVDigitStore& digitStore,
const AliMUONGeometryTransformer* transformer,
const AliMUONTriggerCircuit* triggerCircuit,
const AliMUONTriggerUtilities* triggerUtilities)
: AliTracker(),
fkTransformer(transformer),
fkTriggerCircuit(triggerCircuit),
fTrackHitPatternMaker(0x0),
fTrackReco(0x0),
fClusterStore(0x0),
fTriggerStore(0x0),
fClusterServer(clusterServer),
fIsOwnerOfClusterServer(kFALSE),
fkDigitStore(digitStore),
fInputClusterStore(0x0),
fTriggerTrackStore(0x0),
fkRecoParam(recoParam),
fInternalTrackStore(0x0)
{
if (fkTransformer)
fTrackHitPatternMaker = new AliMUONTrackHitPattern(recoParam,*fkTransformer,fkDigitStore,triggerUtilities);
if (!fClusterServer)
{
AliDebug(1,"No cluster server given. Will use AliMUONLegacyClusterServer");
fIsOwnerOfClusterServer = kTRUE;
}
else
{
TIter next(fkDigitStore.CreateIterator());
fClusterServer->UseDigits(next,&digitStore);
SetupClusterServer(*fClusterServer);
}
}
AliMUONTracker::~AliMUONTracker()
{
delete fTrackReco;
delete fTrackHitPatternMaker;
delete fClusterStore;
delete fTriggerStore;
if ( fIsOwnerOfClusterServer ) delete fClusterServer;
delete fInputClusterStore;
delete fTriggerTrackStore;
delete fInternalTrackStore;
}
AliMUONVClusterStore*
AliMUONTracker::ClusterStore() const
{
if (!fClusterStore)
{
fClusterStore = new AliMUONClusterStoreV2;
}
return fClusterStore;
}
AliMUONVTriggerTrackStore*
AliMUONTracker::TriggerTrackStore() const
{
if (!fTriggerTrackStore)
{
fTriggerTrackStore = new AliMUONTriggerTrackStoreV1;
}
return fTriggerTrackStore;
}
Int_t AliMUONTracker::LoadClusters(TTree* clustersTree)
{
if ( ! clustersTree ) {
AliFatal("No clustersTree");
return 1;
}
if ( !fTriggerStore )
{
fTriggerStore = AliMUONVTriggerStore::Create(*clustersTree);
}
if (!fTriggerStore)
{
AliError("Could not get triggerStore");
return 2;
}
if (!fInputClusterStore)
{
fInputClusterStore = AliMUONVClusterStore::Create(*clustersTree);
if (!fInputClusterStore)
{
AliError("Could not get clusterStore");
return 3;
}
AliDebug(1,Form("Created %s from cluster tree",fInputClusterStore->ClassName()));
}
if ( !fClusterServer && fIsOwnerOfClusterServer )
{
if ( !fClusterServer )
{
fClusterServer = new AliMUONLegacyClusterServer(*fkTransformer,fInputClusterStore,
GetRecoParam()->BypassSt4(),
GetRecoParam()->BypassSt5());
SetupClusterServer(*fClusterServer);
}
}
fInputClusterStore->Clear();
fInputClusterStore->Connect(*clustersTree,kFALSE);
fTriggerStore->Clear();
fTriggerStore->Connect(*clustersTree,kFALSE);
clustersTree->GetEvent(0);
return 0;
}
Int_t AliMUONTracker::Clusters2Tracks(AliESDEvent* esd)
{
AliCodeTimerAuto("",0)
if (!fTrackReco)
{
fTrackReco = CreateTrackReconstructor(GetRecoParam(),fClusterServer,fkTransformer);
fInternalTrackStore = new AliMUONTrackStoreV1;
}
if (!fTrackReco) return 1;
if ( ! ClusterStore() )
{
AliError("ClusterStore is NULL");
return 2;
}
if (!fTriggerStore) {
AliError("TriggerStore is NULL");
return 3;
}
if ( fkTriggerCircuit )
{
TriggerTrackStore()->Clear();
fTrackReco->EventReconstructTrigger(*fkTriggerCircuit,*fTriggerStore,*(TriggerTrackStore()));
}
if ( TriggerTrackStore()->GetSize() > GetRecoParam()->GetMaxTriggerTracks() )
{
AliCodeTimerAuto("MUON Shower events",1);
AliWarning(Form("Probably got a shower event (%d trigger tracks). Will not reconstruct tracks.",
TriggerTrackStore()->GetSize()));
return 0;
}
fTrackReco->EventReconstruct(*(ClusterStore()),*fInternalTrackStore);
if ( fTrackHitPatternMaker )
{
fTrackReco->ValidateTracksWithTrigger(*fInternalTrackStore,*(TriggerTrackStore()),*fTriggerStore,*fTrackHitPatternMaker);
}
FillESD(*fInternalTrackStore,esd);
fInternalTrackStore->Clear();
ClusterStore()->Clear();
return 0;
}
void AliMUONTracker::FillESD(const AliMUONVTrackStore& trackStore, AliESDEvent* esd) const
{
AliDebug(1,"");
AliCodeTimerAuto("",0)
Double_t vertex[3] = {0., 0., 0.};
const AliESDVertex* esdVert = esd->GetVertex();
if (esdVert->GetNContributors() > 0 || !strcmp(esdVert->GetTitle(),"vertexer: smearMC")) {
esdVert->GetXYZ(vertex);
AliDebug(1,Form("found vertex (%e,%e,%e)",vertex[0],vertex[1],vertex[2]));
}
AliMUONTrack* track;
AliMUONLocalTrigger* locTrg;
TIter next(trackStore.CreateIterator());
if (GetRecoParam()->SaveFullClusterInESD() &&
gRandom->Uniform(100.) <= GetRecoParam()->GetPercentOfFullClusterInESD()) {
while ( ( track = static_cast<AliMUONTrack*>(next()) ) ) {
if (track->GetMatchTrigger() > 0) {
locTrg = static_cast<AliMUONLocalTrigger*>(fTriggerStore->FindLocal(track->LoCircuit()));
AliMUONESDInterface::MUONToESD(*track, *esd, vertex, &fkDigitStore, locTrg);
} else AliMUONESDInterface::MUONToESD(*track, *esd, vertex, &fkDigitStore);
}
} else {
while ( ( track = static_cast<AliMUONTrack*>(next()) ) ) {
if (track->GetMatchTrigger() > 0) {
locTrg = static_cast<AliMUONLocalTrigger*>(fTriggerStore->FindLocal(track->LoCircuit()));
AliMUONESDInterface::MUONToESD(*track, *esd, vertex, 0x0, locTrg);
} else AliMUONESDInterface::MUONToESD(*track, *esd, vertex);
}
}
UInt_t ghostId = 0xFFFFFFFF - 1;
Bool_t matched = kFALSE;
AliMUONTriggerTrack *triggerTrack;
TIter itTriggerTrack(fTriggerTrackStore->CreateIterator());
while ( ( triggerTrack = static_cast<AliMUONTriggerTrack*>(itTriggerTrack()) ) ) {
locTrg = static_cast<AliMUONLocalTrigger*>(fTriggerStore->FindLocal(triggerTrack->GetLoTrgNum()));
TIter itTrack(trackStore.CreateIterator());
while ( ( track = static_cast<AliMUONTrack*>(itTrack()) ) ) {
matched = (track->LoCircuit() == locTrg->LoCircuit());
if (matched) break;
}
if (matched) continue;
AliMUONESDInterface::MUONToESD(*locTrg, *esd, ghostId, triggerTrack);
ghostId -= 1;
}
}
AliMUONVTrackReconstructor* AliMUONTracker::CreateTrackReconstructor(const AliMUONRecoParam* recoParam,
AliMUONVClusterServer* clusterServer,
const AliMUONGeometryTransformer* transformer)
{
AliMUONVTrackReconstructor* trackReco(0x0);
TString opt(recoParam->GetTrackingMode());
opt.ToUpper();
if (strstr(opt,"ORIGINAL"))
{
trackReco = new AliMUONTrackReconstructor(recoParam,clusterServer,transformer);
}
else if (strstr(opt,"KALMAN"))
{
trackReco = new AliMUONTrackReconstructorK(recoParam,clusterServer,transformer);
}
else
{
AliErrorClass(Form("tracking mode \"%s\" does not exist",opt.Data()));
return 0x0;
}
AliDebugClass(1,Form("Will use %s for tracking",trackReco->ClassName()));
return trackReco;
}
void AliMUONTracker::UnloadClusters()
{
fInputClusterStore->Clear();
}
void
AliMUONTracker::SetupClusterServer(AliMUONVClusterServer& clusterServer)
{
if ( GetRecoParam()->BypassSt4() ||
GetRecoParam()->BypassSt5() )
{
Bool_t ok = clusterServer.UseTriggerTrackStore(TriggerTrackStore());
TString msg1;
TString msg2;
if ( GetRecoParam()->BypassSt45() )
{
msg1 = "STATIONS 4 AND 5";
msg2 = "THOSE TWO STATIONS";
}
else if ( GetRecoParam()->BypassSt4() )
{
msg1 = "STATION 4";
msg2 = "THAT STATION";
}
else if ( GetRecoParam()->BypassSt5() )
{
msg1 = "STATION 5";
msg2 = "THAT STATION";
}
if ( ok )
{
AliWarning(Form("WILL USE TRIGGER TRACKS TO GENERATE CLUSTERS IN %s, "
"THUS BYPASSING REAL CLUSTERS IN %s!!!",msg1.Data(),msg2.Data()));
}
else
{
AliWarning("BYPASSING OF ST4 AND/OR 5 REQUESTED, BUT CLUSTERSERVER DOES NOT SEEM TO SUPPORT IT !!!");
}
}
}