// $Id$
+#include <TClonesArray.h>
+#include <TParticle.h>
+#include <TTree.h>
+
#include "AliMUONSDigitizerV2.h"
-#include "AliLog.h"
#include "AliMUON.h"
#include "AliMUONChamber.h"
-#include "AliMUONData.h"
-#include "AliMUONDigit.h"
+#include "AliMUONVDigit.h"
#include "AliMUONHit.h"
+#include "AliMUONVDigitStore.h"
+#include "AliMUONVHitStore.h"
+#include "AliMUONResponseTrigger.h"
+#include "AliMUONConstants.h"
+
+#include "AliMpCDB.h"
+#include "AliMpDEManager.h"
+
+#include "AliLog.h"
+#include "AliCDBManager.h"
#include "AliLoader.h"
#include "AliRun.h"
#include "AliRunLoader.h"
-#include "TObjArray.h"
-///
+#include "AliHeader.h"
+#include "AliGenCocktailEventHeader.h"
+
+//-----------------------------------------------------------------------------
/// The sdigitizer performs the transformation from hits (energy deposits by
/// the transport code) to sdigits (equivalent of charges on pad).
///
/// Please note that we do *not* merge sdigits after creation, which means
/// that after sdigitization, a given pad can have several sdigits. This
/// merging is taken care of later on by the digitizer(V3).
-///
+//-----------------------------------------------------------------------------
ClassImp(AliMUONSDigitizerV2)
+Float_t AliMUONSDigitizerV2::fgkMaxIntTime = 10.0;
+Float_t AliMUONSDigitizerV2::fgkMaxPosTimeDif = 1.22E-6;
+Float_t AliMUONSDigitizerV2::fgkMaxNegTimeDif = -3.5E-6;
+Float_t AliMUONSDigitizerV2::fgkMinTimeDif = 25E-9;
+
//_____________________________________________________________________________
AliMUONSDigitizerV2::AliMUONSDigitizerV2()
-: TTask("AliMUONSDigitizerV2","From Hits to SDigits for MUON")
+: TNamed("AliMUONSDigitizerV2","From Hits to SDigits for MUON")
{
- //
- // ctor.
- //
+ ///
+ /// ctor.
+ ///
+
+ // Load mapping
+ if ( ! AliMpCDB::LoadMpSegmentation() ) {
+ AliFatal("Could not access mapping from OCDB !");
+ }
}
//_____________________________________________________________________________
AliMUONSDigitizerV2::~AliMUONSDigitizerV2()
{
- //
- // dtor.
- //
+ ///
+ /// dtor.
+ ///
}
//_____________________________________________________________________________
void
-AliMUONSDigitizerV2::Exec(Option_t*)
+AliMUONSDigitizerV2::Digitize(Option_t*)
{
- //
- // Go from hits to sdigits.
- //
- // In the code below, apart from the loop itself (which look complicated
- // but is really only a loop on each hit in the input file) the main
- // work is done in AliMUONResponse::DisIntegrate method, which converts
- // a single hit in (possibly) several sdigits.
- //
+ ///
+ /// Go from hits to sdigits.
+ ///
+ /// In the code below, apart from the loop itself (which look complicated
+ /// but is really only a loop on each hit in the input file) the main
+ /// work is done in AliMUONResponse::DisIntegrate method, which converts
+ /// a single hit in (possibly) several sdigits.
+ ///
AliDebug(1,"");
- AliRunLoader* runLoader = AliRunLoader::GetRunLoader();
- AliLoader* fLoader = runLoader->GetLoader("MUONLoader");
-
- fLoader->LoadHits("READ");
+ AliRunLoader* runLoader = AliRunLoader::Instance();
+ AliLoader* loader = runLoader->GetDetectorLoader("MUON");
+
+ loader->LoadHits("READ");
- AliMUONData muonData(fLoader,"MUON","MUON");
-
AliMUON* muon = static_cast<AliMUON*>(gAlice->GetModule("MUON"));
-
+
Int_t nofEvents(runLoader->GetNumberOfEvents());
+
+ TString classname = muon->DigitStoreClassName();
+
+ AliMUONVDigitStore* sDigitStore = AliMUONVDigitStore::Create(classname.Data());
+
+ if (!sDigitStore)
+ {
+ AliFatal(Form("Could not create digitstore of class %s",classname.Data()));
+ }
+
+ AliDebug(1,Form("Will use digitStore of type %s",sDigitStore->ClassName()));
+
+ // average arrival time to chambers, for pileup studies
+
for ( Int_t iEvent = 0; iEvent < nofEvents; ++iEvent )
{
// Loop over events.
AliDebug(1,Form("iEvent=%d",iEvent));
runLoader->GetEvent(iEvent);
- TTree* treeS = fLoader->TreeS();
- AliDebug(1,Form("TreeS=%p",treeS));
+
+ // for pile up studies
+ float t0=fgkMaxIntTime; int aa=0;
+ AliHeader* header = runLoader->GetHeader();
+ AliGenCocktailEventHeader* cocktailHeader =
+ dynamic_cast<AliGenCocktailEventHeader*>(header->GenEventHeader());
+ if (cocktailHeader) {
+ AliGenCocktailEventHeader* genEventHeader = (AliGenCocktailEventHeader*) (header->GenEventHeader());
+ TList* headers = genEventHeader->GetHeaders();
+ TIter nextH(headers);
+ AliGenEventHeader *entry;
+ while((entry = (AliGenEventHeader*)nextH())) {
+ float t = entry->InteractionTime();
+ if (TMath::Abs(t)<TMath::Abs(t0)) t0 = t;
+ aa++;
+ }
+ } else {
+ AliGenEventHeader* evtHeader =
+ (AliGenEventHeader*)(header->GenEventHeader());
+ if (evtHeader)
+ {
+ float t = evtHeader->InteractionTime();
+ if (TMath::Abs(t)<TMath::Abs(t0)) t0 = t;
+ aa++;
+ }
+ else
+ {
+ // some generators may not offer a header, if which
+ // case we cannot get the interaction time, so we assume zero
+ t0 = 0.;
+ }
+ }
+
+ loader->MakeSDigitsContainer();
+
+ TTree* treeS = loader->TreeS();
+
if ( !treeS )
{
- AliDebug(1,"MakeSDigitsContainer");
- fLoader->MakeSDigitsContainer();
- treeS = fLoader->TreeS();
+ AliFatal("");
}
- AliDebug(1,Form("TreeS=%p",treeS));
- muonData.MakeBranch("S");
- muonData.SetTreeAddress("S");
-
- muonData.SetTreeAddress("H");
- TTree* treeH = fLoader->TreeH();
- AliDebug(1,Form("TreeH=%p",treeH));
-
+
+ sDigitStore->Connect(*treeS);
+
+ TTree* treeH = loader->TreeH();
+
+ AliMUONVHitStore* hitStore = AliMUONVHitStore::Create(*treeH);
+ hitStore->Connect(*treeH);
+
Long64_t nofTracks = treeH->GetEntries();
+
for ( Long64_t iTrack = 0; iTrack < nofTracks; ++iTrack )
{
// Loop over the tracks of this event.
treeH->GetEvent(iTrack);
- TClonesArray* hits = muonData.Hits();
- Int_t nofHits = hits->GetEntriesFast();
- for ( Int_t ihit = 0; ihit < nofHits; ++ihit )
+
+ AliMUONHit* hit;
+ TIter next(hitStore->CreateIterator());
+ Int_t ihit(0);
+
+ while ( ( hit = static_cast<AliMUONHit*>(next()) ) )
{
- // Loop over the hits of this track.
- AliMUONHit* hit = static_cast<AliMUONHit*>(hits->At(ihit));
Int_t chamberId = hit->Chamber()-1;
+ Float_t age = hit->Age()-t0;
+
AliMUONChamber& chamber = muon->Chamber(chamberId);
AliMUONResponse* response = chamber.ResponseModel();
// This is the heart of this method : the dis-integration
TList digits;
- response->DisIntegrate(*hit,digits);
+ if (aa>1){ // if there are pileup events
+ Float_t chamberTime = AliMUONConstants::AverageChamberT(chamberId);
+ Float_t timeDif=age-chamberTime;
+ if (timeDif>fgkMaxPosTimeDif || timeDif<fgkMaxNegTimeDif) {
+ continue;
+ }
+ if(TMath::Abs(timeDif)>fgkMinTimeDif){
+ response->DisIntegrate(*hit,digits,timeDif);
+ }
+ else{
+ response->DisIntegrate(*hit,digits,0.);
+ }
+ }
+ else{
+ response->DisIntegrate(*hit,digits,0.);
+ }
- TIter next(&digits);
- AliMUONDigit* d;
- while ( ( d = (AliMUONDigit*)next() ) )
+ TIter nextd(&digits);
+ AliMUONVDigit* d;
+ while ( ( d = (AliMUONVDigit*)nextd() ) )
{
// Update some sdigit information that could not be known
// by the DisIntegrate method
d->SetHit(ihit);
- d->AddTrack(iTrack,d->Signal());
+ d->SetTime(age);
+ d->AddTrack(hit->GetTrack(),d->Charge());
tdlist.Add(d);
}
+ ++ihit;
}
- muonData.ResetHits();
+ hitStore->Clear();
} // end of loop on tracks within an event
- for ( Int_t i = 0; i <= tdlist.GetLast(); ++i )
+ TIter next(&tdlist);
+ AliMUONVDigit* d;
+
+ while ( ( d = static_cast<AliMUONVDigit*>(next()) ) )
{
- AliMUONDigit* d = (AliMUONDigit*)tdlist[i];
- StdoutToAliDebug(1,d->Print(););
- if ( d->Signal() > 0 ) // that check would be better in the disintegrate
- // method, but to compare with old sdigitizer, it has to be there.
+ d->ChargeInFC(kTRUE);
+
+ AliMUONVDigit* added = sDigitStore->Add(*d,AliMUONVDigitStore::kMerge);
+ if (!added)
{
- muonData.AddSDigit(d->DetElemId()/100-1,*d);
+ AliError("Could not add digit to digitStore");
}
}
- muonData.Fill("S");
- fLoader->WriteSDigits("OVERWRITE");
- muonData.ResetSDigits();
- fLoader->UnloadSDigits();
+ treeS->Fill();
+
+ loader->WriteSDigits("OVERWRITE");
+
+ sDigitStore->Clear();
+
+ loader->UnloadSDigits();
+
+ delete hitStore;
+
} // loop on events
- fLoader->UnloadHits();
+ loader->UnloadHits();
+
+ delete sDigitStore;
+
}