// These files are not in the same directory, so there's no reason to
// ask the preprocessor to search in the current directory for these
// files by including them with `#include "..."'
-#include <cmath> // __CMATH__
+#include <TBrowser.h> // ROOT_TBrowser
#include <TClonesArray.h> // ROOT_TClonesArray
-#include <TGeometry.h> // ROOT_TGeomtry
-#include <TNode.h> // ROOT_TNode
-#include <TXTRU.h> // ROOT_TXTRU
+#include <TGeoGlobalMagField.h> // ROOT_TGeoGlobalMagField
+#include <TGeoManager.h> // ROOT_TGeoManager
#include <TRotMatrix.h> // ROOT_TRotMatrix
-#include <TTUBE.h> // ROOT_TTUBE
#include <TTree.h> // ROOT_TTree
-#include <TBrowser.h> // ROOT_TBrowser
-#include <TVirtualMC.h> // ROOT_TVirtualMC
#include <TVector2.h> // ROOT_TVector2
-#include <TGeoManager.h> // ROOT_TGeoManager
+#include <TVirtualMC.h> // ROOT_TVirtualMC
+#include <cmath> // __CMATH__
-#include <AliRunDigitizer.h> // ALIRUNDIGITIZER_H
+#include <AliDigitizationInput.h> // ALIRUNDIGITIZER_H
#include <AliLoader.h> // ALILOADER_H
#include <AliRun.h> // ALIRUN_H
#include <AliMC.h> // ALIMC_H
//#endif
// #include "AliFMDGeometryBuilder.h"
#include "AliFMDRawWriter.h" // ALIFMDRAWWRITER_H
-#include "AliFMDPoints.h" // ALIFMDPOINTS_H
+#include "AliFMDRawReader.h" // ALIFMDRAWREADER_H
+#include "AliTrackReference.h"
+#include "AliFMDStripIndex.h"
+#include "AliFMDParameters.h"
+#include "AliFMDReconstructor.h"
//____________________________________________________________________
ClassImp(AliFMD)
fHits = 0;
fDigits = 0;
fIshunt = 0;
- fBad = new TClonesArray("AliFMDHit");
+ // fBad = new TClonesArray("AliFMDHit");
}
//____________________________________________________________________
// Standard constructor for Forward Multiplicity Detector
//
AliFMDDebug(10, ("\tStandard CTOR"));
- fBad = new TClonesArray("AliFMDHit");
+ // fBad = new TClonesArray("AliFMDHit");
// Initialise Hit array
- HitsArray();
- gAlice->GetMCApp()->AddHitList(fHits);
+ // HitsArray();
+ // gAlice->GetMCApp()->AddHitList(fHits);
// (S)Digits for the detectors disk
- DigitsArray();
- SDigitsArray();
+ // DigitsArray();
+ // SDigitsArray();
// CHC: What is this?
fIshunt = 0;
Double_t density = 0;
Double_t radiationLength = 0;
Double_t absorbtionLength = 999;
- Int_t fieldType = gAlice->Field()->Integ(); // Field type
- Double_t maxField = gAlice->Field()->Max(); // Field max.
+ Int_t fieldType = ((AliMagF*)TGeoGlobalMagField::Instance()->GetField())->Integ(); // Field type
+ Double_t maxField = ((AliMagF*)TGeoGlobalMagField::Instance()->GetField())->Max(); // Field max.
Double_t maxBending = 0; // Max Angle
Double_t maxStepSize = 0.001; // Max step size
Double_t maxEnergyLoss = 1; // Max Delta E
}
+#if 0
+//____________________________________________________________________
+void
+AliFMD::SetTrackingParameters(Int_t imed,
+ Float_t gamma,
+ Float_t electron,
+ Float_t neutral_hadron,
+ Float_t charged_hadron,
+ Float_t muon,
+ Float_t electron_bremstrahlung,
+ Float_t muon__bremstrahlung,
+ Float_t electron_delta,
+ Float_t muon_delta,
+ Float_t muon_pair,
+ Int_t annihilation,
+ Int_t bremstrahlung,
+ Int_t compton_scattering,
+ Int_t decay,
+ Int_t delta_ray,
+ Int_t hadronic,
+ Int_t energy_loss,
+ Int_t multiple_scattering,
+ Int_t pair_production,
+ Int_t photon_production,
+ Int_t rayleigh_scattering)
+{
+ // Disabled by request of FCA, kept for reference only
+ if (!gMC) return;
+ TArrayI& idtmed = *(GetIdtmed());
+ Int_t iimed = idtmed[imed];
+ // gMC->Gstpar(iimed, "CUTGAM", gamma);
+ // gMC->Gstpar(iimed, "CUTELE", electron);
+ // gMC->Gstpar(iimed, "CUTNEU", neutral_hadron);
+ // gMC->Gstpar(iimed, "CUTHAD", charged_hadron);
+ // gMC->Gstpar(iimed, "CUTMUO", muon);
+ // gMC->Gstpar(iimed, "BCUTE", electron_bremstrahlung);
+ // gMC->Gstpar(iimed, "BCUTM", muon__bremstrahlung);
+ // gMC->Gstpar(iimed, "DCUTE", electron_delta);
+ // gMC->Gstpar(iimed, "DCUTM", muon_delta);
+ // gMC->Gstpar(iimed, "PPCUTM", muon_pair);
+ // gMC->Gstpar(iimed, "ANNI", Float_t(annihilation));
+ // gMC->Gstpar(iimed, "BREM", Float_t(bremstrahlung));
+ // gMC->Gstpar(iimed, "COMP", Float_t(compton_scattering));
+ // gMC->Gstpar(iimed, "DCAY", Float_t(decay));
+ // gMC->Gstpar(iimed, "DRAY", Float_t(delta_ray));
+ // gMC->Gstpar(iimed, "HADR", Float_t(hadronic));
+ // gMC->Gstpar(iimed, "LOSS", Float_t(energy_loss));
+ // gMC->Gstpar(iimed, "MULS", Float_t(multiple_scattering));
+ // gMC->Gstpar(iimed, "PAIR", Float_t(pair_production));
+ // gMC->Gstpar(iimed, "PHOT", Float_t(photon_production));
+ // gMC->Gstpar(iimed, "RAYL", Float_t(rayleigh_scattering));
+}
+#endif
+
//____________________________________________________________________
void
AliFMD::Init()
AliFMDDebug(1, ("Initialising FMD detector object"));
TVirtualMC* mc = TVirtualMC::GetMC();
AliFMDGeometry* fmd = AliFMDGeometry::Instance();
- const TArrayI& actGeo = fmd->ActiveIds();
+ TArrayI actGeo = fmd->ActiveIds();
+ bool valid = true;
+ if (actGeo.fN <= 0) valid = false;
+ else {
+ for (int i = 0; i < actGeo.fN; i++) {
+ if (actGeo[i] < 0) {
+ valid = false;
+ break;
+ }
+ }
+ }
+ if (!valid) {
+ AliFMDDebug(1, ("Extracting geometry info from loaded geometry"));
+ fmd->ExtractGeomInfo();
+ actGeo = fmd->ActiveIds();
+ }
TArrayI actVmc(actGeo.fN);
for (Int_t i = 0; i < actGeo.fN; i++) {
+ if (actGeo[i] < 0) {
+ AliError(Form("Invalid id: %d", actGeo[i]));
+ continue;
+ }
TGeoVolume *sens = gGeoManager->GetVolume(actGeo[i]);
if (!sens) {
AliError(Form("No TGeo volume for sensitive volume ID=%d",actGeo[i]));
//
if (AliLog::GetDebugLevel("FMD", "AliFMD") < 10) return;
if (fBad && fBad->GetEntries() > 0) {
- AliWarning((Form("EndEvent", "got %d 'bad' hits", fBad->GetEntries())));
+ AliWarning(Form("got %d 'bad' hits", fBad->GetEntries()));
TIter next(fBad);
AliFMDHit* hit;
while ((hit = static_cast<AliFMDHit*>(next()))) hit->Print("D");
}
-//====================================================================
-//
-// Graphics and event display
-//
-//____________________________________________________________________
-void
-AliFMD::BuildGeometry()
-{
- //
- // Build simple ROOT TNode geometry for event display. With the new
- // geometry modeller, TGeoManager, this seems rather redundant.
- AliFMDDebug(10, ("\tCreating a simplified geometry"));
-
- AliFMDGeometry* fmd = AliFMDGeometry::Instance();
-
- static TXTRU* innerShape = 0;
- static TXTRU* outerShape = 0;
- static TObjArray* innerRot = 0;
- static TObjArray* outerRot = 0;
-
- if (!innerShape || !outerShape) {
- // Make the shapes for the modules
- for (Int_t i = 0; i < 2; i++) {
- AliFMDRing* r = 0;
- switch (i) {
- case 0: r = fmd->GetRing('I'); break;
- case 1: r = fmd->GetRing('O'); break;
- }
- if (!r) {
- AliError(Form("no ring found for i=%d", i));
- return;
- }
- Double_t siThick = r->GetSiThickness();
- const Int_t knv = r->GetNVerticies();
- Double_t theta = r->GetTheta();
- Int_t nmod = r->GetNModules();
-
- TXTRU* shape = new TXTRU(r->GetName(), r->GetTitle(), "void", knv, 2);
- for (Int_t j = 0; j < knv; j++) {
- TVector2* vv = r->GetVertex(knv - 1 - j);
- shape->DefineVertex(j, vv->X(), vv->Y());
- }
- shape->DefineSection(0, -siThick / 2, 1, 0, 0);
- shape->DefineSection(1, +siThick / 2, 1, 0, 0);
- shape->SetLineColor(kYellow); //PH kYellow is the default line color in FMD
-
- TObjArray* rots = new TObjArray(nmod);
- for (Int_t j = 0; j < nmod; j++) {
- Double_t th = (j + .5) * theta * 2;
- TString name(Form("FMD_ring_%c_rot_%02d", r->GetId(), j));
- TString title(Form("FMD Ring %c Rotation # %d", r->GetId(), j));
- TRotMatrix* rot = new TRotMatrix(name.Data(), title.Data(),
- 90, th, 90, fmod(90+th,360), 0, 0);
- rots->AddAt(rot, j);
- }
-
- switch (r->GetId()) {
- case 'i':
- case 'I': innerShape = shape; innerRot = rots; break;
- case 'o':
- case 'O': outerShape = shape; outerRot = rots; break;
- }
- }
- }
-
- TNode* top = gAlice->GetGeometry()->GetNode("alice");
-
- for (Int_t i = 1; i <= 3; i++) {
- AliFMDDetector* det = fmd->GetDetector(i);
- if (!det) {
- Warning("BuildGeometry", "FMD%d seems to be disabled", i);
- continue;
- }
- Double_t w = 0;
- Double_t rh = det->GetRing('I')->GetHighR();
- Char_t id = 'I';
- if (det->GetRing('O')) {
- w = TMath::Abs(det->GetRingZ('O') - det->GetRingZ('I'));
- id = (TMath::Abs(det->GetRingZ('O'))
- > TMath::Abs(det->GetRingZ('I')) ? 'O' : 'I');
- rh = det->GetRing('O')->GetHighR();
- }
- w += (det->GetRing(id)->GetModuleSpacing() +
- det->GetRing(id)->GetSiThickness());
- TShape* shape = new TTUBE(det->GetName(), det->GetTitle(), "void",
- det->GetRing('I')->GetLowR(), rh, w / 2);
- Double_t z = (det->GetRingZ('I') - w / 2);
- if (z > 0) z += det->GetRing(id)->GetModuleSpacing();
- top->cd();
- TNode* node = new TNode(det->GetName(), det->GetTitle(), shape,
- 0, 0, z, 0);
- fNodes->Add(node);
-
- for (Int_t j = 0; j < 2; j++) {
- AliFMDRing* r = 0;
- TShape* rshape = 0;
- TObjArray* rots = 0;
- switch (j) {
- case 0:
- r = det->GetRing('I'); rshape = innerShape; rots = innerRot; break;
- case 1:
- r = det->GetRing('O'); rshape = outerShape; rots = outerRot; break;
- }
- if (!r) continue;
-
- Double_t siThick = r->GetSiThickness();
- Int_t nmod = r->GetNModules();
- Double_t modspace = r->GetModuleSpacing();
- Double_t rz = - (z - det->GetRingZ(r->GetId()));
-
- for (Int_t k = 0; k < nmod; k++) {
- node->cd();
- Double_t offz = (k % 2 == 1 ? modspace : 0);
- TRotMatrix* rot = static_cast<TRotMatrix*>(rots->At(k));
- TString name(Form("%s%c_module_%02d", det->GetName(), r->GetId(),k));
- TString title(Form("%s%c Module %d", det->GetName(), r->GetId(),k));
- TNode* mnod = new TNode(name.Data(), title.Data(), rshape,
- 0, 0, rz - siThick / 2
- + TMath::Sign(offz,z), rot);
- mnod->SetLineColor(kYellow); //PH kYellow is the default line color in FMD
- fNodes->Add(mnod);
- } // for (Int_t k = 0 ; ...)
- } // for (Int_t j = 0 ; ...)
- } // for (Int_t i = 1 ; ...)
-}
-
-//____________________________________________________________________
-void
-AliFMD::LoadPoints(Int_t /* track */)
-{
- // Store x, y, z of all hits in memory for display.
- //
- // Normally, the hits are drawn using TPolyMarker3D - however, that
- // is not very useful for the FMD. Therefor, this member function
- // is overloaded to make TMarker3D, via the class AliFMDPoints.
- // AliFMDPoints is a local class.
- //
- if (!fHits) {
- AliError(Form("fHits == 0. Name is %s",GetName()));
- return;
- }
- Int_t nHits = fHits->GetEntriesFast();
- if (nHits == 0) {
- return;
- }
- Int_t tracks = gAlice->GetMCApp()->GetNtrack();
- if (fPoints == 0) fPoints = new TObjArray(2 * tracks);
-
- // Get geometry
- AliFMDGeometry* geom = AliFMDGeometry::Instance();
- geom->Init();
- geom->InitTransformations();
-
- // Now make markers for each hit
- // AliInfo(Form("Drawing %d hits (have %d points) for track %d",
- // nHits, fPoints->GetEntriesFast(), track));
- for (Int_t ihit = 0; ihit < nHits; ihit++) {
- AliFMDHit* hit = static_cast<AliFMDHit*>(fHits->At(ihit));
- if (!hit) continue;
- Double_t edep = hit->Edep();
- Double_t m = hit->M();
- Double_t poverm = (m == 0 ? 0 : hit->P());
- Double_t absQ = TMath::Abs(hit->Q());
- Bool_t bad = kFALSE;
- // This `if' is to debug abnormal energy depositions. We trigger on
- // p/m approx larger than or equal to a MIP, and a large edep - more
- // than 1 keV - a MIP is 100 eV.
- if (edep > absQ * absQ && poverm > 1) bad = kTRUE;
-
- AliFMDPoints* p1 = new AliFMDPoints(hit, kRed); //PH kRed is the default marker color in FMD
- // AliPoints* p1 = new AliPoints();
- // p1->SetMarkerColor(GetMarkerColor());
- // p1->SetMarkerSize(GetMarkerSize());
- // p1->SetPoint(0, hit->X(), hit->Y(), hit->Z());
- p1->SetDetector(this);
- p1->SetParticle(hit->GetTrack());
- fPoints->AddAt(p1, hit->GetTrack());
- if (bad) {
- p1->SetMarkerColor(4);
- // p1->SetMarkerSize(2 * GetMarkerSize());
- }
-
- Double_t x, y, z;
- geom->Detector2XYZ(hit->Detector(), hit->Ring(), hit->Sector(),
- hit->Strip(), x, y, z);
- AliFMDPoints* p = new AliFMDPoints(hit, 3);
- // AliPoints* p = new AliPoints();
- // p->SetMarkerColor(3);
- // p->SetMarkerSize(GetMarkerSize());
- // p->SetPoint(0, x, y, z);
- p->SetDetector(this);
- p->SetParticle(hit->GetTrack());
- p->SetXYZ(x, y, z);
- p->SetMarkerColor(3);
- fPoints->AddAt(p, tracks+hit->GetTrack());
- if (bad) {
- p->SetMarkerColor(5);
- // p->SetMarkerSize(2 * GetMarkerSize());
- }
- // AliInfo(Form("Adding point at %d", tracks+hit->GetTrack()));
- }
-}
-
-//____________________________________________________________________
-void
-AliFMD::DrawDetector()
-{
- // Draw a shaded view of the Forward multiplicity detector. This
- // isn't really useful anymore.
- AliFMDDebug(10, ("\tDraw detector"));
-}
-
-//____________________________________________________________________
-Int_t
-AliFMD::DistancetoPrimitive(Int_t, Int_t)
-{
- // Calculate the distance from the mouse to the FMD on the screen
- // Dummy routine.
- //
- return 9999;
-}
//====================================================================
//
hit = new (a[fNhits]) AliFMDHit(fIshunt, track, detector, ring, sector,
strip, x, y, z, px, py, pz, edep, pdg, t,
l, stop);
+ // gMC->AddTrackReference(track, 12);
fNhits++;
+
+ //Reference track
+
+ AliMC *mcApplication = (AliMC*)gAlice->GetMCApp();
+
+ AliTrackReference* trackRef =
+ AddTrackReference(mcApplication->GetCurrentTrackNumber(),
+ AliTrackReference::kFMD);
+ UInt_t stripId = AliFMDStripIndex::Pack(detector,ring,sector,strip);
+ trackRef->SetUserId(stripId);
+
+
+
return hit;
}
//____________________________________________________________________
void
-AliFMD::AddDigitByFields(UShort_t detector,
- Char_t ring,
- UShort_t sector,
- UShort_t strip,
- UShort_t count1,
- Short_t count2,
- Short_t count3,
- Short_t count4)
+AliFMD::AddDigitByFields(UShort_t detector,
+ Char_t ring,
+ UShort_t sector,
+ UShort_t strip,
+ UShort_t count1,
+ Short_t count2,
+ Short_t count3,
+ Short_t count4,
+ UShort_t nrefs,
+ Int_t* refs)
{
// add a real digit - as coming from data
//
// count3 ADC count (a 10-bit word), or -1 if not used
TClonesArray& a = *(DigitsArray());
- new (a[fNdigits++])
- AliFMDDigit(detector, ring, sector, strip, count1, count2, count3, count4);
- AliFMDDebug(15, ("Adding digit # %5d/%5d for FMD%d%c[%2d,%3d]=(%d,%d,%d,%d)",
+ AliFMDDebug(15, ("Adding digit # %5d/%5d for FMD%d%c[%2d,%3d]"
+ "=(%d,%d,%d,%d) with %d tracks",
fNdigits-1, a.GetEntriesFast(),
detector, ring, sector, strip,
- count1, count2, count3, count4));
+ count1, count2, count3, count4, nrefs));
+ new (a[fNdigits++])
+ AliFMDDigit(detector, ring, sector, strip,
+ count1, count2, count3, count4, nrefs, refs);
}
Short_t(digits[8]), // ADC Count4
UShort_t(digits[9]), // N particles
UShort_t(digits[10])); // N primaries
-
}
//____________________________________________________________________
void
-AliFMD::AddSDigitByFields(UShort_t detector,
- Char_t ring,
- UShort_t sector,
- UShort_t strip,
- Float_t edep,
- UShort_t count1,
- Short_t count2,
- Short_t count3,
- Short_t count4,
- UShort_t ntot,
- UShort_t nprim)
+AliFMD::AddSDigitByFields(UShort_t detector,
+ Char_t ring,
+ UShort_t sector,
+ UShort_t strip,
+ Float_t edep,
+ UShort_t count1,
+ Short_t count2,
+ Short_t count3,
+ Short_t count4,
+ UShort_t ntot,
+ UShort_t nprim,
+ Int_t* refs)
{
// add a summable digit
//
TClonesArray& a = *(SDigitsArray());
// AliFMDDebug(0, ("Adding sdigit # %d", fNsdigits));
+ AliFMDDebug(15, ("Adding sdigit # %5d/%5d for FMD%d%c[%2d,%3d]"
+ "=(%d,%d,%d,%d) with %d tracks %d primaries (%p)",
+ fNsdigits-1, a.GetEntriesFast(),
+ detector, ring, sector, strip,
+ count1, count2, count3, count4, ntot, nprim, refs));
new (a[fNsdigits++])
AliFMDSDigit(detector, ring, sector, strip, edep,
- count1, count2, count3, count4, ntot, nprim);
+ count1, count2, count3, count4, ntot, nprim, refs);
}
//____________________________________________________________________
if (!fHits) {
fHits = new TClonesArray("AliFMDHit", 1000);
fNhits = 0;
+ if (gAlice && gAlice->GetMCApp() && gAlice->GetMCApp()->GetHitLists())
+ gAlice->GetMCApp()->AddHitList(fHits);
}
return fHits;
}
//
AliFMDHitDigitizer digitizer(this, AliFMDHitDigitizer::kDigits);
digitizer.Init();
- digitizer.Exec("");
+ digitizer.Digitize("");
}
//____________________________________________________________________
//
AliFMDHitDigitizer digitizer(this, AliFMDHitDigitizer::kSDigits);
digitizer.Init();
- digitizer.Exec("");
+ digitizer.Digitize("");
}
//____________________________________________________________________
AliDigitizer*
-AliFMD::CreateDigitizer(AliRunDigitizer* manager) const
+AliFMD::CreateDigitizer(AliDigitizationInput* digInput) const
{
// Create a digitizer object
AliFMDBaseDigitizer* digitizer = 0;
#ifdef USE_SSDIGITIZER
- digitizer = new AliFMDSSDigitizer(manager);
+ digitizer = new AliFMDSSDigitizer(digInput);
#else
/* This is what we actually do, and will work */
#if 0
AliInfo("SDigit->Digit conversion not really supported, "
"doing Hit->Digit conversion instead");
#endif
- digitizer = new AliFMDDigitizer(manager);
+ digitizer = new AliFMDDigitizer(digInput);
#endif
return digitizer;
}
writer.Exec();
}
+//====================================================================
+//
+// Raw data reading
+//
+//__________________________________________________________________
+Bool_t
+AliFMD::Raw2SDigits(AliRawReader* reader)
+{
+ // Turn digits into raw data.
+ //
+ // This uses the class AliFMDRawWriter to do the job. Please refer
+ // to that class for more information.
+ AliFMDParameters::Instance()->Init();
+ MakeTree("S");
+ MakeBranch("S");
+
+ TClonesArray* sdigits = SDigits();
+ AliFMDReconstructor rec;
+
+ // The two boolean arguments
+ // Make sdigits instead of digits
+ // Subtract the pedestal off the signal
+ rec.Digitize(reader, sdigits);
+ //
+ // Bool_t ret = fmdReader.ReadAdcs(sdigits, kTRUE, kTRUE);
+ // sdigits->ls();
+ UShort_t ns = sdigits->GetEntriesFast();
+ if (AliLog::GetDebugLevel("FMD", 0) > 5) {
+ for (UShort_t i = 0; i < ns; i++)
+ sdigits->At(i)->Print("pl");
+ }
+ AliFMDDebug(1, ("Got a total of %d SDigits", ns));
+
+ fLoader->TreeS()->Fill();
+ ResetSDigits();
+ fLoader->WriteSDigits("OVERWRITE");
+
+ return kTRUE;
+}
+
//====================================================================
//