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 //-----------------------------------------------------------------------------
19 // Class AliMUONVGeometryBuilder
20 // -----------------------------
21 // Abstract base class for geometry construction per geometry module(s).
22 // Author: Ivana Hrivnacova, IPN Orsay
24 //-----------------------------------------------------------------------------
26 #include "AliMUONVGeometryBuilder.h"
27 #include "AliMUONGeometryModule.h"
28 #include "AliMUONGeometryDetElement.h"
29 #include "AliMUONGeometryEnvelopeStore.h"
30 #include "AliMUONGeometryEnvelope.h"
31 #include "AliMUONGeometryConstituent.h"
32 #include "AliMUONGeometryBuilder.h"
33 #include "AliMUONStringIntMap.h"
35 #include "AliMpDEManager.h"
36 #include "AliMpExMap.h"
40 #include <Riostream.h>
41 #include <TObjArray.h>
43 #include <TGeoMatrix.h>
44 #include <TVirtualMC.h>
47 ClassImp(AliMUONVGeometryBuilder)
50 //______________________________________________________________________________
51 AliMUONVGeometryBuilder::AliMUONVGeometryBuilder(
58 /// Standard constructor
60 // Create the module geometries array
61 fGeometryModules = new TObjArray();
62 fGeometryModules->SetOwner(kFALSE);
64 for (Int_t i=0; i<nofModules; i++ )
65 fGeometryModules->Add(new AliMUONGeometryModule(firstModuleId++));
68 //______________________________________________________________________________
69 AliMUONVGeometryBuilder::AliMUONVGeometryBuilder()
74 /// Default constructor
77 //______________________________________________________________________________
78 AliMUONVGeometryBuilder::~AliMUONVGeometryBuilder()
82 if (fGeometryModules) {
83 fGeometryModules->Clear(); // Sets pointers to 0 since it is not the owner
84 delete fGeometryModules;
92 //______________________________________________________________________________
94 AliMUONVGeometryBuilder::ConvertTransform(const TGeoHMatrix& transform) const
96 /// Convert transformation into the reference frame
98 if ( fReferenceFrame.IsIdentity() )
101 return AliMUONGeometryBuilder::Multiply( fReferenceFrame,
103 fReferenceFrame.Inverse() );
107 //______________________________________________________________________________
109 AliMUONVGeometryBuilder::ConvertDETransform(const TGeoHMatrix& transform) const
111 /// Convert DE transformation into the reference frame
113 if ( fReferenceFrame.IsIdentity() )
116 return AliMUONGeometryBuilder::Multiply( fReferenceFrame,
121 //______________________________________________________________________________
122 TString AliMUONVGeometryBuilder::ComposePath(const TString& volName,
125 /// Compose path from given volName and copyNo
135 //______________________________________________________________________________
136 void AliMUONVGeometryBuilder::MapSV(const TString& path0,
137 const TString& volName, Int_t detElemId) const
139 /// Update the path with all daughters volumes recursively
140 /// and map it to the detection element Id if it is a sensitive volume
142 // Get module sensitive volumes map
143 Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId);
144 AliMUONStringIntMap* svMap = GetSVMap(moduleId);
146 Int_t nofDaughters = gMC->NofVolDaughters(volName);
147 if (nofDaughters == 0) {
149 // Get the name of the last volume in the path
150 Ssiz_t npos1 = path0.Last('/')+1;
151 Ssiz_t npos2 = path0.Last('_');
152 TString volName(path0(npos1, npos2-npos1));
154 // Check if it is sensitive volume
155 Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId);
156 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
157 if ( geometry->IsSensitiveVolume(volName) &&
158 ! svMap->Get(path0) ) {
159 //cout << ".. adding to the map "
160 // << path0 << " " << detElemId << endl;
162 // Map the sensitive volume to detection element
163 svMap->Add(path0, detElemId);
168 for (Int_t i=0; i<nofDaughters; i++) {
169 Int_t copyNo = gMC->VolDaughterCopyNo(volName, i);
170 TString newName = gMC->VolDaughterName(volName, i);
172 TString path = path0;
173 path += ComposePath(newName, copyNo);
175 MapSV(path, newName, detElemId);
183 //______________________________________________________________________________
184 AliMUONGeometryModule*
185 AliMUONVGeometryBuilder::GetGeometry(Int_t moduleId) const
187 /// Return the module geometry specified by moduleId
189 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
191 AliMUONGeometryModule* geometry
192 = (AliMUONGeometryModule*)fGeometryModules->At(i);
194 if ( geometry->GetModuleId() == moduleId) return geometry;
200 //______________________________________________________________________________
201 AliMUONGeometryEnvelopeStore*
202 AliMUONVGeometryBuilder::GetEnvelopes(Int_t moduleId) const
204 /// Return the envelope store of the module geometry specified by moduleId
206 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
209 AliFatal(Form("Module geometry %d is not defined", moduleId));
213 return geometry->GetEnvelopeStore();
216 //______________________________________________________________________________
218 AliMUONVGeometryBuilder::GetSVMap(Int_t moduleId) const
220 /// Return the transformation store of the module geometry specified by moduleId
222 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
225 AliFatal(Form("Geometry %d is not defined", moduleId));
229 return geometry->GetSVMap();
232 //______________________________________________________________________________
234 AliMUONVGeometryBuilder::GetModuleId(const TString& envName) const
236 /// Return module Id which has the envelope with given name
238 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
240 AliMUONGeometryModule* geometry
241 = (AliMUONGeometryModule*)fGeometryModules->At(i);
243 if ( geometry->GetEnvelopeStore()->FindEnvelope(envName) )
244 return geometry->GetModuleId();
251 //______________________________________________________________________________
252 void AliMUONVGeometryBuilder::SetTranslation(Int_t moduleId,
253 const TGeoTranslation& translation)
255 /// Set the translation to the geometry module given by moduleId,
256 /// apply reference frame transformation
258 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
261 AliFatal(Form("Geometry %d is not defined", moduleId));
265 // Apply frame transform
266 TGeoHMatrix newTransform = ConvertTransform(translation);
268 // Set new transformation
269 geometry->SetTransformation(newTransform);
273 //______________________________________________________________________________
274 void AliMUONVGeometryBuilder::SetTransformation(Int_t moduleId,
275 const TGeoTranslation& translation,
276 const TGeoRotation& rotation)
278 /// Set the transformation to the geometry module given by moduleId,
279 /// apply reference frame transformation
281 AliMUONGeometryModule* geometry = GetGeometry(moduleId);
284 AliFatal(Form("Geometry %d is not defined", moduleId));
288 TGeoCombiTrans transformation
289 = TGeoCombiTrans(translation, rotation);
291 // Apply frame transform
292 TGeoHMatrix newTransform = ConvertTransform(transformation);
294 // Set new transformation
295 geometry->SetTransformation(newTransform);
298 //______________________________________________________________________________
299 void AliMUONVGeometryBuilder::SetVolume(Int_t moduleId,
300 const TString& volumeName,
303 /// Set volume name, virtuality
305 TString path = GetGeometry(moduleId)->GetVolumePath();
306 // cout << "in AliMUONVGeometryBuilder::SetVolume " << path.Data() << endl;
308 if ( path == "" ) path = "/ALIC_1";
309 path += ComposePath(volumeName, 1);
311 GetGeometry(moduleId)->SetVolumePath(path);
312 GetGeometry(moduleId)->SetIsVirtual(isVirtual);
313 // cout << "... set " << path.Data() << endl;
316 //______________________________________________________________________________
317 void AliMUONVGeometryBuilder::SetMotherVolume(Int_t moduleId,
318 const TString& volumeName)
320 /// Set mother volume name
322 TString motherVolumeName = ComposePath(volumeName, 1);
324 TString path = GetGeometry(moduleId)->GetVolumePath();
325 if ( path == "" ) path = "/ALIC_1";
326 path.Insert(7, motherVolumeName);
328 GetGeometry(moduleId)->SetVolumePath(path);
335 //______________________________________________________________________________
336 void AliMUONVGeometryBuilder::SetReferenceFrame(
337 const TGeoCombiTrans& referenceFrame)
339 /// Set reference frame to builder and to all associated geometry
342 fReferenceFrame = referenceFrame;
344 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
345 AliMUONGeometryModule* geometry
346 = (AliMUONGeometryModule*)fGeometryModules->At(i);
347 AliMUONGeometryEnvelopeStore* envelopeStore
348 = geometry->GetEnvelopeStore();
350 envelopeStore->SetReferenceFrame(referenceFrame);
355 //______________________________________________________________________________
356 void AliMUONVGeometryBuilder::CreateDetElements() const
358 /// Create detection elements and fill their global and
359 /// local transformations from geometry.
361 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
362 AliMUONGeometryModule* geometry
363 = (AliMUONGeometryModule*)fGeometryModules->At(i);
365 const TObjArray* envelopes
366 = geometry->GetEnvelopeStore()->GetEnvelopes();
368 AliMpExMap* detElements
369 = geometry->GetTransformer()->GetDetElementStore();
371 for (Int_t j=0; j<envelopes->GetEntriesFast(); j++) {
372 AliMUONGeometryEnvelope* envelope
373 = (AliMUONGeometryEnvelope*)envelopes->At(j);
375 // skip envelope not corresponding to detection element
376 if ( envelope->GetUniqueID() == 0) continue;
379 Int_t detElemId = envelope->GetUniqueID();
381 // Compose full volume path
382 TString volPath = geometry->GetVolumePath();
383 volPath += ComposePath(envelope->GetName(), envelope->GetCopyNo());
385 // Create detection element
386 AliMUONGeometryDetElement* detElement
387 = new AliMUONGeometryDetElement(detElemId, volPath);
388 detElements->Add(detElemId, detElement);
390 // Compose local transformation
391 const TGeoCombiTrans* transform = envelope->GetTransformation();
392 // Apply frame transform
393 TGeoHMatrix localTransform = ConvertDETransform(*transform);
394 detElement->SetLocalTransformation(localTransform);
396 // Compose global transformation
397 TGeoHMatrix globalTransform
398 = AliMUONGeometryBuilder::Multiply(
399 (*geometry->GetTransformer()->GetTransformation()),
402 // Set the global transformation to detection element
403 detElement->SetGlobalTransformation(globalTransform);
408 //_____ _________________________________________________________________________
409 void AliMUONVGeometryBuilder::RebuildSVMaps(Bool_t withEnvelopes) const
411 /// Clear the SV maps in memory and fill them from defined geometry.
413 for (Int_t i=0; i<fGeometryModules->GetEntriesFast(); i++) {
414 AliMUONGeometryModule* geometry
415 = (AliMUONGeometryModule*)fGeometryModules->At(i);
418 geometry->GetSVMap()->Clear();
420 // Fill the map from geometry
421 const TObjArray* envelopes
422 = geometry->GetEnvelopeStore()->GetEnvelopes();
424 for (Int_t j=0; j<envelopes->GetEntriesFast(); j++) {
425 AliMUONGeometryEnvelope* envelope
426 = (AliMUONGeometryEnvelope*)envelopes->At(j);
428 // skip envelope not corresponding to detection element
429 if ( envelope->GetUniqueID() == 0 ) continue;
431 // Get volume path of detection element
432 AliMUONGeometryDetElement* detElement
433 = geometry->GetTransformer()->GetDetElement(envelope->GetUniqueID());
434 std::string path0 = detElement->GetVolumePath().Data();
436 if ( ! withEnvelopes && geometry->IsVirtual() ) {
437 std::string vName = geometry->GetTransformer()->GetVolumeName().Data();
438 std::string vPath = ComposePath(vName, 1).Data();
439 path0.erase(path0.find(vPath), vPath.size());
442 if ( ! withEnvelopes && envelope->IsVirtual()) {
443 std::string eName = envelope->GetName();
444 std::string ePath = ComposePath(eName, envelope->GetCopyNo()).Data();
445 path0.erase(path0.find(ePath), ePath.size());
448 if ( ! envelope->IsVirtual() )
449 MapSV(path0, envelope->GetName(), envelope->GetUniqueID());
451 for (Int_t k=0; k<envelope->GetConstituents()->GetEntriesFast(); k++) {
452 AliMUONGeometryConstituent* constituent
453 = (AliMUONGeometryConstituent*)envelope->GetConstituents()->At(k);
454 TString path = path0;
455 path += ComposePath(constituent->GetName(), constituent->GetCopyNo());
456 MapSV(path, constituent->GetName(), envelope->GetUniqueID());