From 9de78b35aa5e35dbfb3e41c7ba5b2e1e1795ab2a Mon Sep 17 00:00:00 2001 From: cholm Date: Thu, 14 Dec 2006 22:57:50 +0000 Subject: [PATCH] Implemented the AliModule::AddAlignableVolumes properly via call to AliFMDGeometry. We search through the TGeo geometry for nodes that we should make alignable. If needed, we can make them physical too. Added a small test macro to check that everything works as expected. --- FMD/AliFMD.cxx | 4 +- FMD/AliFMDDetector.cxx | 137 ++++++++++++++++++++++++++++++++++++ FMD/AliFMDDetector.h | 3 + FMD/AliFMDGeometry.cxx | 10 +++ FMD/AliFMDGeometry.h | 2 + FMD/scripts/TestAlignable.C | 15 ++++ 6 files changed, 170 insertions(+), 1 deletion(-) create mode 100644 FMD/scripts/TestAlignable.C diff --git a/FMD/AliFMD.cxx b/FMD/AliFMD.cxx index 38d8e118a26..bc744f3a1fc 100644 --- a/FMD/AliFMD.cxx +++ b/FMD/AliFMD.cxx @@ -1086,6 +1086,8 @@ AliFMD::AddAlignableVolumes() const // This code was made by Raffaele Grosso . I // (cholm) will probably want to change it. For one, I think it // should be the job of the geometry manager to deal with this. + AliFMDGeometry::Instance()->SetAlignableVolumes(); +#if 0 for(size_t f = 1; f <= 3; f++){ // Detector 1,2,3 for(size_t tb = 0; tb <2 ; tb++){ // Top/Bottom char stb = tb == 0 ? 'T' : 'B'; @@ -1116,7 +1118,7 @@ AliFMD::AddAlignableVolumes() const } } } - +#endif } //___________________________________________________________________ // diff --git a/FMD/AliFMDDetector.cxx b/FMD/AliFMDDetector.cxx index 2a890d5e487..2674f633e9e 100644 --- a/FMD/AliFMDDetector.cxx +++ b/FMD/AliFMDDetector.cxx @@ -165,6 +165,8 @@ AliFMDDetector::HasAllTransforms(Char_t ring) const (name[3] == 'T' || name[3] == 'B')) #define IS_NODE_SENSOR(name) \ (name[0] == 'F' && name[2] == 'S' && name[3] == 'E') +#define IS_NODE_HALF(name) \ + (name[0] == 'F' && name[2] == 'M' && (name[3] == 'B' || name[3] == 'T')) //____________________________________________________________________ void @@ -255,6 +257,141 @@ AliFMDDetector::InitTransformations() } } +//____________________________________________________________________ +void +AliFMDDetector::SetAlignableVolumes() const +{ + AliDebug(10, Form("Making alignable volumes for FMD%d", fId)); + if (!gGeoManager) { + AliFatal("No TGeoManager defined"); + return; + } + TGeoVolume* topVolume = gGeoManager->GetTopVolume(); + if (!topVolume) { + AliFatal("No top-level volume defined"); + return; + } + + // Make an iterator + TGeoIterator next(topVolume); + next.Reset(topVolume); + next.SetTopName(Form("/%s_1", topVolume->GetName())); + TGeoNode* node = 0; + + Int_t nInnerSensor = (fInner ? fInner->GetNModules() : 0); + Int_t nOuterSensor = (fOuter ? fOuter->GetNModules() : 0); + // Find the node corresponding to this detector, and then find the + // sensor volumes + Bool_t thisNodeFound = kFALSE; + Char_t thisHalf = '\0'; + Int_t iInnerSensor = 0; + Int_t iOuterSensor = 0; + Bool_t hasTop = false; + Bool_t hasBottom = false; + + TString path, align; + while ((node = static_cast(next())) + && (iInnerSensor < nInnerSensor || iOuterSensor < nOuterSensor + || !hasBottom || !hasTop)) { + // Get nodes names + const Char_t* name = node->GetName(); + if (!name) continue; + AliDebug((name[0] == 'F' ? 40 : 50), Form("Got volume %s", name)); + // Check if this node is this detector + // The base offset for numbers in the ASCII table is 48 + if (IS_NODE_THIS(name)) { + AliDebug(20, Form("Found detector node '%s' for FMD%d", name, fId)); + thisNodeFound = kTRUE; + } + + // if a half ring is found, then we're on that branch, and we + // check if this node represents a half ring on that branch + if (thisNodeFound && IS_NODE_HALF(name)) { + AliDebug(30, Form("Found half node '%s' for FMD%d", name, fId)); + // Get the half Id. + thisHalf = name[3]; + + // Check if we're done + Bool_t done = (thisHalf == 'T' ? hasTop : hasBottom); + if (done) { + AliDebug(20,Form("Already has all halves for detector %c",name[1])); + continue; + } + + switch (thisHalf) { + case 'T': hasTop = true; break; + case 'B': hasBottom = true; break; + default: + AliWarning(Form("Unknown part '%c' of FMD%d", fId)); + continue; // because the node is unknown. + } + + // Get the node path + next.GetPath(path); + align = Form("FMD/FMD%d%c", fId, thisHalf); + } + + // if the detector was found, then we're on that branch, and we + // check if this node represents a module in that branch. + if (thisNodeFound && thisHalf && IS_NODE_SENSOR(name)) { + AliDebug(30, Form("Found sensor node '%s' for FMD%d", name, fId)); + // Get the ring Id. + Char_t ringid = name[1]; + + // check that the ring is valid + if (!GetRing(ringid)) { + AliWarning(Form("Invalid ring %c for FMD%d", ringid, fId)); + continue; + } + + // Check if we're done + Bool_t done = false; + switch (ringid) { + case 'I': done = iInnerSensor >= nInnerSensor; break; + case 'O': done = iOuterSensor >= nOuterSensor; break; + default: continue; + } + if (done) { + AliDebug(20,Form("Already has all sensor volumes for ring %c",ringid)); + continue; + } + // Get the copy (module) number, and check that it hasn't + // already been added to the container. + Int_t copy = node->GetNumber(); + next.GetPath(path); + // path.Replace("ALIC", "/ALIC_1"); + align = Form("FMD/FMD%d_%c/FMD%c_%02d", fId, thisHalf, ringid, copy); + + switch (ringid) { + case 'I': iInnerSensor++; break; + case 'O': iOuterSensor++; break; + } + } + if (!align.IsNull() && !path.IsNull()) { + AliDebug(20, Form("Got %s -> %s", path.Data(), align.Data())); + TGeoPNEntry* entry = + gGeoManager->SetAlignableEntry(align.Data(),path.Data()); + if(!entry) + AliFatal(Form("Alignable entry %s not created. " + "Volume path %s not valid", + align.Data(),path.Data())); +#ifdef MAKE_ALIGNABLE_PHYSICAL + TGeoPhysicalNode* phys = gGeoManager->MakeAlignablePN(entry); + if (!phys) + AliWarning(Form("Physical node entry %s not created. " + "Volume path %s not valid", + align.Data(),path.Data())); +#endif + align = ""; + } + AliDebug(20, Form("FMD%d: top: %d bottom: %d Inner: %d/%d Outer %d/%d", + fId, hasTop, hasBottom, iInnerSensor, nInnerSensor, + iOuterSensor, nOuterSensor)); + } +} + + + //____________________________________________________________________ AliFMDRing* AliFMDDetector::GetRing(Char_t id) const diff --git a/FMD/AliFMDDetector.h b/FMD/AliFMDDetector.h index 3740256fd96..aaf40a4fa9d 100644 --- a/FMD/AliFMDDetector.h +++ b/FMD/AliFMDDetector.h @@ -135,6 +135,9 @@ public: detector. */ Bool_t XYZ2Detector(Double_t x, Double_t y, Double_t z, Char_t& ring, UShort_t& sector, UShort_t& strip) const; + + /** Declare alignable volumes */ + virtual void SetAlignableVolumes() const; protected: /** Check if we have all transformations for a ring @param ring Ring to check for diff --git a/FMD/AliFMDGeometry.cxx b/FMD/AliFMDGeometry.cxx index 176ff2fa913..ab4ac1693db 100644 --- a/FMD/AliFMDGeometry.cxx +++ b/FMD/AliFMDGeometry.cxx @@ -400,6 +400,16 @@ AliFMDGeometry::Impact(const TParticle* /* particle */) const return kFALSE; } +//____________________________________________________________________ +void +AliFMDGeometry::SetAlignableVolumes() const +{ + // Declare alignable volumes + for (Int_t d = 1; d <= 3; d++) + if (GetDetector(d)) GetDetector(d)->SetAlignableVolumes(); +} + + //____________________________________________________________________ void AliFMDGeometry::ExtractGeomInfo() diff --git a/FMD/AliFMDGeometry.h b/FMD/AliFMDGeometry.h index 38fa18c9640..8a41c9a152c 100644 --- a/FMD/AliFMDGeometry.h +++ b/FMD/AliFMDGeometry.h @@ -205,6 +205,8 @@ public: @param particle Track @return @c true if @a particle will hit this detector */ virtual Bool_t Impact(const TParticle* particle) const; + /** Declare alignable volumes */ + virtual void SetAlignableVolumes() const; protected: Bool_t fIsInitialized; // Whether singleton is initalized AliFMDRing* fInner; // Inner ring geometry information diff --git a/FMD/scripts/TestAlignable.C b/FMD/scripts/TestAlignable.C new file mode 100644 index 00000000000..2fef52e92f3 --- /dev/null +++ b/FMD/scripts/TestAlignable.C @@ -0,0 +1,15 @@ +void +TestAlignable(const char* file="geom.root", Int_t lvl=35) +{ + TGeoManager::Import(file); + if (!gGeoManager) return; + + AliFMDGeometry* g = AliFMDGeometry::Instance(); + g->Init(); + + AliLog::SetModuleDebugLevel("FMD", lvl); + + + g->SetAlignableVolumes(); +} + -- 2.43.0