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 ///////////////////////////////////////////////////////////////////////////////
20 // TRD geometry class //
22 ///////////////////////////////////////////////////////////////////////////////
25 #include <TGeoManager.h>
26 #include <TGeoPhysicalNode.h>
27 #include <TGeoMatrix.h>
30 #include "AliRunLoader.h"
31 #include "AliAlignObj.h"
32 #include "AliAlignObjAngles.h"
36 #include "AliTRDcalibDB.h"
37 #include "AliTRDCommonParam.h"
38 #include "AliTRDgeometry.h"
39 #include "AliTRDpadPlane.h"
41 ClassImp(AliTRDgeometry)
43 //_____________________________________________________________________________
46 // The geometry constants
48 const Int_t AliTRDgeometry::fgkNsect = kNsect;
49 const Int_t AliTRDgeometry::fgkNplan = kNplan;
50 const Int_t AliTRDgeometry::fgkNcham = kNcham;
51 const Int_t AliTRDgeometry::fgkNdet = kNdet;
54 // Dimensions of the detector
57 // Inner and outer radius of the mother volumes
58 const Float_t AliTRDgeometry::fgkRmin = 294.0;
59 const Float_t AliTRDgeometry::fgkRmax = 368.0;
61 // Upper and lower length of the mother volumes
62 const Float_t AliTRDgeometry::fgkZmax1 = 378.35;
63 const Float_t AliTRDgeometry::fgkZmax2 = 302.0;
65 // Parameter of the BTR mother volumes
66 const Float_t AliTRDgeometry::fgkSheight = 77.9;
67 const Float_t AliTRDgeometry::fgkSwidth1 = 94.881;
68 const Float_t AliTRDgeometry::fgkSwidth2 = 122.353;
69 const Float_t AliTRDgeometry::fgkSlenTR1 = 751.0;
70 const Float_t AliTRDgeometry::fgkSlenTR2 = 313.5;
71 const Float_t AliTRDgeometry::fgkSlenTR3 = 159.5;
73 // The super module side plates
74 const Float_t AliTRDgeometry::fgkSMpltT = 0.2;
75 //const Float_t AliTRDgeometry::fgkSMgapT = 0.5;
77 // Height of different chamber parts
79 const Float_t AliTRDgeometry::fgkCraH = 4.8;
81 const Float_t AliTRDgeometry::fgkCdrH = 3.0;
82 // Amplification region
83 const Float_t AliTRDgeometry::fgkCamH = 0.7;
85 const Float_t AliTRDgeometry::fgkCroH = 2.316;
87 const Float_t AliTRDgeometry::fgkCH = AliTRDgeometry::fgkCraH
88 + AliTRDgeometry::fgkCdrH
89 + AliTRDgeometry::fgkCamH
90 + AliTRDgeometry::fgkCroH;
92 // Vertical spacing of the chambers
93 const Float_t AliTRDgeometry::fgkVspace = 1.784;
95 // Horizontal spacing of the chambers
96 const Float_t AliTRDgeometry::fgkHspace = 2.0;
98 // Radial distance of the first ROC to the outer plates of the SM
99 const Float_t AliTRDgeometry::fgkVrocsm = 1.2;
101 // Thicknesses of different parts of the chamber frame
102 // Lower aluminum frame
103 const Float_t AliTRDgeometry::fgkCalT = 0.3;
104 // Lower G10 frame sides
105 const Float_t AliTRDgeometry::fgkCclsT = 0.3;
106 // Lower G10 frame front
107 const Float_t AliTRDgeometry::fgkCclfT = 1.0;
109 const Float_t AliTRDgeometry::fgkCcuT = 0.9;
111 const Float_t AliTRDgeometry::fgkCauT = 1.5;
113 // Additional width of the readout chamber frames
114 const Float_t AliTRDgeometry::fgkCroW = 0.9;
116 // Difference of outer chamber width and pad plane width
117 //const Float_t AliTRDgeometry::fgkCpadW = 1.0;
118 const Float_t AliTRDgeometry::fgkCpadW = 0.0;
119 const Float_t AliTRDgeometry::fgkRpadW = 1.0;
122 // Thickness of the the material layers
124 const Float_t AliTRDgeometry::fgkRaThick = 0.3646;
125 const Float_t AliTRDgeometry::fgkMyThick = 0.005;
126 const Float_t AliTRDgeometry::fgkDrThick = AliTRDgeometry::fgkCdrH;
127 const Float_t AliTRDgeometry::fgkAmThick = AliTRDgeometry::fgkCamH;
128 const Float_t AliTRDgeometry::fgkXeThick = AliTRDgeometry::fgkDrThick
129 + AliTRDgeometry::fgkAmThick;
130 const Float_t AliTRDgeometry::fgkCuThick = 0.0072;
131 const Float_t AliTRDgeometry::fgkSuThick = 0.06;
132 const Float_t AliTRDgeometry::fgkFeThick = 0.0044;
133 const Float_t AliTRDgeometry::fgkCoThick = 0.02;
134 const Float_t AliTRDgeometry::fgkWaThick = 0.02;
135 const Float_t AliTRDgeometry::fgkRcThick = 0.0058;
136 const Float_t AliTRDgeometry::fgkRpThick = 0.0632;
139 // Position of the material layers
141 const Float_t AliTRDgeometry::fgkRaZpos = -1.50;
142 const Float_t AliTRDgeometry::fgkMyZpos = 0.895;
143 const Float_t AliTRDgeometry::fgkDrZpos = 2.4;
144 const Float_t AliTRDgeometry::fgkAmZpos = 0.0;
145 const Float_t AliTRDgeometry::fgkCuZpos = -0.9995;
146 const Float_t AliTRDgeometry::fgkSuZpos = 0.0000;
147 const Float_t AliTRDgeometry::fgkFeZpos = 0.0322;
148 const Float_t AliTRDgeometry::fgkCoZpos = 0.97;
149 const Float_t AliTRDgeometry::fgkWaZpos = 0.99;
150 const Float_t AliTRDgeometry::fgkRcZpos = 1.04;
151 const Float_t AliTRDgeometry::fgkRpZpos = 1.0;
153 const Double_t AliTRDgeometry::fgkTime0Base = Rmin() + CraHght() + CdrHght() + CamHght()/2.;
154 const Float_t AliTRDgeometry::fgkTime0[6] = { fgkTime0Base + 0 * (Cheight() + Cspace()),
155 fgkTime0Base + 1 * (Cheight() + Cspace()),
156 fgkTime0Base + 2 * (Cheight() + Cspace()),
157 fgkTime0Base + 3 * (Cheight() + Cspace()),
158 fgkTime0Base + 4 * (Cheight() + Cspace()),
159 fgkTime0Base + 5 * (Cheight() + Cspace()) };
161 //_____________________________________________________________________________
162 AliTRDgeometry::AliTRDgeometry()
165 ,fMatrixCorrectionArray(0)
170 // AliTRDgeometry default constructor
177 //_____________________________________________________________________________
178 AliTRDgeometry::AliTRDgeometry(const AliTRDgeometry &g)
180 ,fMatrixArray(g.fMatrixArray)
181 ,fMatrixCorrectionArray(g.fMatrixCorrectionArray)
182 ,fMatrixGeo(g.fMatrixGeo)
186 // AliTRDgeometry copy constructor
193 //_____________________________________________________________________________
194 AliTRDgeometry::~AliTRDgeometry()
197 // AliTRDgeometry destructor
201 delete fMatrixCorrectionArray;
205 //_____________________________________________________________________________
206 AliTRDgeometry &AliTRDgeometry::operator=(const AliTRDgeometry &g)
209 // Assignment operator
212 if (this != &g) Init();
217 //_____________________________________________________________________________
218 void AliTRDgeometry::Init()
221 // Initializes the geometry parameter
223 // The maximum number of pads
224 // and the position of pad 0,0,0
226 // chambers seen from the top:
227 // +----------------------------+
233 // +----------------------------+ +------>
235 // chambers seen from the side: ^
236 // +----------------------------+ drift|
239 // +----------------------------+ +------>
242 // IMPORTANT: time bin 0 is now the first one in the drift region
243 // closest to the readout !!!
250 // The outer width of the chambers
258 // The outer lengths of the chambers
259 // Includes the spacings between the chambers!
260 Float_t length[kNplan][kNcham] = { { 124.0, 124.0, 110.0, 124.0, 124.0 }
261 , { 124.0, 124.0, 110.0, 124.0, 124.0 }
262 , { 131.0, 131.0, 110.0, 131.0, 131.0 }
263 , { 138.0, 138.0, 110.0, 138.0, 138.0 }
264 , { 145.0, 145.0, 110.0, 145.0, 145.0 }
265 , { 147.0, 147.0, 110.0, 147.0, 147.0 } };
267 for (icham = 0; icham < kNcham; icham++) {
268 for (iplan = 0; iplan < kNplan; iplan++) {
269 fClength[iplan][icham] = length[iplan][icham];
273 // The rotation matrix elements
275 for (isect = 0; isect < fgkNsect; isect++) {
276 phi = -2.0 * TMath::Pi() / (Float_t) fgkNsect * ((Float_t) isect + 0.5);
277 fRotA11[isect] = TMath::Cos(phi);
278 fRotA12[isect] = TMath::Sin(phi);
279 fRotA21[isect] = TMath::Sin(phi);
280 fRotA22[isect] = TMath::Cos(phi);
282 fRotB11[isect] = TMath::Cos(phi);
283 fRotB12[isect] = TMath::Sin(phi);
284 fRotB21[isect] = TMath::Sin(phi);
285 fRotB22[isect] = TMath::Cos(phi);
288 for (isect = 0; isect < fgkNsect; isect++) {
289 SetSMstatus(isect,1);
294 //_____________________________________________________________________________
295 void AliTRDgeometry::CreateGeometry(Int_t *idtmed)
298 // Create the TRD geometry without hole
301 // Names of the TRD volumina (xx = detector number):
303 // Volume (Air) wrapping the readout chamber components
304 // UTxx includes: UAxx, UDxx, UFxx, UUxx
306 // UUxx the services volume has been reduced by 7.42 mm
307 // in order to allow shifts in radial direction
309 // Lower part of the readout chambers (gas volume + radiator)
311 // UAxx Aluminum frames (Al)
312 // UBxx G10 frames (C)
313 // UCxx Inner volumes (Air)
315 // Upper part of the readout chambers (readout plane + fee)
317 // UDxx G10 frames (C)
318 // UExx Inner volumes of the G10 (Air)
319 // UFxx Aluminum frames (Al)
320 // UGxx Inner volumes of the Al (Air)
322 // Inner material layers
324 // UHxx Radiator (Rohacell)
325 // UIxx Entrance window (Mylar)
326 // UJxx Drift volume (Xe/CO2)
327 // UKxx Amplification volume (Xe/CO2)
328 // ULxx Pad plane (Cu)
329 // UMxx Support structure (Rohacell)
330 // UNxx ROB base material (C)
331 // UOxx ROB copper (Cu)
334 const Int_t kNparTrd = 4;
335 const Int_t kNparCha = 3;
337 Float_t xpos, ypos, zpos;
339 Float_t parTrd[kNparTrd];
340 Float_t parCha[kNparCha];
345 // The TRD mother volume for one sector (Air), full length in z-direction
346 // Provides material for side plates of super module
347 parTrd[0] = fgkSwidth1/2.;
348 parTrd[1] = fgkSwidth2/2.;
349 parTrd[2] = fgkSlenTR1/2.;
350 parTrd[3] = fgkSheight/2.;
351 gMC->Gsvolu("UTR1","TRD1",idtmed[1302-1],parTrd,kNparTrd);
354 // The outer aluminum plates of the super module (Al)
355 parTrd[0] = fgkSwidth1/2.;
356 parTrd[1] = fgkSwidth2/2.;
357 parTrd[2] = fgkSlenTR1/2.;
358 parTrd[3] = fgkSheight/2.;
359 gMC->Gsvolu("UTS1","TRD1",idtmed[1301-1],parTrd,kNparTrd);
361 // The inner part of the TRD mother volume for one sector (Air),
362 // full length in z-direction
363 parTrd[0] = fgkSwidth1/2. - fgkSMpltT;
364 parTrd[1] = fgkSwidth2/2. - fgkSMpltT;
365 parTrd[2] = fgkSlenTR1/2.;
366 parTrd[3] = fgkSheight/2. - fgkSMpltT;
367 gMC->Gsvolu("UTI1","TRD1",idtmed[1302-1],parTrd,kNparTrd);
369 for (Int_t icham = 0; icham < kNcham; icham++) {
370 for (Int_t iplan = 0; iplan < kNplan; iplan++) {
372 Int_t iDet = GetDetectorSec(iplan,icham);
374 // The lower part of the readout chambers (gas volume + radiator)
375 // The aluminum frames
376 sprintf(cTagV,"UA%02d",iDet);
377 parCha[0] = fCwidth[iplan]/2.;
378 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.;
379 parCha[2] = fgkCraH/2. + fgkCdrH/2.;
380 fChamberUAboxd[iDet][0] = parCha[0];
381 fChamberUAboxd[iDet][1] = parCha[1];
382 fChamberUAboxd[iDet][2] = parCha[2];
383 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parCha,kNparCha);
385 sprintf(cTagV,"UB%02d",iDet);
386 parCha[0] = fCwidth[iplan]/2. - fgkCalT;
389 gMC->Gsvolu(cTagV,"BOX ",idtmed[1307-1],parCha,kNparCha);
390 // The inner part (air)
391 sprintf(cTagV,"UC%02d",iDet);
392 parCha[0] = fCwidth[iplan]/2. - fgkCalT - fgkCclsT;
393 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.- fgkCclfT;
395 gMC->Gsvolu(cTagV,"BOX ",idtmed[1302-1],parCha,kNparCha);
397 // The upper part of the readout chambers (readout plane)
399 sprintf(cTagV,"UD%02d",iDet);
400 parCha[0] = fCwidth[iplan]/2. + fgkCroW;
401 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.;
402 parCha[2] = fgkCamH/2.;
403 fChamberUDboxd[iDet][0] = parCha[0];
404 fChamberUDboxd[iDet][1] = parCha[1];
405 fChamberUDboxd[iDet][2] = parCha[2];
406 gMC->Gsvolu(cTagV,"BOX ",idtmed[1307-1],parCha,kNparCha);
407 // The inner part of the G10 frame (air)
408 sprintf(cTagV,"UE%02d",iDet);
409 parCha[0] = fCwidth[iplan]/2. + fgkCroW - fgkCcuT;
410 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.- fgkCcuT;
412 gMC->Gsvolu(cTagV,"BOX ",idtmed[1302-1],parCha,kNparCha);
413 // The aluminum frames
414 sprintf(cTagV,"UF%02d",iDet);
415 parCha[0] = fCwidth[iplan]/2. + fgkCroW;
416 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.;
417 parCha[2] = fgkCroH/2.;
418 fChamberUFboxd[iDet][0] = parCha[0];
419 fChamberUFboxd[iDet][1] = parCha[1];
420 fChamberUFboxd[iDet][2] = parCha[2];
421 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parCha,kNparCha);
422 // The inner part of the aluminum frames
423 sprintf(cTagV,"UG%02d",iDet);
424 parCha[0] = fCwidth[iplan]/2. + fgkCroW - fgkCauT;
425 parCha[1] = fClength[iplan][icham]/2. - fgkHspace/2.- fgkCauT;
427 gMC->Gsvolu(cTagV,"BOX ",idtmed[1302-1],parCha,kNparCha);
429 // The material layers inside the chambers
432 // Rohacell layer (radiator)
433 parCha[2] = fgkRaThick/2;
434 sprintf(cTagV,"UH%02d",iDet);
435 gMC->Gsvolu(cTagV,"BOX ",idtmed[1315-1],parCha,kNparCha);
436 // Mylar layer (entrance window + HV cathode)
437 parCha[2] = fgkMyThick/2;
438 sprintf(cTagV,"UI%02d",iDet);
439 gMC->Gsvolu(cTagV,"BOX ",idtmed[1308-1],parCha,kNparCha);
440 // Xe/Isobutane layer (drift volume)
441 parCha[2] = fgkDrThick/2.;
442 sprintf(cTagV,"UJ%02d",iDet);
443 gMC->Gsvolu(cTagV,"BOX ",idtmed[1309-1],parCha,kNparCha);
444 // Xe/Isobutane layer (amplification volume)
445 parCha[2] = fgkAmThick/2.;
446 sprintf(cTagV,"UK%02d",iDet);
447 gMC->Gsvolu(cTagV,"BOX ",idtmed[1309-1],parCha,kNparCha);
448 // Cu layer (pad plane)
449 parCha[2] = fgkCuThick/2;
450 sprintf(cTagV,"UL%02d",iDet);
451 gMC->Gsvolu(cTagV,"BOX ",idtmed[1305-1],parCha,kNparCha);
452 // G10 layer (support structure / honeycomb)
453 parCha[2] = fgkSuThick/2;
454 sprintf(cTagV,"UM%02d",iDet);
455 gMC->Gsvolu(cTagV,"BOX ",idtmed[1313-1],parCha,kNparCha);
456 // G10 layer (readout board)
457 parCha[2] = fgkRpThick/2;
458 sprintf(cTagV,"UN%02d",iDet);
459 gMC->Gsvolu(cTagV,"BOX ",idtmed[1313-1],parCha,kNparCha);
460 // Cu layer (readout board)
461 parCha[2] = fgkRcThick/2;
462 sprintf(cTagV,"UO%02d",iDet);
463 gMC->Gsvolu(cTagV,"BOX ",idtmed[1306-1],parCha,kNparCha);
465 // Position the layers in the chambers
469 // Rohacell layer (radiator)
471 sprintf(cTagV,"UH%02d",iDet);
472 sprintf(cTagM,"UC%02d",iDet);
473 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
474 // Mylar layer (entrance window + HV cathode)
476 sprintf(cTagV,"UI%02d",iDet);
477 sprintf(cTagM,"UC%02d",iDet);
478 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
479 // Xe/Isobutane layer (drift volume)
481 sprintf(cTagV,"UJ%02d",iDet);
482 sprintf(cTagM,"UC%02d",iDet);
483 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
485 // Xe/Isobutane layer (amplification volume)
487 sprintf(cTagV,"UK%02d",iDet);
488 sprintf(cTagM,"UE%02d",iDet);
489 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
491 // Cu layer (pad plane)
493 sprintf(cTagV,"UL%02d",iDet);
494 sprintf(cTagM,"UG%02d",iDet);
495 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
496 // G10 layer (support structure)
498 sprintf(cTagV,"UM%02d",iDet);
499 sprintf(cTagM,"UG%02d",iDet);
500 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
501 // G10 layer (readout board)
503 sprintf(cTagV,"UN%02d",iDet);
504 sprintf(cTagM,"UG%02d",iDet);
505 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
506 // Cu layer (readout board)
508 sprintf(cTagV,"UO%02d",iDet);
509 sprintf(cTagM,"UG%02d",iDet);
510 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
512 // Position the inner volumes of the chambers in the frames
516 // The inside of the lower G10 frame
517 sprintf(cTagV,"UC%02d",iDet);
518 sprintf(cTagM,"UB%02d",iDet);
519 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
520 // The lower G10 frame inside the aluminum frame
521 sprintf(cTagV,"UB%02d",iDet);
522 sprintf(cTagM,"UA%02d",iDet);
523 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
524 // The inside of the upper G10 frame
525 sprintf(cTagV,"UE%02d",iDet);
526 sprintf(cTagM,"UD%02d",iDet);
527 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
528 // The inside of the upper aluminum frame
529 sprintf(cTagV,"UG%02d",iDet);
530 sprintf(cTagM,"UF%02d",iDet);
531 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
533 // Position the frames of the chambers in the TRD mother volume
535 ypos = - fClength[iplan][0] - fClength[iplan][1] - fClength[iplan][2]/2.;
536 for (Int_t ic = 0; ic < icham; ic++) {
537 ypos += fClength[iplan][ic];
539 ypos += fClength[iplan][icham]/2.;
540 zpos = fgkVrocsm + fgkCraH/2. + fgkCdrH/2. - fgkSheight/2.
541 + iplan * (fgkCH + fgkVspace);
542 // The lower aluminum frame, radiator + drift region
543 sprintf(cTagV,"UA%02d",iDet);
544 fChamberUAorig[iDet][0] = xpos;
545 fChamberUAorig[iDet][1] = ypos;
546 fChamberUAorig[iDet][2] = zpos;
547 // The upper G10 frame, amplification region
548 sprintf(cTagV,"UD%02d",iDet);
549 zpos += fgkCamH/2. + fgkCraH/2. + fgkCdrH/2.;
550 fChamberUDorig[iDet][0] = xpos;
551 fChamberUDorig[iDet][1] = ypos;
552 fChamberUDorig[iDet][2] = zpos;
553 // The upper aluminum frame
554 sprintf(cTagV,"UF%02d",iDet);
555 zpos += fgkCroH/2. + fgkCamH/2.;
556 fChamberUForig[iDet][0] = xpos;
557 fChamberUForig[iDet][1] = ypos;
558 fChamberUForig[iDet][2] = zpos;
563 // Create the volumes of the super module frame
566 // Create the volumes of the services
567 CreateServices(idtmed);
569 for (Int_t icham = 0; icham < kNcham; icham++) {
570 for (Int_t iplan = 0; iplan < kNplan; iplan++) {
571 GroupChamber(iplan,icham,idtmed);
578 gMC->Gspos("UTI1",1,"UTS1",xpos,ypos,zpos,0,"ONLY");
583 gMC->Gspos("UTS1",1,"UTR1",xpos,ypos,zpos,0,"ONLY");
585 // Put the TRD volumes into the space frame mother volumes
586 // if enabled via status flag
590 for (Int_t isect = 0; isect < kNsect; isect++) {
591 if (fSMstatus[isect]) {
592 sprintf(cTagV,"BTRD%d",isect);
593 gMC->Gspos("UTR1",1,cTagV,xpos,ypos,zpos,0,"ONLY");
599 //_____________________________________________________________________________
600 void AliTRDgeometry::CreateFrame(Int_t *idtmed)
603 // Create the geometry of the frame of the supermodule
605 // Names of the TRD services volumina
607 // USRL Support rails for the chambers (Al)
608 // USxx Support cross bars between the chambers (Al)
620 // The chamber support rails
623 const Float_t kSRLwid = 2.0;
624 const Float_t kSRLhgt = 2.3;
625 const Float_t kSRLdst = 0.6;
626 const Int_t kNparSRL = 3;
627 Float_t parSRL[kNparSRL];
628 parSRL[0] = kSRLwid/2.;
629 parSRL[1] = fgkSlenTR1/2.;
630 parSRL[2] = kSRLhgt/2.;
631 gMC->Gsvolu("USRL","BOX ",idtmed[1301-1],parSRL,kNparSRL);
636 for (iplan = 0; iplan < kNplan; iplan++) {
638 xpos = fCwidth[iplan]/2. + kSRLwid/2. + kSRLdst;
640 zpos = fgkVrocsm + fgkCraH + fgkCdrH - fgkSheight/2. - kSRLhgt/2.
641 + iplan * (fgkCH + fgkVspace);
642 gMC->Gspos("USRL",iplan+1 ,"UTI1", xpos,ypos,zpos,0,"ONLY");
643 gMC->Gspos("USRL",iplan+1+ kNplan,"UTI1",-xpos,ypos,zpos,0,"ONLY");
648 // The cross bars between the chambers
651 const Float_t kSCBwid = 1.0;
652 const Int_t kNparSCB = 3;
653 Float_t parSCB[kNparSCB];
654 parSCB[1] = kSCBwid/2.;
655 parSCB[2] = fgkCH/2.;
660 for (iplan = 0; iplan < kNplan; iplan++) {
662 parSCB[0] = fCwidth[iplan]/2. + kSRLdst/2.;
664 sprintf(cTagV,"US0%01d",iplan);
665 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
667 ypos = fgkSlenTR1/2. - kSCBwid/2.;
668 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
669 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
671 sprintf(cTagV,"US1%01d",iplan);
672 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
674 ypos = fClength[iplan][2]/2. + fClength[iplan][1];
675 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
676 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
678 sprintf(cTagV,"US2%01d",iplan);
679 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
681 ypos = fClength[iplan][2]/2.;
682 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
683 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
685 sprintf(cTagV,"US3%01d",iplan);
686 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
688 ypos = - fClength[iplan][2]/2.;
689 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
690 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
692 sprintf(cTagV,"US4%01d",iplan);
693 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
695 ypos = - fClength[iplan][2]/2. - fClength[iplan][1];
696 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
697 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
699 sprintf(cTagV,"US5%01d",iplan);
700 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
702 ypos = - fgkSlenTR1/2. + kSCBwid/2.;
703 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
704 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
710 //_____________________________________________________________________________
711 void AliTRDgeometry::CreateServices(Int_t *idtmed)
714 // Create the geometry of the services
716 // Names of the TRD services volumina
718 // UTCL Cooling arterias (Al)
719 // UTCW Cooling arterias (Water)
720 // UUxx Volumes for the services at the chambers (Air)
721 // UTPW Power bars (Cu)
722 // UTCP Cooling pipes (Al)
723 // UTCH Cooling pipes (Water)
724 // UTPL Power lines (Cu)
725 // UMCM Readout MCMs (G10/Cu/Si)
737 // The rotation matrices
738 const Int_t kNmatrix = 3;
739 Int_t matrix[kNmatrix];
740 gMC->Matrix(matrix[0],100.0, 0.0, 90.0, 90.0, 10.0, 0.0);
741 gMC->Matrix(matrix[1], 80.0, 0.0, 90.0, 90.0, 10.0,180.0);
742 gMC->Matrix(matrix[2], 0.0, 0.0, 90.0, 90.0, 90.0, 0.0);
744 AliTRDCommonParam* commonParam = AliTRDCommonParam::Instance();
746 AliError("Could not get common parameters\n");
751 // The cooling arterias
754 // Width of the cooling arterias
755 const Float_t kCOLwid = 0.5;
756 // Height of the cooling arterias
757 const Float_t kCOLhgt = 5.5;
758 // Positioning of the cooling
759 const Float_t kCOLposx = 1.6;
760 const Float_t kCOLposz = -0.2;
761 // Thickness of the walls of the cooling arterias
762 const Float_t kCOLthk = 0.1;
763 const Int_t kNparCOL = 3;
764 Float_t parCOL[kNparCOL];
765 parCOL[0] = kCOLwid/2.;
766 parCOL[1] = fgkSlenTR1/2.;
767 parCOL[2] = kCOLhgt/2.;
768 gMC->Gsvolu("UTCL","BOX ",idtmed[1324-1],parCOL,kNparCOL);
769 parCOL[0] -= kCOLthk;
770 parCOL[1] = fgkSlenTR1/2.;
771 parCOL[2] -= kCOLthk;
772 gMC->Gsvolu("UTCW","BOX ",idtmed[1314-1],parCOL,kNparCOL);
777 gMC->Gspos("UTCW",1,"UTCL", xpos,ypos,zpos,0,"ONLY");
779 for (iplan = 0; iplan < kNplan; iplan++) {
781 xpos = fCwidth[iplan]/2. + kCOLwid/2. + kCOLposx;
783 zpos = fgkVrocsm + kCOLhgt/2. - fgkSheight/2. + kCOLposz
784 + iplan * (fgkCH + fgkVspace);
785 if (iplan == 0) zpos += 0.25; // To avoid overlaps !
786 gMC->Gspos("UTCL",iplan+1 ,"UTI1", xpos,ypos,zpos,matrix[0],"ONLY");
787 gMC->Gspos("UTCL",iplan+1+ kNplan,"UTI1",-xpos,ypos,zpos,matrix[1],"ONLY");
795 const Float_t kPWRwid = 0.6;
796 const Float_t kPWRhgt = 4.5;
797 const Float_t kPWRposx = 1.05;
798 const Float_t kPWRposz = 0.9;
799 const Int_t kNparPWR = 3;
800 Float_t parPWR[kNparPWR];
801 parPWR[0] = kPWRwid/2.;
802 parPWR[1] = fgkSlenTR1/2.;
803 parPWR[2] = kPWRhgt/2.;
804 gMC->Gsvolu("UTPW","BOX ",idtmed[1325-1],parPWR,kNparPWR);
806 for (iplan = 0; iplan < kNplan; iplan++) {
808 xpos = fCwidth[iplan]/2. + kPWRwid/2. + kPWRposx;
810 zpos = fgkVrocsm + kPWRhgt/2. - fgkSheight/2. + kPWRposz
811 + iplan * (fgkCH + fgkVspace);
812 gMC->Gspos("UTPW",iplan+1 ,"UTI1", xpos,ypos,zpos,matrix[0],"ONLY");
813 gMC->Gspos("UTPW",iplan+1+ kNplan,"UTI1",-xpos,ypos,zpos,matrix[1],"ONLY");
818 // The volumes for the services at the chambers
821 const Int_t kNparServ = 3;
822 Float_t parServ[kNparServ];
824 for (icham = 0; icham < kNcham; icham++) {
825 for (iplan = 0; iplan < kNplan; iplan++) {
827 Int_t iDet = GetDetectorSec(iplan,icham);
829 sprintf(cTagV,"UU%02d",iDet);
830 parServ[0] = fCwidth[iplan]/2.;
831 parServ[1] = fClength[iplan][icham]/2. - fgkHspace/2.;
832 parServ[2] = fgkVspace/2. - 0.742/2.; //!!!!!!!!!!!!!!
833 fChamberUUboxd[iDet][0] = parServ[0];
834 fChamberUUboxd[iDet][1] = parServ[1];
835 fChamberUUboxd[iDet][2] = parServ[2];
836 gMC->Gsvolu(cTagV,"BOX",idtmed[1302-1],parServ,kNparServ);
839 ypos = - fClength[iplan][0] - fClength[iplan][1] - fClength[iplan][2]/2.;
840 for (Int_t ic = 0; ic < icham; ic++) {
841 ypos += fClength[iplan][ic];
843 ypos += fClength[iplan][icham]/2.;
844 zpos = fgkVrocsm + fgkCH + fgkVspace/2. - fgkSheight/2.
845 + iplan * (fgkCH + fgkVspace);
847 fChamberUUorig[iDet][0] = xpos;
848 fChamberUUorig[iDet][1] = ypos;
849 fChamberUUorig[iDet][2] = zpos;
855 // The cooling pipes inside the service volumes
858 const Int_t kNparTube = 3;
859 Float_t parTube[kNparTube];
860 // The aluminum pipe for the cooling
864 gMC->Gsvolu("UTCP","TUBE",idtmed[1324-1],parTube,0);
869 gMC->Gsvolu("UTCH","TUBE",idtmed[1314-1],parTube,kNparTube);
870 // Water inside the cooling pipe
874 gMC->Gspos("UTCH",1,"UTCP",xpos,ypos,zpos,0,"ONLY");
876 // Position the cooling pipes in the mother volume
877 const Int_t kNpar = 3;
879 for (icham = 0; icham < kNcham; icham++) {
880 for (iplan = 0; iplan < kNplan; iplan++) {
881 Int_t iDet = GetDetectorSec(iplan,icham);
882 Int_t iCopy = GetDetector(iplan,icham,0) * 100;
883 Int_t nMCMrow = commonParam->GetRowMax(iplan,icham,0);
884 Float_t ySize = (GetChamberLength(iplan,icham) - 2.*fgkRpadW)
885 / ((Float_t) nMCMrow);
886 sprintf(cTagV,"UU%02d",iDet);
887 for (Int_t iMCMrow = 0; iMCMrow < nMCMrow; iMCMrow++) {
889 ypos = (0.5 + iMCMrow) * ySize - 1.9
890 - fClength[iplan][icham]/2. + fgkHspace/2.;
891 zpos = 0.0 + 0.742/2.;
893 par[1] = 0.3/2.; // Thickness of the cooling pipes
894 par[2] = fCwidth[iplan]/2.;
895 gMC->Gsposp("UTCP",iCopy+iMCMrow,cTagV,xpos,ypos,zpos
896 ,matrix[2],"ONLY",par,kNpar);
905 // The copper power lines
909 gMC->Gsvolu("UTPL","TUBE",idtmed[1305-1],parTube,0);
911 // Position the power lines in the mother volume
912 for (icham = 0; icham < kNcham; icham++) {
913 for (iplan = 0; iplan < kNplan; iplan++) {
914 Int_t iDet = GetDetectorSec(iplan,icham);
915 Int_t iCopy = GetDetector(iplan,icham,0) * 100;
916 Int_t nMCMrow = commonParam->GetRowMax(iplan,icham,0);
917 Float_t ySize = (GetChamberLength(iplan,icham) - 2.*fgkRpadW)
918 / ((Float_t) nMCMrow);
919 sprintf(cTagV,"UU%02d",iDet);
920 for (Int_t iMCMrow = 0; iMCMrow < nMCMrow; iMCMrow++) {
922 ypos = (0.5 + iMCMrow) * ySize - 1.0
923 - fClength[iplan][icham]/2. + fgkHspace/2.;
924 zpos = -0.4 + 0.742/2.;
926 par[1] = 0.2/2.; // Thickness of the power lines
927 par[2] = fCwidth[iplan]/2.;
928 gMC->Gsposp("UTPL",iCopy+iMCMrow,cTagV,xpos,ypos,zpos
929 ,matrix[2],"ONLY",par,kNpar);
938 // The mother volume for the MCMs (air)
939 const Int_t kNparMCM = 3;
940 Float_t parMCM[kNparMCM];
944 gMC->Gsvolu("UMCM","BOX",idtmed[1302-1],parMCM,kNparMCM);
946 // The MCM carrier G10 layer
950 gMC->Gsvolu("UMC1","BOX",idtmed[1319-1],parMCM,kNparMCM);
951 // The MCM carrier Cu layer
954 parMCM[2] = 0.0162/2.;
955 gMC->Gsvolu("UMC2","BOX",idtmed[1318-1],parMCM,kNparMCM);
956 // The silicon of the chips
959 parMCM[2] = 0.003/2.;
960 gMC->Gsvolu("UMC3","BOX",idtmed[1320-1],parMCM,kNparMCM);
962 // Put the MCM material inside the MCM mother volume
965 zpos = -0.07 + 0.1/2.;
966 gMC->Gspos("UMC1",1,"UMCM",xpos,ypos,zpos,0,"ONLY");
967 zpos += 0.1/2. + 0.0162/2.;
968 gMC->Gspos("UMC2",1,"UMCM",xpos,ypos,zpos,0,"ONLY");
969 zpos += 0.00162/2 + 0.003/2.;
970 gMC->Gspos("UMC3",1,"UMCM",xpos,ypos,zpos,0,"ONLY");
972 // Position the MCMs in the mother volume
973 for (icham = 0; icham < kNcham; icham++) {
974 for (iplan = 0; iplan < kNplan; iplan++) {
975 // Take out upper plane until TRD mothervolume is adjusted
976 //for (iplan = 0; iplan < kNplan-1; iplan++) {
977 Int_t iDet = GetDetectorSec(iplan,icham);
978 Int_t iCopy = GetDetector(iplan,icham,0) * 1000;
979 Int_t nMCMrow = commonParam->GetRowMax(iplan,icham,0);
980 Float_t ySize = (GetChamberLength(iplan,icham) - 2.*fgkRpadW)
981 / ((Float_t) nMCMrow);
983 Float_t xSize = (GetChamberWidth(iplan) - 2.* fgkCpadW)
984 / ((Float_t) nMCMcol);
985 sprintf(cTagV,"UU%02d",iDet);
986 for (Int_t iMCMrow = 0; iMCMrow < nMCMrow; iMCMrow++) {
987 for (Int_t iMCMcol = 0; iMCMcol < nMCMcol; iMCMcol++) {
988 xpos = (0.5 + iMCMcol) * xSize + 1.0
990 ypos = (0.5 + iMCMrow) * ySize + 1.0
991 - fClength[iplan][icham]/2. + fgkHspace/2.;
992 zpos = -0.4 + 0.742/2.;
994 par[1] = 0.2/2.; // Thickness of the power lines
995 par[2] = fCwidth[iplan]/2.;
996 gMC->Gspos("UMCM",iCopy+iMCMrow*10+iMCMcol,cTagV
997 ,xpos,ypos,zpos,0,"ONLY");
1006 //_____________________________________________________________________________
1007 void AliTRDgeometry::GroupChamber(Int_t iplan, Int_t icham, Int_t *idtmed)
1010 // Group volumes UA, UD, UF, UU in a single chamber (Air)
1011 // UA, UD, UF, UU are boxes
1015 const Int_t kNparCha = 3;
1017 Int_t iDet = GetDetectorSec(iplan,icham);
1027 for (Int_t i = 0; i < 3; i++) {
1028 xyzMin[i] = +9999; xyzMax[i] = -9999;
1031 for (Int_t i = 0; i < 3; i++) {
1033 xyzMin[i] = TMath::Min(xyzMin[i],fChamberUAorig[iDet][i]-fChamberUAboxd[iDet][i]);
1034 xyzMax[i] = TMath::Max(xyzMax[i],fChamberUAorig[iDet][i]+fChamberUAboxd[iDet][i]);
1036 xyzMin[i] = TMath::Min(xyzMin[i],fChamberUDorig[iDet][i]-fChamberUDboxd[iDet][i]);
1037 xyzMax[i] = TMath::Max(xyzMax[i],fChamberUDorig[iDet][i]+fChamberUDboxd[iDet][i]);
1039 xyzMin[i] = TMath::Min(xyzMin[i],fChamberUForig[iDet][i]-fChamberUFboxd[iDet][i]);
1040 xyzMax[i] = TMath::Max(xyzMax[i],fChamberUForig[iDet][i]+fChamberUFboxd[iDet][i]);
1042 xyzMin[i] = TMath::Min(xyzMin[i],fChamberUUorig[iDet][i]-fChamberUUboxd[iDet][i]);
1043 xyzMax[i] = TMath::Max(xyzMax[i],fChamberUUorig[iDet][i]+fChamberUUboxd[iDet][i]);
1045 xyzOrig[i] = 0.5*(xyzMax[i]+xyzMin[i]);
1046 xyzBoxd[i] = 0.5*(xyzMax[i]-xyzMin[i]);
1050 sprintf(cTagM,"UT%02d",iDet);
1052 gMC->Gsvolu(cTagM,"BOX ",idtmed[1302-1],xyzBoxd,kNparCha);
1054 sprintf(cTagV,"UA%02d",iDet);
1055 gMC->Gspos(cTagV,1,cTagM,
1056 fChamberUAorig[iDet][0]-xyzOrig[0],
1057 fChamberUAorig[iDet][1]-xyzOrig[1],
1058 fChamberUAorig[iDet][2]-xyzOrig[2],
1061 sprintf(cTagV,"UD%02d",iDet);
1062 gMC->Gspos(cTagV,1,cTagM,
1063 fChamberUDorig[iDet][0]-xyzOrig[0],
1064 fChamberUDorig[iDet][1]-xyzOrig[1],
1065 fChamberUDorig[iDet][2]-xyzOrig[2],
1068 sprintf(cTagV,"UF%02d",iDet);
1069 gMC->Gspos(cTagV,1,cTagM,
1070 fChamberUForig[iDet][0]-xyzOrig[0],
1071 fChamberUForig[iDet][1]-xyzOrig[1],
1072 fChamberUForig[iDet][2]-xyzOrig[2],
1075 sprintf(cTagV,"UU%02d",iDet);
1076 gMC->Gspos(cTagV,1,cTagM,
1077 fChamberUUorig[iDet][0]-xyzOrig[0],
1078 fChamberUUorig[iDet][1]-xyzOrig[1],
1079 fChamberUUorig[iDet][2]-xyzOrig[2],
1082 sprintf(cTagV,"UT%02d",iDet);
1083 gMC->Gspos(cTagV,1,"UTI1",xyzOrig[0],xyzOrig[1],xyzOrig[2],0,"ONLY");
1087 //_____________________________________________________________________________
1088 Bool_t AliTRDgeometry::Local2Global(Int_t idet, Double_t *local
1089 , Double_t *global) const
1092 // Converts local pad-coordinates (row,col,time) into
1093 // global ALICE reference frame coordinates (x,y,z)
1096 Int_t icham = GetChamber(idet); // Chamber info (0-4)
1097 Int_t isect = GetSector(idet); // Sector info (0-17)
1098 Int_t iplan = GetPlane(idet); // Plane info (0-5)
1100 return Local2Global(iplan,icham,isect,local,global);
1104 //_____________________________________________________________________________
1105 Bool_t AliTRDgeometry::Local2Global(Int_t iplan, Int_t icham, Int_t isect
1106 , Double_t *local, Double_t *global) const
1109 // Converts local pad-coordinates (row,col,time) into
1110 // global ALICE reference frame coordinates (x,y,z)
1113 AliTRDCommonParam* commonParam = AliTRDCommonParam::Instance();
1115 AliError("Could not get common parameters\n");
1119 AliTRDcalibDB* calibration = AliTRDcalibDB::Instance();
1121 AliError("Could not get calibration data\n");
1125 AliTRDpadPlane *padPlane = commonParam->GetPadPlane(iplan,icham);
1127 // calculate (x,y,z) position in rotated chamber
1128 Int_t row = ((Int_t) local[0]);
1129 Int_t col = ((Int_t) local[1]);
1130 Float_t timeSlice = local[2] + 0.5;
1131 Float_t time0 = GetTime0(iplan);
1133 Int_t idet = GetDetector(iplan, icham, isect);
1136 rot[0] = time0 - (timeSlice - calibration->GetT0(idet, col, row))
1137 * calibration->GetVdrift(idet, col, row)/calibration->GetSamplingFrequency();
1138 rot[1] = padPlane->GetColPos(col) - 0.5 * padPlane->GetColSize(col);
1139 rot[2] = padPlane->GetRowPos(row) - 0.5 * padPlane->GetRowSize(row);
1141 // Rotate back to original position
1142 return RotateBack(idet,rot,global);
1146 //_____________________________________________________________________________
1147 Bool_t AliTRDgeometry::Global2Local(Int_t mode, Double_t *local, Double_t *global
1148 , Int_t* index) const
1151 // Converts local pad-coordinates (row,col,time) into
1152 // global ALICE reference frame coordinates (x,y,z)
1154 // index[0] = plane number
1155 // index[1] = chamber number
1156 // index[2] = sector number
1158 // mode=0 - local coordinate in y, z, x - rotated global
1159 // mode=2 - local coordinate in pad, and pad row, x - rotated global
1162 Int_t idet = GetDetector(index[0],index[1],index[2]); // Detector number
1163 RotateBack(idet,global,local);
1164 if (mode == 0) return kTRUE;
1170 //_____________________________________________________________________________
1171 Bool_t AliTRDgeometry::Global2Detector(Double_t global[3], Int_t index[3])
1174 // Find detector for given global point - Ideal geometry
1177 // input = global position
1179 // index[0] = plane number
1180 // index[1] = chamber number
1181 // index[2] = sector number
1187 Float_t fi = TMath::ATan2(global[1],global[0]);
1189 fi += 2*TMath::Pi();
1191 index[2] = fgkNsect - 1 - TMath::Nint((fi - GetAlpha()/2.)/GetAlpha());
1196 Float_t locx = global[0] * fRotA11[index[2]] + global[1] * fRotA12[index[2]];
1198 Float_t max = locx - GetTime0(0);
1199 for (Int_t iplane=1; iplane<fgkNplan;iplane++){
1200 Float_t dist = TMath::Abs(locx - GetTime0(iplane));
1210 if (TMath::Abs(global[2]) < 0.5*GetChamberLength(index[0],2)){
1214 Double_t localZ = global[2];
1216 localZ -= 0.5*(GetChamberLength(index[0],2)+GetChamberLength(index[0],1));
1217 index[1] = (TMath::Abs(localZ) < 0.5*GetChamberLength(index[0],3)) ? 1:0;
1220 localZ += 0.5*(GetChamberLength(index[0],2)+GetChamberLength(index[0],3));
1221 index[1] = (TMath::Abs(localZ) < 0.5*GetChamberLength(index[0],1)) ? 3:4;
1229 //_____________________________________________________________________________
1230 Bool_t AliTRDgeometry::Rotate(Int_t d, Double_t *pos, Double_t *rot) const
1233 // Rotates all chambers in the position of sector 0 and transforms
1234 // the coordinates in the ALICE restframe <pos> into the
1235 // corresponding local frame <rot>.
1238 Int_t sector = GetSector(d);
1240 rot[0] = pos[0] * fRotA11[sector] + pos[1] * fRotA12[sector];
1241 rot[1] = -pos[0] * fRotA21[sector] + pos[1] * fRotA22[sector];
1248 //_____________________________________________________________________________
1249 Bool_t AliTRDgeometry::RotateBack(Int_t d, Double_t *rot, Double_t *pos) const
1252 // Rotates a chambers from the position of sector 0 into its
1253 // original position and transforms the corresponding local frame
1254 // coordinates <rot> into the coordinates of the ALICE restframe <pos>.
1257 Int_t sector = GetSector(d);
1259 pos[0] = rot[0] * fRotB11[sector] + rot[1] * fRotB12[sector];
1260 pos[1] = -rot[0] * fRotB21[sector] + rot[1] * fRotB22[sector];
1267 //_____________________________________________________________________________
1268 Int_t AliTRDgeometry::GetDetectorSec(Int_t p, Int_t c)
1271 // Convert plane / chamber into detector number for one single sector
1274 return (p + c * fgkNplan);
1278 //_____________________________________________________________________________
1279 Int_t AliTRDgeometry::GetDetector(Int_t p, Int_t c, Int_t s)
1282 // Convert plane / chamber / sector into detector number
1285 return (p + c * fgkNplan + s * fgkNplan * fgkNcham);
1289 //_____________________________________________________________________________
1290 Int_t AliTRDgeometry::GetPlane(Int_t d) const
1293 // Reconstruct the plane number from the detector number
1296 return ((Int_t) (d % fgkNplan));
1300 //_____________________________________________________________________________
1301 Int_t AliTRDgeometry::GetChamber(Int_t d) const
1304 // Reconstruct the chamber number from the detector number
1307 return ((Int_t) (d % (fgkNplan * fgkNcham)) / fgkNplan);
1311 //_____________________________________________________________________________
1312 Int_t AliTRDgeometry::GetSector(Int_t d) const
1315 // Reconstruct the sector number from the detector number
1318 return ((Int_t) (d / (fgkNplan * fgkNcham)));
1322 //_____________________________________________________________________________
1323 AliTRDgeometry* AliTRDgeometry::GetGeometry(AliRunLoader* runLoader)
1326 // load the geometry from the galice file
1329 if (!runLoader) runLoader = AliRunLoader::GetRunLoader();
1331 //AliError("No run loader");
1335 TDirectory* saveDir = gDirectory;
1336 runLoader->CdGAFile();
1338 // Try from the galice.root file
1339 AliTRDgeometry* geom = (AliTRDgeometry*) gDirectory->Get("TRDgeometry");
1342 // It is not in the file, try to get it from gAlice,
1343 // which corresponds to the run loader
1344 AliTRD * trd = (AliTRD*)runLoader->GetAliRun()->GetDetector("TRD");
1345 geom = trd->GetGeometry();
1348 //AliError("Geometry not found");
1357 //_____________________________________________________________________________
1358 Bool_t AliTRDgeometry::ReadGeoMatrices()
1361 // Read geo matrices from current gGeoManager for each TRD sector
1364 if (!gGeoManager) return kFALSE;
1365 fMatrixArray = new TObjArray(kNdet);
1366 fMatrixCorrectionArray = new TObjArray(kNdet);
1367 fMatrixGeo = new TObjArray(kNdet);
1368 AliAlignObjAngles o;
1370 for (Int_t iLayer = AliAlignObj::kTRD1; iLayer <= AliAlignObj::kTRD6; iLayer++) {
1371 for (Int_t iModule = 0; iModule < AliAlignObj::LayerSize(iLayer); iModule++) {
1372 UShort_t volid = AliAlignObj::LayerToVolUID(iLayer,iModule);
1373 const char *path = AliAlignObj::GetVolPath(volid);
1374 if (!gGeoManager->cd(path)) return kFALSE;
1375 TGeoHMatrix* m = gGeoManager->GetCurrentMatrix();
1376 Int_t iLayerTRD = iLayer-AliAlignObj::kTRD1;
1377 Int_t isector = Nsect()-1-(iModule/Ncham());
1378 Int_t ichamber = Ncham()-1-(iModule%Ncham());
1379 Int_t lid = GetDetector(iLayerTRD,ichamber,isector);
1382 // Local geo system z-x-y to x-y--z
1384 fMatrixGeo->AddAt(new TGeoHMatrix(*m),lid);
1386 TGeoRotation mchange;
1387 mchange.RotateY(90); mchange.RotateX(90);
1389 TGeoHMatrix gMatrix(mchange.Inverse());
1390 gMatrix.MultiplyLeft(m);
1391 fMatrixArray->AddAt(new TGeoHMatrix(gMatrix),lid);
1394 // Cluster transformation matrix
1396 TGeoHMatrix rotMatrix(mchange.Inverse());
1397 rotMatrix.MultiplyLeft(m);
1398 Double_t sectorAngle = 20.*(isector%18)+10;
1399 TGeoHMatrix rotSector;
1400 rotSector.RotateZ(sectorAngle);
1401 rotMatrix.MultiplyLeft(&rotSector);
1403 fMatrixCorrectionArray->AddAt(new TGeoHMatrix(rotMatrix),lid);