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