1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 // Class AliMUONVGeometryBuilder
19 // -----------------------------
20 // Abstract base class for geometry construction per geometry module(s).
21 // Author: Ivana Hrivnacova, IPN Orsay
24 #include "AliMUONVGeometryBuilder.h"
25 #include "AliMUONGeometryModule.h"
26 #include "AliMUONGeometryDetElement.h"
27 #include "AliMUONGeometryEnvelopeStore.h"
28 #include "AliMUONGeometryEnvelope.h"
29 #include "AliMUONGeometryConstituent.h"
30 #include "AliMUONGeometryBuilder.h"
31 #include "AliMUONStringIntMap.h"
33 #include "AliMpDEManager.h"
34 #include "AliMpExMap.h"
38 #include <Riostream.h>
39 #include <TObjArray.h>
41 #include <TGeoMatrix.h>
42 #include <TVirtualMC.h>
45 ClassImp(AliMUONVGeometryBuilder)
48 //______________________________________________________________________________
49 AliMUONVGeometryBuilder::AliMUONVGeometryBuilder(
56 /// Standard constructor
58 // Create the module geometries array
59 fGeometryModules = new TObjArray();
60 fGeometryModules->SetOwner(kFALSE);
62 for (Int_t i=0; i<nofModules; i++ )
63 fGeometryModules->Add(new AliMUONGeometryModule(firstModuleId++));
66 //______________________________________________________________________________
67 AliMUONVGeometryBuilder::AliMUONVGeometryBuilder()
72 /// Default constructor
75 //______________________________________________________________________________
76 AliMUONVGeometryBuilder::~AliMUONVGeometryBuilder()
80 if (fGeometryModules) {
81 fGeometryModules->Clear(); // Sets pointers to 0 since it is not the owner
82 delete fGeometryModules;
90 //______________________________________________________________________________
92 AliMUONVGeometryBuilder::ConvertTransform(const TGeoHMatrix& transform) const
94 /// Convert transformation into the reference frame
96 if ( fReferenceFrame.IsIdentity() )
99 return AliMUONGeometryBuilder::Multiply( fReferenceFrame,
101 fReferenceFrame.Inverse() );
105 //______________________________________________________________________________
107 AliMUONVGeometryBuilder::ConvertDETransform(const TGeoHMatrix& transform) const
109 /// Convert DE transformation into the reference frame
111 if ( fReferenceFrame.IsIdentity() )
114 return AliMUONGeometryBuilder::Multiply( fReferenceFrame,
119 //______________________________________________________________________________
120 TString AliMUONVGeometryBuilder::ComposePath(const TString& volName,
123 /// Compose path from given volName and copyNo
133 //______________________________________________________________________________
134 void AliMUONVGeometryBuilder::MapSV(const TString& path0,
135 const TString& volName, Int_t detElemId) const
137 /// Update the path with all daughters volumes recursively
138 /// and map it to the detection element Id if it is a sensitive volume
140 // Get module sensitive volumes map
141 Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId);
142 AliMUONStringIntMap* svMap = GetSVMap(moduleId);
144 Int_t nofDaughters = gMC->NofVolDaughters(volName);
145 if (nofDaughters == 0) {
147 // Get the name of the last volume in the path
148 Ssiz_t npos1 = path0.Last('/')+1;
149 Ssiz_t npos2 = path0.Last('_');
150 TString volName(path0(npos1, npos2-npos1));
152 // Check if it is sensitive volume
153 Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId);
154 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
155 if ( geometry->IsSensitiveVolume(volName) &&
156 ! svMap->Get(path0) ) {
157 //cout << ".. adding to the map "
158 // << path0 << " " << detElemId << endl;
160 // Map the sensitive volume to detection element
161 svMap->Add(path0, detElemId);
166 for (Int_t i=0; i<nofDaughters; i++) {
167 Int_t copyNo = gMC->VolDaughterCopyNo(volName, i);
168 TString newName = gMC->VolDaughterName(volName, i);
170 TString path = path0;
171 path += ComposePath(newName, copyNo);
173 MapSV(path, newName, detElemId);
181 //______________________________________________________________________________
182 AliMUONGeometryModule*
183 AliMUONVGeometryBuilder::GetGeometry(Int_t moduleId) const
185 /// Return the module geometry specified by moduleId
187 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
189 AliMUONGeometryModule* geometry
190 = (AliMUONGeometryModule*)fGeometryModules->At(i);
192 if ( geometry->GetModuleId() == moduleId) return geometry;
198 //______________________________________________________________________________
199 AliMUONGeometryEnvelopeStore*
200 AliMUONVGeometryBuilder::GetEnvelopes(Int_t moduleId) const
202 /// Return the envelope store of the module geometry specified by moduleId
204 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
207 AliFatal(Form("Module geometry %d is not defined", moduleId));
211 return geometry->GetEnvelopeStore();
214 //______________________________________________________________________________
216 AliMUONVGeometryBuilder::GetSVMap(Int_t moduleId) const
218 /// Return the transformation store of the module geometry specified by moduleId
220 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
223 AliFatal(Form("Geometry %d is not defined", moduleId));
227 return geometry->GetSVMap();
230 //______________________________________________________________________________
232 AliMUONVGeometryBuilder::GetModuleId(const TString& envName) const
234 /// Return module Id which has the envelope with given name
236 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
238 AliMUONGeometryModule* geometry
239 = (AliMUONGeometryModule*)fGeometryModules->At(i);
241 if ( geometry->GetEnvelopeStore()->FindEnvelope(envName) )
242 return geometry->GetModuleId();
249 //______________________________________________________________________________
250 void AliMUONVGeometryBuilder::SetTranslation(Int_t moduleId,
251 const TGeoTranslation& translation)
253 /// Set the translation to the geometry module given by moduleId,
254 /// apply reference frame transformation
256 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
259 AliFatal(Form("Geometry %d is not defined", moduleId));
263 // Apply frame transform
264 TGeoHMatrix newTransform = ConvertTransform(translation);
266 // Set new transformation
267 geometry->SetTransformation(newTransform);
271 //______________________________________________________________________________
272 void AliMUONVGeometryBuilder::SetTransformation(Int_t moduleId,
273 const TGeoTranslation& translation,
274 const TGeoRotation& rotation)
276 /// Set the transformation to the geometry module given by moduleId,
277 /// apply reference frame transformation
279 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
282 AliFatal(Form("Geometry %d is not defined", moduleId));
286 TGeoCombiTrans transformation
287 = TGeoCombiTrans(translation, rotation);
289 // Apply frame transform
290 TGeoHMatrix newTransform = ConvertTransform(transformation);
292 // Set new transformation
293 geometry->SetTransformation(newTransform);
296 //______________________________________________________________________________
297 void AliMUONVGeometryBuilder::SetVolume(Int_t moduleId,
298 const TString& volumeName,
301 /// Set volume name, virtuality
303 TString path = GetGeometry(moduleId)->GetVolumePath();
304 // cout << "in AliMUONVGeometryBuilder::SetVolume " << path.Data() << endl;
306 if ( path == "" ) path = "/ALIC_1";
307 path += ComposePath(volumeName, 1);
309 GetGeometry(moduleId)->SetVolumePath(path);
310 GetGeometry(moduleId)->SetIsVirtual(isVirtual);
311 // cout << "... set " << path.Data() << endl;
314 //______________________________________________________________________________
315 void AliMUONVGeometryBuilder::SetMotherVolume(Int_t moduleId,
316 const TString& volumeName)
318 /// Set mother volume name
320 TString motherVolumeName = ComposePath(volumeName, 1);
322 TString path = GetGeometry(moduleId)->GetVolumePath();
323 if ( path == "" ) path = "/ALIC_1";
324 path.Insert(7, motherVolumeName);
326 GetGeometry(moduleId)->SetVolumePath(path);
333 //______________________________________________________________________________
334 void AliMUONVGeometryBuilder::SetReferenceFrame(
335 const TGeoCombiTrans& referenceFrame)
337 /// Set reference frame to builder and to all associated geometry
340 fReferenceFrame = referenceFrame;
342 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
343 AliMUONGeometryModule* geometry
344 = (AliMUONGeometryModule*)fGeometryModules->At(i);
345 AliMUONGeometryEnvelopeStore* envelopeStore
346 = geometry->GetEnvelopeStore();
348 envelopeStore->SetReferenceFrame(referenceFrame);
353 //______________________________________________________________________________
354 void AliMUONVGeometryBuilder::CreateDetElements() const
356 /// Create detection elements and fill their global and
357 /// local transformations from geometry.
359 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
360 AliMUONGeometryModule* geometry
361 = (AliMUONGeometryModule*)fGeometryModules->At(i);
363 const TObjArray* envelopes
364 = geometry->GetEnvelopeStore()->GetEnvelopes();
366 AliMpExMap* detElements
367 = geometry->GetTransformer()->GetDetElementStore();
369 for (Int_t j=0; j<envelopes->GetEntriesFast(); j++) {
370 AliMUONGeometryEnvelope* envelope
371 = (AliMUONGeometryEnvelope*)envelopes->At(j);
373 // skip envelope not corresponding to detection element
374 if ( envelope->GetUniqueID() == 0) continue;
377 Int_t detElemId = envelope->GetUniqueID();
379 // Compose full volume path
380 TString volPath = geometry->GetVolumePath();
381 volPath += ComposePath(envelope->GetName(), envelope->GetCopyNo());
383 // Create detection element
384 AliMUONGeometryDetElement* detElement
385 = new AliMUONGeometryDetElement(detElemId, volPath);
386 detElements->Add(detElemId, detElement);
388 // Compose local transformation
389 const TGeoCombiTrans* transform = envelope->GetTransformation();
390 // Apply frame transform
391 TGeoHMatrix localTransform = ConvertDETransform(*transform);
392 detElement->SetLocalTransformation(localTransform);
394 // Compose global transformation
395 TGeoHMatrix globalTransform
396 = AliMUONGeometryBuilder::Multiply(
397 (*geometry->GetTransformer()->GetTransformation()),
400 // Set the global transformation to detection element
401 detElement->SetGlobalTransformation(globalTransform);
406 //_____ _________________________________________________________________________
407 void AliMUONVGeometryBuilder::RebuildSVMaps(Bool_t withEnvelopes) const
409 /// Clear the SV maps in memory and fill them from defined geometry.
411 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
412 AliMUONGeometryModule* geometry
413 = (AliMUONGeometryModule*)fGeometryModules->At(i);
416 geometry->GetSVMap()->Clear();
418 // Fill the map from geometry
419 const TObjArray* envelopes
420 = geometry->GetEnvelopeStore()->GetEnvelopes();
422 for (Int_t j=0; j<envelopes->GetEntriesFast(); j++) {
423 AliMUONGeometryEnvelope* envelope
424 = (AliMUONGeometryEnvelope*)envelopes->At(j);
426 // skip envelope not corresponding to detection element
427 if ( envelope->GetUniqueID() == 0 ) continue;
429 // Get volume path of detection element
430 AliMUONGeometryDetElement* detElement
431 = geometry->GetTransformer()->GetDetElement(envelope->GetUniqueID());
432 std::string path0 = detElement->GetVolumePath().Data();
434 if ( ! withEnvelopes && geometry->IsVirtual() ) {
435 std::string vName = geometry->GetTransformer()->GetVolumeName().Data();
436 std::string vPath = ComposePath(vName, 1).Data();
437 path0.erase(path0.find(vPath), vPath.size());
440 if ( ! withEnvelopes && envelope->IsVirtual()) {
441 std::string eName = envelope->GetName();
442 std::string ePath = ComposePath(eName, envelope->GetCopyNo()).Data();
443 path0.erase(path0.find(ePath), ePath.size());
446 if ( ! envelope->IsVirtual() )
447 MapSV(path0, envelope->GetName(), envelope->GetUniqueID());
449 for (Int_t k=0; k<envelope->GetConstituents()->GetEntriesFast(); k++) {
450 AliMUONGeometryConstituent* constituent
451 = (AliMUONGeometryConstituent*)envelope->GetConstituents()->At(k);
452 TString path = path0;
453 path += ComposePath(constituent->GetName(), constituent->GetCopyNo());
454 MapSV(path, constituent->GetName(), envelope->GetUniqueID());