]>
Commit | Line | Data |
---|---|---|
1 | /************************************************************************** | |
2 | * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. * | |
3 | * SigmaEffect_thetadegrees * | |
4 | * Author: The ALICE Off-line Project. * | |
5 | * Contributors are mentioned in the code where appropriate. * | |
6 | * * | |
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 purpeateose. It is * | |
13 | * provided "as is" without express or implied warranty. * | |
14 | **************************************************************************/ | |
15 | ||
16 | // $Id$ | |
17 | ||
18 | //----------------------------------------------------------------------------- | |
19 | // Class AliMUONGeometryTransformer | |
20 | // ---------------------------- | |
21 | // Top container class for geometry transformations | |
22 | // Author: Ivana Hrivnacova, IPN Orsay | |
23 | //----------------------------------------------------------------------------- | |
24 | ||
25 | #include "AliMUONGeometryTransformer.h" | |
26 | #include "AliMUONGeometryModuleTransformer.h" | |
27 | #include "AliMUONGeometryDetElement.h" | |
28 | #include "AliMUONGeometryBuilder.h" | |
29 | ||
30 | #include "AliMpDEManager.h" | |
31 | #include "AliMpConstants.h" | |
32 | #include "AliMpExMap.h" | |
33 | #include "AliMpCDB.h" | |
34 | #include "AliMpArea.h" | |
35 | #include <float.h> | |
36 | #include "AliMpVPadIterator.h" | |
37 | #include "AliMpPad.h" | |
38 | #include "AliMpDEIterator.h" | |
39 | #include <TVector2.h> | |
40 | #include "AliMpVSegmentation.h" | |
41 | #include "AliMpSegmentation.h" | |
42 | #include "AliMpExMapIterator.h" | |
43 | #include "AliLog.h" | |
44 | #include "AliAlignObjMatrix.h" | |
45 | #include "AliAlignObj.h" | |
46 | ||
47 | #include <Riostream.h> | |
48 | #include <TSystem.h> | |
49 | #include <TClonesArray.h> | |
50 | #include <TGeoManager.h> | |
51 | #include <TGeoPhysicalNode.h> | |
52 | #include <TFile.h> | |
53 | #include <TString.h> | |
54 | ||
55 | #include <sstream> | |
56 | ||
57 | /// \cond CLASSIMP | |
58 | ClassImp(AliMUONGeometryTransformer) | |
59 | /// \endcond | |
60 | ||
61 | const TString AliMUONGeometryTransformer::fgkDefaultDetectorName = "MUON"; | |
62 | ||
63 | //______________________________________________________________________________ | |
64 | AliMUONGeometryTransformer::AliMUONGeometryTransformer() | |
65 | ||
66 | : TObject(), | |
67 | fDetectorName(fgkDefaultDetectorName), | |
68 | fModuleTransformers(0), | |
69 | fMisAlignArray(0), | |
70 | fDEAreas(0x0) | |
71 | { | |
72 | /// Standard constructor | |
73 | ||
74 | // Create array for geometry modules | |
75 | fModuleTransformers = new TObjArray(100); | |
76 | fModuleTransformers->SetOwner(true); | |
77 | } | |
78 | ||
79 | //______________________________________________________________________________ | |
80 | AliMUONGeometryTransformer::AliMUONGeometryTransformer(TRootIOCtor* /*ioCtor*/) | |
81 | : TObject(), | |
82 | fDetectorName(), | |
83 | fModuleTransformers(0), | |
84 | fMisAlignArray(0), | |
85 | fDEAreas(0x0) | |
86 | { | |
87 | /// Default constructor | |
88 | } | |
89 | ||
90 | //______________________________________________________________________________ | |
91 | AliMUONGeometryTransformer::~AliMUONGeometryTransformer() | |
92 | { | |
93 | /// Destructor | |
94 | ||
95 | delete fModuleTransformers; | |
96 | delete fMisAlignArray; | |
97 | delete fDEAreas; | |
98 | } | |
99 | ||
100 | // | |
101 | // private methods | |
102 | // | |
103 | ||
104 | ||
105 | //_____________________________________________________________________________ | |
106 | AliMpArea* | |
107 | AliMUONGeometryTransformer::GetDEArea(Int_t detElemId) const | |
108 | { | |
109 | /// Get area (in global coordinates) covered by a given detection element | |
110 | if (!fDEAreas) | |
111 | { | |
112 | CreateDEAreas(); | |
113 | } | |
114 | return static_cast<AliMpArea*>(fDEAreas->GetValue(detElemId)); | |
115 | } | |
116 | ||
117 | //_____________________________________________________________________________ | |
118 | void | |
119 | AliMUONGeometryTransformer::CreateDEAreas() const | |
120 | { | |
121 | /// Create DE areas | |
122 | ||
123 | fDEAreas = new AliMpExMap; | |
124 | ||
125 | AliMpDEIterator it; | |
126 | ||
127 | it.First(); | |
128 | ||
129 | /// Generate the DE areas in global coordinates | |
130 | ||
131 | while ( !it.IsDone() ) | |
132 | { | |
133 | Int_t detElemId = it.CurrentDEId(); | |
134 | ||
135 | if ( !HasDE(detElemId) ) continue; | |
136 | ||
137 | const AliMpVSegmentation* seg = AliMpSegmentation::Instance()->GetMpSegmentation(detElemId,AliMp::kCath0); | |
138 | ||
139 | Double_t xg,yg,zg; | |
140 | ||
141 | AliMp::StationType stationType = AliMpDEManager::GetStationType(detElemId); | |
142 | ||
143 | Double_t xl(0.0), yl(0.0), zl(0.0); | |
144 | Double_t dx(seg->GetDimensionX()); | |
145 | Double_t dy(seg->GetDimensionY()); | |
146 | ||
147 | if ( stationType == AliMp::kStation12 ) | |
148 | { | |
149 | Double_t xmin(FLT_MAX); | |
150 | Double_t xmax(-FLT_MAX); | |
151 | Double_t ymin(FLT_MAX); | |
152 | Double_t ymax(-FLT_MAX); | |
153 | ||
154 | for ( Int_t icathode = 0; icathode < 2; ++icathode ) | |
155 | { | |
156 | const AliMpVSegmentation* cathode | |
157 | = AliMpSegmentation::Instance()->GetMpSegmentation(detElemId,AliMp::GetCathodType(icathode)); | |
158 | ||
159 | AliMpVPadIterator* itp = cathode->CreateIterator(); | |
160 | ||
161 | itp->First(); | |
162 | ||
163 | while ( !itp->IsDone() ) | |
164 | { | |
165 | AliMpPad pad = itp->CurrentItem(); | |
166 | AliMpArea a(pad.GetPositionX(),pad.GetPositionY(), | |
167 | pad.GetDimensionX(), pad.GetDimensionY()); | |
168 | xmin = TMath::Min(xmin,a.LeftBorder()); | |
169 | xmax = TMath::Max(xmax,a.RightBorder()); | |
170 | ymin = TMath::Min(ymin,a.DownBorder()); | |
171 | ymax = TMath::Max(ymax,a.UpBorder()); | |
172 | itp->Next(); | |
173 | } | |
174 | ||
175 | delete itp; | |
176 | } | |
177 | ||
178 | xl = (xmin+xmax)/2.0; | |
179 | yl = (ymin+ymax)/2.0; | |
180 | dx = (xmax-xmin)/2.0; | |
181 | dy = (ymax-ymin)/2.0; | |
182 | ||
183 | Local2Global(detElemId,xl,yl,zl,xg,yg,zg); | |
184 | } | |
185 | else | |
186 | { | |
187 | Local2Global(detElemId,xl,yl,zl,xg,yg,zg); | |
188 | } | |
189 | ||
190 | fDEAreas->Add(detElemId,new AliMpArea(xg,yg,dx,dy)); | |
191 | ||
192 | it.Next(); | |
193 | } | |
194 | } | |
195 | ||
196 | //_____________________________________________________________________________ | |
197 | Bool_t AliMUONGeometryTransformer::LoadMapping() const | |
198 | { | |
199 | /// Load mapping from CDB | |
200 | ||
201 | if ( ! AliMpCDB::LoadMpSegmentation() ) | |
202 | { | |
203 | AliFatal("Could not access mapping from OCDB !"); | |
204 | return false; | |
205 | } | |
206 | ||
207 | return true; | |
208 | } | |
209 | ||
210 | //_____________________________________________________________________________ | |
211 | AliMUONGeometryModuleTransformer* | |
212 | AliMUONGeometryTransformer::GetModuleTransformerNonConst( | |
213 | Int_t index, Bool_t warn) const | |
214 | { | |
215 | /// Return the geometry module specified by index | |
216 | ||
217 | if (index < 0 || index >= fModuleTransformers->GetEntriesFast()) { | |
218 | if (warn) { | |
219 | AliWarningStream() | |
220 | << "Index: " << index << " outside limits" << std::endl; | |
221 | } | |
222 | return 0; | |
223 | } | |
224 | ||
225 | return (AliMUONGeometryModuleTransformer*) fModuleTransformers->At(index); | |
226 | } | |
227 | ||
228 | //______________________________________________________________________________ | |
229 | TGeoHMatrix AliMUONGeometryTransformer::GetTransform( | |
230 | Double_t x, Double_t y, Double_t z, | |
231 | Double_t a1, Double_t a2, Double_t a3, | |
232 | Double_t a4, Double_t a5, Double_t a6) const | |
233 | { | |
234 | /// Build the transformation from the given parameters | |
235 | ||
236 | // Compose transform | |
237 | return TGeoCombiTrans(TGeoTranslation(x, y, z), | |
238 | TGeoRotation("rot", a1, a2, a3, a4, a5, a6)); | |
239 | } | |
240 | ||
241 | ||
242 | //______________________________________________________________________________ | |
243 | void AliMUONGeometryTransformer::FillModuleTransform(Int_t moduleId, | |
244 | Double_t x, Double_t y, Double_t z, | |
245 | Double_t a1, Double_t a2, Double_t a3, | |
246 | Double_t a4, Double_t a5, Double_t a6) | |
247 | { | |
248 | /// Fill the transformation of the module. | |
249 | ||
250 | AliMUONGeometryModuleTransformer* moduleTransformer | |
251 | = GetModuleTransformerNonConst(moduleId, false); | |
252 | ||
253 | if ( !moduleTransformer) { | |
254 | AliErrorStream() | |
255 | << "Module " << moduleId << " has not volume path defined." << endl; | |
256 | } | |
257 | ||
258 | // Build the transformation from the parameters | |
259 | TGeoHMatrix transform | |
260 | = GetTransform(x, y, z, a1, a2, a3, a4, a5, a6); | |
261 | ||
262 | moduleTransformer->SetTransformation(transform); | |
263 | } | |
264 | ||
265 | //______________________________________________________________________________ | |
266 | void AliMUONGeometryTransformer::FillDetElemTransform( | |
267 | Int_t detElemId, | |
268 | Double_t x, Double_t y, Double_t z, | |
269 | Double_t a1, Double_t a2, Double_t a3, | |
270 | Double_t a4, Double_t a5, Double_t a6) | |
271 | { | |
272 | /// Fill the transformation of the detection element. | |
273 | ||
274 | // Module Id | |
275 | Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId); | |
276 | ||
277 | // Get module transformer | |
278 | const AliMUONGeometryModuleTransformer* kModuleTransformer | |
279 | = GetModuleTransformer(moduleId); | |
280 | ||
281 | if ( ! kModuleTransformer ) { | |
282 | AliFatal(Form("Module transformer not defined, detElemId: %d", detElemId)); | |
283 | return; | |
284 | } | |
285 | ||
286 | // Get detection element | |
287 | AliMUONGeometryDetElement* detElement | |
288 | = kModuleTransformer->GetDetElement(detElemId); | |
289 | ||
290 | if ( ! detElement ) { | |
291 | AliFatal(Form("Det element %d has not volume path defined", detElemId)); | |
292 | return; | |
293 | } | |
294 | ||
295 | // Build the transformation from the parameters | |
296 | TGeoHMatrix localTransform | |
297 | = GetTransform(x, y, z, a1, a2, a3, a4, a5, a6); | |
298 | detElement->SetLocalTransformation(localTransform); | |
299 | ||
300 | // Compute global transformation | |
301 | TGeoHMatrix globalTransform | |
302 | = AliMUONGeometryBuilder::Multiply( | |
303 | *kModuleTransformer->GetTransformation(), | |
304 | localTransform ); | |
305 | detElement->SetGlobalTransformation(globalTransform); | |
306 | } | |
307 | ||
308 | //______________________________________________________________________________ | |
309 | TString AliMUONGeometryTransformer::ReadModuleTransforms(ifstream& in) | |
310 | { | |
311 | /// Read and fill modules transformations from the stream. | |
312 | /// Return true, if reading finished correctly. | |
313 | ||
314 | TString key(AliMUONGeometryModuleTransformer::GetModuleNamePrefix()); | |
315 | while ( key == AliMUONGeometryModuleTransformer::GetModuleNamePrefix() ) { | |
316 | Int_t id; | |
317 | Double_t x, y, z; | |
318 | Double_t a1, a2, a3, a4, a5, a6; | |
319 | TString dummy; | |
320 | ||
321 | in >> id; | |
322 | in >> dummy; | |
323 | in >> x; | |
324 | in >> y; | |
325 | in >> z; | |
326 | in >> dummy; | |
327 | in >> a1; | |
328 | in >> a2; | |
329 | in >> a3; | |
330 | in >> a4; | |
331 | in >> a5; | |
332 | in >> a6; | |
333 | ||
334 | //cout << "moduleId=" << id << " " | |
335 | // << "position= " << x << ", " << y << ", " << z << " " | |
336 | // << "rotation= " << a1 << ", " << a2 << ", " << a3 << ", " | |
337 | // << a4 << ", " << a5 << ", " << a6 | |
338 | // << endl; | |
339 | ||
340 | // Fill data | |
341 | FillModuleTransform(id, x, y, z, a1, a2, a3, a4, a5, a6); | |
342 | ||
343 | // Go to next line | |
344 | in >> key; | |
345 | } | |
346 | ||
347 | return key; | |
348 | } | |
349 | ||
350 | //______________________________________________________________________________ | |
351 | TString AliMUONGeometryTransformer::ReadDetElemTransforms(ifstream& in) | |
352 | { | |
353 | /// Read detection elements transformations from the stream. | |
354 | /// Return true, if reading finished correctly. | |
355 | ||
356 | TString key(AliMUONGeometryDetElement::GetDENamePrefix()); | |
357 | while ( key == AliMUONGeometryDetElement::GetDENamePrefix() ) { | |
358 | ||
359 | // Input data | |
360 | Int_t detElemId; | |
361 | Double_t x, y, z; | |
362 | Double_t a1, a2, a3, a4, a5, a6; | |
363 | TString dummy; | |
364 | ||
365 | in >> detElemId; | |
366 | in >> dummy; | |
367 | in >> x; | |
368 | in >> y; | |
369 | in >> z; | |
370 | in >> dummy; | |
371 | in >> a1; | |
372 | in >> a2; | |
373 | in >> a3; | |
374 | in >> a4; | |
375 | in >> a5; | |
376 | in >> a6; | |
377 | ||
378 | //cout << "detElemId=" << detElemId << " " | |
379 | // << "position= " << x << ", " << y << ", " << z << " " | |
380 | // << "rotation= " << a1 << ", " << a2 << ", " << a3 << ", " | |
381 | // << a4 << ", " << a5 << ", " << a6 | |
382 | // << endl; | |
383 | ||
384 | // Fill data | |
385 | FillDetElemTransform(detElemId, x, y, z, a1, a2, a3, a4, a5, a6); | |
386 | ||
387 | // Go to next line | |
388 | in >> key; | |
389 | } | |
390 | ||
391 | return key; | |
392 | } | |
393 | ||
394 | //______________________________________________________________________________ | |
395 | Bool_t | |
396 | AliMUONGeometryTransformer::ReadTransformations(const TString& fileName) | |
397 | { | |
398 | /// Read transformations from a file. | |
399 | /// Return true, if reading finished correctly. | |
400 | ||
401 | // File path | |
402 | TString filePath = gSystem->Getenv("ALICE_ROOT"); | |
403 | filePath += "/MUON/data/"; | |
404 | filePath += fileName; | |
405 | ||
406 | // Open input file | |
407 | ifstream in(filePath, ios::in); | |
408 | if (!in) { | |
409 | cerr << filePath << endl; | |
410 | AliFatal("File not found."); | |
411 | return false; | |
412 | } | |
413 | ||
414 | TString key; | |
415 | in >> key; | |
416 | while ( !in.eof() ) { | |
417 | if ( key == AliMUONGeometryModuleTransformer::GetModuleNamePrefix() ) | |
418 | key = ReadModuleTransforms(in); | |
419 | else if ( key == AliMUONGeometryDetElement::GetDENamePrefix() ) | |
420 | key = ReadDetElemTransforms(in); | |
421 | else { | |
422 | AliFatal(Form("%s key not recognized", key.Data())); | |
423 | return false; | |
424 | } | |
425 | } | |
426 | ||
427 | return true; | |
428 | } | |
429 | ||
430 | //______________________________________________________________________________ | |
431 | void AliMUONGeometryTransformer::WriteTransform(ofstream& out, | |
432 | const TGeoMatrix* transform) const | |
433 | { | |
434 | /// Write given transformation | |
435 | ||
436 | out << " pos: "; | |
437 | const Double_t* xyz = transform->GetTranslation(); | |
438 | out << setw(10) << setprecision(4) << xyz[0] << " " | |
439 | << setw(10) << setprecision(4) << xyz[1] << " " | |
440 | << setw(10) << setprecision(4) << xyz[2]; | |
441 | ||
442 | out << " rot: "; | |
443 | const Double_t* rm = transform->GetRotationMatrix(); | |
444 | TGeoRotation rotation; | |
445 | rotation.SetMatrix(const_cast<Double_t*>(rm)); | |
446 | Double_t a1, a2, a3, a4, a5, a6; | |
447 | rotation.GetAngles(a1, a2, a3, a4, a5, a6); | |
448 | ||
449 | out << setw(8) << setprecision(4) << a1 << " " | |
450 | << setw(8) << setprecision(4) << a2 << " " | |
451 | << setw(8) << setprecision(4) << a3 << " " | |
452 | << setw(8) << setprecision(4) << a4 << " " | |
453 | << setw(8) << setprecision(4) << a5 << " " | |
454 | << setw(8) << setprecision(4) << a6 << " " << endl; | |
455 | } | |
456 | ||
457 | //______________________________________________________________________________ | |
458 | void AliMUONGeometryTransformer::WriteModuleTransforms(ofstream& out) const | |
459 | { | |
460 | /// Write module transformations for all module transformers | |
461 | ||
462 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
463 | AliMUONGeometryModuleTransformer* moduleTransformer | |
464 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
465 | const TGeoMatrix* transform | |
466 | = moduleTransformer->GetTransformation(); | |
467 | ||
468 | // Write data on out | |
469 | out << AliMUONGeometryModuleTransformer::GetModuleNamePrefix() << " " | |
470 | << setw(4) << moduleTransformer->GetModuleId(); | |
471 | ||
472 | WriteTransform(out, transform); | |
473 | } | |
474 | out << endl; | |
475 | } | |
476 | ||
477 | //______________________________________________________________________________ | |
478 | void AliMUONGeometryTransformer::WriteDetElemTransforms(ofstream& out) const | |
479 | { | |
480 | /// Write detection element transformations for all detection elements in all | |
481 | /// module transformers | |
482 | ||
483 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
484 | AliMUONGeometryModuleTransformer* moduleTransformer | |
485 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
486 | AliMpExMap* detElements = moduleTransformer->GetDetElementStore(); | |
487 | TIter next(detElements->CreateIterator()); | |
488 | AliMUONGeometryDetElement* detElement; | |
489 | while ( ( detElement = static_cast<AliMUONGeometryDetElement*>(next()) ) ) | |
490 | { | |
491 | const TGeoMatrix* transform | |
492 | = detElement->GetLocalTransformation(); | |
493 | ||
494 | // Write data on out | |
495 | out << AliMUONGeometryDetElement::GetDENamePrefix() << " " | |
496 | << setw(4) << detElement->GetId(); | |
497 | ||
498 | WriteTransform(out, transform); | |
499 | } | |
500 | out << endl; | |
501 | } | |
502 | } | |
503 | ||
504 | //______________________________________________________________________________ | |
505 | TString AliMUONGeometryTransformer::GetModuleSymName(Int_t moduleId) const | |
506 | { | |
507 | /// Return the module symbolic name (use for alignment) | |
508 | ||
509 | return "/" + fDetectorName + "/" | |
510 | + AliMUONGeometryModuleTransformer::GetModuleName(moduleId); | |
511 | } | |
512 | ||
513 | //______________________________________________________________________________ | |
514 | TString AliMUONGeometryTransformer::GetDESymName(Int_t detElemId) const | |
515 | { | |
516 | /// Return the detection element symbolic name (used for alignment) | |
517 | ||
518 | // Module Id | |
519 | Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId); | |
520 | ||
521 | return GetModuleSymName(moduleId) + "/" | |
522 | + AliMUONGeometryDetElement::GetDEName(detElemId); | |
523 | } | |
524 | ||
525 | // | |
526 | // public functions | |
527 | // | |
528 | ||
529 | //______________________________________________________________________________ | |
530 | Bool_t | |
531 | AliMUONGeometryTransformer::LoadTransformations() | |
532 | { | |
533 | /// Load transformations for defined modules and detection elements | |
534 | /// using AliGeomManager | |
535 | ||
536 | if ( ! AliGeomManager::GetGeometry() ) { | |
537 | AliFatal("Geometry has to be laoded in AliGeomManager first."); | |
538 | return false; | |
539 | } | |
540 | ||
541 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
542 | AliMUONGeometryModuleTransformer* moduleTransformer | |
543 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
544 | ||
545 | // Module symbolic name | |
546 | TString symname = GetModuleSymName(moduleTransformer->GetModuleId()); | |
547 | ||
548 | // Set matrix from physical node | |
549 | TGeoHMatrix* matrix = AliGeomManager::GetMatrix(symname); | |
550 | if ( ! matrix ) { | |
551 | AliErrorStream() << "Geometry module matrix not found." << endl; | |
552 | return false; | |
553 | } | |
554 | moduleTransformer->SetTransformation(*matrix); | |
555 | ||
556 | // Loop over detection elements | |
557 | AliMpExMap* detElements = moduleTransformer->GetDetElementStore(); | |
558 | TIter next(detElements->CreateIterator()); | |
559 | AliMUONGeometryDetElement* detElement; | |
560 | ||
561 | while ( ( detElement = static_cast<AliMUONGeometryDetElement*>(next()) ) ) | |
562 | { | |
563 | // Det element symbolic name | |
564 | TString symnameDE = GetDESymName(detElement->GetId()); | |
565 | ||
566 | // Set global matrix from physical node | |
567 | TGeoHMatrix* globalMatrix = AliGeomManager::GetMatrix(symnameDE); | |
568 | if ( ! globalMatrix ) { | |
569 | AliErrorStream() << "Detection element matrix not found." << endl; | |
570 | return false; | |
571 | } | |
572 | detElement->SetGlobalTransformation(*globalMatrix, false); | |
573 | ||
574 | // Set local matrix | |
575 | TGeoHMatrix localMatrix = | |
576 | AliMUONGeometryBuilder::Multiply( | |
577 | (*matrix).Inverse(), (*globalMatrix) ); | |
578 | detElement->SetLocalTransformation(localMatrix, false); | |
579 | } | |
580 | } | |
581 | return true; | |
582 | } | |
583 | ||
584 | //______________________________________________________________________________ | |
585 | Bool_t | |
586 | AliMUONGeometryTransformer::LoadGeometryData(const TString& fileName) | |
587 | { | |
588 | /// Read geometry data either from ASCII file with transformations or | |
589 | /// from root geometry file (if fileName has ".root" extension) | |
590 | ||
591 | CreateModules(); | |
592 | ||
593 | // Get file extension | |
594 | std::string fileName2 = fileName.Data(); | |
595 | std::string rootExt = fileName2.substr(fileName2.size()-5, fileName2.size()); | |
596 | ||
597 | if ( rootExt != ".root" ) | |
598 | return ReadTransformations(fileName); | |
599 | else { | |
600 | // Load root geometry | |
601 | AliGeomManager::LoadGeometry(fileName.Data()); | |
602 | return LoadTransformations(); | |
603 | } | |
604 | } | |
605 | ||
606 | //______________________________________________________________________________ | |
607 | Bool_t | |
608 | AliMUONGeometryTransformer::LoadGeometryData() | |
609 | { | |
610 | /// Load geometry data from already loaded Root geometry using AliGeomManager | |
611 | ||
612 | if ( ! AliGeomManager::GetGeometry() ) { | |
613 | AliErrorStream() << "Geometry has not been loaded in AliGeomManager" << endl; | |
614 | return false; | |
615 | } | |
616 | ||
617 | CreateModules(); | |
618 | ||
619 | return LoadTransformations(); | |
620 | } | |
621 | ||
622 | //______________________________________________________________________________ | |
623 | Bool_t | |
624 | AliMUONGeometryTransformer::WriteTransformations(const TString& fileName) const | |
625 | { | |
626 | /// Write transformations into a file. | |
627 | /// Return true, if writing finished correctly. | |
628 | ||
629 | // No writing | |
630 | // if builder is not associated with any geometry module | |
631 | if (fModuleTransformers->GetEntriesFast() == 0) return false; | |
632 | ||
633 | // File path | |
634 | TString filePath = gSystem->Getenv("ALICE_ROOT"); | |
635 | filePath += "/MUON/data/"; | |
636 | filePath += fileName; | |
637 | ||
638 | // Open output file | |
639 | ofstream out(filePath, ios::out); | |
640 | if (!out) { | |
641 | cerr << filePath << endl; | |
642 | AliError("File not found."); | |
643 | return false; | |
644 | } | |
645 | #if !defined (__DECCXX) | |
646 | out.setf(std::ios::fixed); | |
647 | #endif | |
648 | WriteModuleTransforms(out); | |
649 | WriteDetElemTransforms(out); | |
650 | ||
651 | return true; | |
652 | } | |
653 | ||
654 | //______________________________________________________________________________ | |
655 | Bool_t | |
656 | AliMUONGeometryTransformer::WriteMisAlignmentData(const TString& fileName) const | |
657 | { | |
658 | /// Write misalignment data into a file | |
659 | /// Return true, if writing finished correctly. | |
660 | ||
661 | // No writing | |
662 | // if builder is not associated with any geometry module | |
663 | if ( fModuleTransformers->GetEntriesFast() == 0 ) { | |
664 | AliWarningStream() << "No geometry modules defined." << endl; | |
665 | return false; | |
666 | } | |
667 | ||
668 | // No writing | |
669 | // if builder has no mis-alignment data | |
670 | if ( ! fMisAlignArray ) { | |
671 | AliWarningStream() << "No mis-alignment data defined." << endl; | |
672 | return false; | |
673 | } | |
674 | ||
675 | // File path | |
676 | TString filePath = gSystem->Getenv("ALICE_ROOT"); | |
677 | filePath += "/MUON/data/"; | |
678 | filePath += fileName; | |
679 | ||
680 | // Write mis-alignment data in the root file | |
681 | TFile file(fileName.Data(), "RECREATE"); | |
682 | fMisAlignArray->Write(); | |
683 | file.Close(); | |
684 | ||
685 | return true; | |
686 | } | |
687 | ||
688 | //_____________________________________________________________________________ | |
689 | void AliMUONGeometryTransformer::AddModuleTransformer( | |
690 | AliMUONGeometryModuleTransformer* moduleTransformer) | |
691 | { | |
692 | /// Add the module transformer to the array | |
693 | ||
694 | // Expand the size if not sufficient | |
695 | Int_t moduleId = moduleTransformer->GetModuleId(); | |
696 | if ( moduleId >= fModuleTransformers->GetSize() ) | |
697 | fModuleTransformers->Expand(moduleId+1); | |
698 | ||
699 | fModuleTransformers->AddAt(moduleTransformer, moduleId); | |
700 | } | |
701 | ||
702 | //_____________________________________________________________________________ | |
703 | void AliMUONGeometryTransformer::AddMisAlignModule(Int_t moduleId, | |
704 | const TGeoHMatrix& matrix) | |
705 | { | |
706 | /// Build AliAlignObjMatrix with module ID, its volumePath | |
707 | /// and the given delta transformation matrix | |
708 | ||
709 | if ( ! fMisAlignArray ) | |
710 | fMisAlignArray = new TClonesArray("AliAlignObjMatrix", 200); | |
711 | ||
712 | const AliMUONGeometryModuleTransformer* kTransformer | |
713 | = GetModuleTransformer(moduleId); | |
714 | if ( ! kTransformer ) { | |
715 | AliErrorStream() << "Module " << moduleId << " not found." << endl; | |
716 | return; | |
717 | } | |
718 | ||
719 | // Get unique align object ID | |
720 | Int_t volId = AliGeomManager::LayerToVolUID(AliGeomManager::kMUON, moduleId); | |
721 | ||
722 | // Create mis align matrix | |
723 | TClonesArray& refArray =*fMisAlignArray; | |
724 | Int_t pos = fMisAlignArray->GetEntriesFast(); | |
725 | new (refArray[pos]) AliAlignObjMatrix(GetModuleSymName(moduleId), volId, | |
726 | const_cast<TGeoHMatrix&>(matrix),kTRUE); | |
727 | } | |
728 | ||
729 | //_____________________________________________________________________________ | |
730 | void AliMUONGeometryTransformer::AddMisAlignDetElement(Int_t detElemId, | |
731 | const TGeoHMatrix& matrix) | |
732 | { | |
733 | /// Build AliAlignObjMatrix with detection element ID, its volumePath | |
734 | /// and the given delta transformation matrix | |
735 | ||
736 | if ( ! fMisAlignArray ) | |
737 | fMisAlignArray = new TClonesArray("AliAlignObjMatrix", 200); | |
738 | ||
739 | const AliMUONGeometryDetElement* kDetElement | |
740 | = GetDetElement(detElemId); | |
741 | ||
742 | if ( ! kDetElement ) { | |
743 | AliErrorStream() << "Det element " << detElemId << " not found." << endl; | |
744 | return; | |
745 | } | |
746 | ||
747 | // Get unique align object ID | |
748 | Int_t volId = AliGeomManager::LayerToVolUID(AliGeomManager::kMUON, detElemId); | |
749 | ||
750 | // Create mis align matrix | |
751 | TClonesArray& refArray =*fMisAlignArray; | |
752 | Int_t pos = fMisAlignArray->GetEntriesFast(); | |
753 | new(refArray[pos]) AliAlignObjMatrix(GetDESymName(detElemId), volId, | |
754 | const_cast<TGeoHMatrix&>(matrix),kTRUE); | |
755 | } | |
756 | ||
757 | //______________________________________________________________________________ | |
758 | void AliMUONGeometryTransformer::CreateModules() | |
759 | { | |
760 | /// Create modules and their detection elements using info from mapping; | |
761 | /// but do not fill matrices | |
762 | ||
763 | // Load mapping as its info is used to define modules & DEs | |
764 | LoadMapping(); | |
765 | ||
766 | if ( fModuleTransformers->GetEntriesFast() == 0 ) { | |
767 | // Create modules only if they do not yet exist | |
768 | ||
769 | // Loop over geometry module | |
770 | for (Int_t moduleId = 0; moduleId < AliMpConstants::NofGeomModules(); ++moduleId ) { | |
771 | ||
772 | // Create geometry module transformer | |
773 | AliMUONGeometryModuleTransformer* moduleTransformer | |
774 | = new AliMUONGeometryModuleTransformer(moduleId); | |
775 | AddModuleTransformer(moduleTransformer); | |
776 | } | |
777 | } | |
778 | ||
779 | // Loop over detection elements | |
780 | AliMpDEIterator it; | |
781 | for ( it.First(); ! it.IsDone(); it.Next() ) { | |
782 | ||
783 | Int_t detElemId = it.CurrentDEId(); | |
784 | Int_t moduleId = AliMpDEManager::GetGeomModuleId(detElemId); | |
785 | ||
786 | // Get detection element store | |
787 | AliMpExMap* detElements = | |
788 | GetModuleTransformer(moduleId)->GetDetElementStore(); | |
789 | ||
790 | // Add detection element | |
791 | AliMUONGeometryDetElement* detElement | |
792 | = new AliMUONGeometryDetElement(detElemId); | |
793 | detElements->Add(detElemId, detElement); | |
794 | } | |
795 | } | |
796 | ||
797 | //_____________________________________________________________________________ | |
798 | void AliMUONGeometryTransformer::AddAlignableVolumes() const | |
799 | { | |
800 | /// Set symbolic names and matrices to alignable objects to TGeo | |
801 | ||
802 | if ( ! gGeoManager ) { | |
803 | AliWarning("TGeoManager not defined."); | |
804 | return; | |
805 | } | |
806 | ||
807 | // Modules | |
808 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
809 | AliMUONGeometryModuleTransformer* module | |
810 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
811 | ||
812 | // Set module symbolic name | |
813 | TGeoPNEntry* pnEntry | |
814 | = gGeoManager->SetAlignableEntry(GetModuleSymName(module->GetModuleId()), | |
815 | module->GetVolumePath()); | |
816 | if ( ! pnEntry ) { | |
817 | AliErrorStream() | |
818 | << "Volume path " << module->GetVolumePath().Data() | |
819 | << " for geometry module " << module->GetModuleId() << " " << module | |
820 | << " not found in geometry." << endl; | |
821 | } | |
822 | else { | |
823 | // Set module matrix | |
824 | pnEntry->SetMatrix(new TGeoHMatrix(*module->GetTransformation())); | |
825 | // the matrix will be deleted via TGeoManager | |
826 | } | |
827 | ||
828 | // Detection elements | |
829 | AliMpExMap* detElements = module->GetDetElementStore(); | |
830 | TIter next(detElements->CreateIterator()); | |
831 | AliMUONGeometryDetElement* detElement; | |
832 | ||
833 | while ( ( detElement = static_cast<AliMUONGeometryDetElement*>(next()) ) ) | |
834 | { | |
835 | // Set detection element symbolic name | |
836 | TGeoPNEntry* pnEntryDE | |
837 | = gGeoManager->SetAlignableEntry(GetDESymName(detElement->GetId()), | |
838 | detElement->GetVolumePath()); | |
839 | if ( ! pnEntryDE ) { | |
840 | AliErrorStream() | |
841 | << "Volume path " | |
842 | << detElement->GetVolumePath().Data() | |
843 | << " for detection element " << detElement->GetId() | |
844 | << " not found in geometry." << endl; | |
845 | } | |
846 | else { | |
847 | // Set detection element matrix | |
848 | pnEntryDE->SetMatrix(new TGeoHMatrix(*detElement->GetGlobalTransformation())); | |
849 | // the matrix will be deleted via TGeoManager | |
850 | } | |
851 | } | |
852 | } | |
853 | } | |
854 | ||
855 | //_____________________________________________________________________________ | |
856 | TClonesArray* AliMUONGeometryTransformer::CreateZeroAlignmentData() const | |
857 | { | |
858 | /// Create array with zero alignment data | |
859 | ||
860 | // Create array for zero-alignment objects | |
861 | TClonesArray* array = new TClonesArray("AliAlignObjMatrix", 200); | |
862 | TClonesArray& refArray =*array; | |
863 | array->SetOwner(true); | |
864 | ||
865 | // Identity matrix | |
866 | TGeoHMatrix matrix; | |
867 | ||
868 | // Modules | |
869 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
870 | AliMUONGeometryModuleTransformer* module | |
871 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
872 | ||
873 | Int_t moduleId = module->GetModuleId(); | |
874 | ||
875 | // Align object ID | |
876 | Int_t volId = AliGeomManager::LayerToVolUID(AliGeomManager::kMUON, moduleId); | |
877 | ||
878 | // Create mis align matrix | |
879 | Int_t pos = array->GetEntriesFast(); | |
880 | new (refArray[pos]) AliAlignObjMatrix(GetModuleSymName(moduleId), volId, matrix, kTRUE); | |
881 | } | |
882 | ||
883 | // Detection elements | |
884 | for (Int_t i=0; i<fModuleTransformers->GetEntriesFast(); i++) { | |
885 | AliMUONGeometryModuleTransformer* moduleTransformer | |
886 | = (AliMUONGeometryModuleTransformer*)fModuleTransformers->At(i); | |
887 | ||
888 | AliMpExMap* detElements = moduleTransformer->GetDetElementStore(); | |
889 | TIter next(detElements->CreateIterator()); | |
890 | AliMUONGeometryDetElement* detElement; | |
891 | ||
892 | while ( ( detElement = static_cast<AliMUONGeometryDetElement*>(next()) ) ) | |
893 | { | |
894 | Int_t detElemId = detElement->GetId(); | |
895 | ||
896 | // Align object ID | |
897 | Int_t volId = AliGeomManager::LayerToVolUID(AliGeomManager::kMUON, detElemId); | |
898 | ||
899 | // Create mis align matrix | |
900 | Int_t pos = array->GetEntriesFast(); | |
901 | new (refArray[pos]) AliAlignObjMatrix(GetDESymName(detElemId), volId, matrix, kTRUE); | |
902 | } | |
903 | } | |
904 | ||
905 | return array; | |
906 | } | |
907 | ||
908 | //_____________________________________________________________________________ | |
909 | void AliMUONGeometryTransformer::ClearMisAlignmentData() | |
910 | { | |
911 | /// Clear the array of misalignment data | |
912 | ||
913 | if ( ! fMisAlignArray ) return; | |
914 | ||
915 | fMisAlignArray->Delete(); | |
916 | } | |
917 | ||
918 | //_____________________________________________________________________________ | |
919 | void AliMUONGeometryTransformer::Global2Local(Int_t detElemId, | |
920 | Float_t xg, Float_t yg, Float_t zg, | |
921 | Float_t& xl, Float_t& yl, Float_t& zl) const | |
922 | { | |
923 | /// Transform point from the global reference frame (ALIC) | |
924 | /// to the local reference frame of the detection element specified | |
925 | /// by detElemId. | |
926 | ||
927 | const AliMUONGeometryModuleTransformer* kTransformer | |
928 | = GetModuleTransformerByDEId(detElemId); | |
929 | ||
930 | if (kTransformer) | |
931 | kTransformer->Global2Local(detElemId, xg, yg, zg, xl, yl, zl); | |
932 | } | |
933 | ||
934 | //_____________________________________________________________________________ | |
935 | void AliMUONGeometryTransformer::Global2Local(Int_t detElemId, | |
936 | Double_t xg, Double_t yg, Double_t zg, | |
937 | Double_t& xl, Double_t& yl, Double_t& zl) const | |
938 | { | |
939 | /// Transform point from the global reference frame (ALIC) | |
940 | /// to the local reference frame of the detection element specified | |
941 | /// by detElemId. | |
942 | ||
943 | const AliMUONGeometryModuleTransformer* kTransformer | |
944 | = GetModuleTransformerByDEId(detElemId); | |
945 | ||
946 | if (kTransformer) | |
947 | kTransformer->Global2Local(detElemId, xg, yg, zg, xl, yl, zl); | |
948 | } | |
949 | ||
950 | //_____________________________________________________________________________ | |
951 | void AliMUONGeometryTransformer::Local2Global(Int_t detElemId, | |
952 | Float_t xl, Float_t yl, Float_t zl, | |
953 | Float_t& xg, Float_t& yg, Float_t& zg) const | |
954 | { | |
955 | /// Transform point from the local reference frame of the detection element | |
956 | /// specified by detElemId to the global reference frame (ALIC). | |
957 | ||
958 | const AliMUONGeometryModuleTransformer* kTransformer | |
959 | = GetModuleTransformerByDEId(detElemId); | |
960 | ||
961 | if (kTransformer) | |
962 | kTransformer->Local2Global(detElemId, xl, yl, zl, xg, yg, zg); | |
963 | } | |
964 | ||
965 | //_____________________________________________________________________________ | |
966 | void AliMUONGeometryTransformer::Local2Global(Int_t detElemId, | |
967 | Double_t xl, Double_t yl, Double_t zl, | |
968 | Double_t& xg, Double_t& yg, Double_t& zg) const | |
969 | { | |
970 | /// Transform point from the local reference frame of the detection element | |
971 | /// specified by detElemId to the global reference frame (ALIC). | |
972 | ||
973 | const AliMUONGeometryModuleTransformer* kTransformer | |
974 | = GetModuleTransformerByDEId(detElemId); | |
975 | ||
976 | if (kTransformer) | |
977 | kTransformer->Local2Global(detElemId, xl, yl, zl, xg, yg, zg); | |
978 | } | |
979 | ||
980 | //_____________________________________________________________________________ | |
981 | const AliMUONGeometryModuleTransformer* | |
982 | AliMUONGeometryTransformer::GetModuleTransformer(Int_t index, Bool_t warn) const | |
983 | { | |
984 | /// Return the geometry module transformer specified by index | |
985 | ||
986 | return GetModuleTransformerNonConst(index, warn); | |
987 | } | |
988 | ||
989 | //_____________________________________________________________________________ | |
990 | const AliMUONGeometryModuleTransformer* | |
991 | AliMUONGeometryTransformer::GetModuleTransformerByDEId(Int_t detElemId, | |
992 | Bool_t warn) const | |
993 | { | |
994 | /// Return the geometry module transformer specified by detection element ID | |
995 | ||
996 | // Get module index | |
997 | Int_t index = AliMpDEManager::GetGeomModuleId(detElemId); | |
998 | ||
999 | return GetModuleTransformer(index, warn); | |
1000 | } | |
1001 | ||
1002 | //_____________________________________________________________________________ | |
1003 | const AliMUONGeometryDetElement* | |
1004 | AliMUONGeometryTransformer::GetDetElement(Int_t detElemId, Bool_t warn) const | |
1005 | { | |
1006 | /// Return detection element with given detElemId | |
1007 | ||
1008 | const AliMUONGeometryModuleTransformer* kTransformer | |
1009 | = GetModuleTransformerByDEId(detElemId, warn); | |
1010 | ||
1011 | if (!kTransformer) return 0; | |
1012 | ||
1013 | return kTransformer->GetDetElement(detElemId, warn); | |
1014 | } | |
1015 | ||
1016 | //_____________________________________________________________________________ | |
1017 | Bool_t AliMUONGeometryTransformer::HasDE(Int_t detElemId) const | |
1018 | { | |
1019 | /// Return true if detection element with given detElemId is defined | |
1020 | ||
1021 | const AliMUONGeometryModuleTransformer* kTransformer | |
1022 | = GetModuleTransformerByDEId(detElemId, false); | |
1023 | ||
1024 | if (!kTransformer) return false; | |
1025 | ||
1026 | return ( kTransformer->GetDetElement(detElemId, false) != 0 ); | |
1027 | } | |
1028 | ||
1029 |