First round of effc++ changes
[u/mrichter/AliRoot.git] / TRD / AliTRDgeometry.cxx
CommitLineData
f7336fa3 1/**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3 * *
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 purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
15
afc51ac2 16/* $Id$ */
f7336fa3 17
18///////////////////////////////////////////////////////////////////////////////
19// //
20// TRD geometry class //
21// //
22///////////////////////////////////////////////////////////////////////////////
23
793ff80c 24
b4a9cd27 25#include <TGeoManager.h>
26#include <TGeoPhysicalNode.h>
27#include <TGeoMatrix.h>
28
2745a409 29#include "AliLog.h"
bdbb05bb 30#include "AliRunLoader.h"
b4a9cd27 31#include "AliAlignObj.h"
32#include "AliAlignObjAngles.h"
33
ecb36af7 34#include "AliRun.h"
35#include "AliTRD.h"
3551db50 36#include "AliTRDcalibDB.h"
37#include "AliTRDCommonParam.h"
2745a409 38#include "AliTRDgeometry.h"
39#include "AliTRDpadPlane.h"
ecb36af7 40
f7336fa3 41ClassImp(AliTRDgeometry)
42
43//_____________________________________________________________________________
793ff80c 44
45 //
46 // The geometry constants
47 //
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;
52
53 //
54 // Dimensions of the detector
55 //
0a770ac9 56
57 // Inner and outer radius of the mother volumes
793ff80c 58 const Float_t AliTRDgeometry::fgkRmin = 294.0;
59 const Float_t AliTRDgeometry::fgkRmax = 368.0;
60
0a770ac9 61 // Upper and lower length of the mother volumes
793ff80c 62 const Float_t AliTRDgeometry::fgkZmax1 = 378.35;
63 const Float_t AliTRDgeometry::fgkZmax2 = 302.0;
64
0a770ac9 65 // Parameter of the BTR mother volumes
a797f961 66 const Float_t AliTRDgeometry::fgkSheight = 77.9;
67 const Float_t AliTRDgeometry::fgkSwidth1 = 94.881;
68 const Float_t AliTRDgeometry::fgkSwidth2 = 122.353;
793ff80c 69 const Float_t AliTRDgeometry::fgkSlenTR1 = 751.0;
70 const Float_t AliTRDgeometry::fgkSlenTR2 = 313.5;
71 const Float_t AliTRDgeometry::fgkSlenTR3 = 159.5;
72
73ae7b59 73 // The super module side plates
287c5d50 74 const Float_t AliTRDgeometry::fgkSMpltT = 0.2;
a797f961 75 //const Float_t AliTRDgeometry::fgkSMgapT = 0.5;
73ae7b59 76
0a770ac9 77 // Height of different chamber parts
78 // Radiator
79 const Float_t AliTRDgeometry::fgkCraH = 4.8;
80 // Drift region
81 const Float_t AliTRDgeometry::fgkCdrH = 3.0;
82 // Amplification region
83 const Float_t AliTRDgeometry::fgkCamH = 0.7;
84 // Readout
73ae7b59 85 const Float_t AliTRDgeometry::fgkCroH = 2.316;
0a770ac9 86 // Total height
87 const Float_t AliTRDgeometry::fgkCH = AliTRDgeometry::fgkCraH
88 + AliTRDgeometry::fgkCdrH
89 + AliTRDgeometry::fgkCamH
90 + AliTRDgeometry::fgkCroH;
91
92 // Vertical spacing of the chambers
73ae7b59 93 const Float_t AliTRDgeometry::fgkVspace = 1.784;
0a770ac9 94
95 // Horizontal spacing of the chambers
96 const Float_t AliTRDgeometry::fgkHspace = 2.0;
97
a797f961 98 // Radial distance of the first ROC to the outer plates of the SM
99 const Float_t AliTRDgeometry::fgkVrocsm = 1.2;
100
0a770ac9 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;
108 // Upper G10 frame
109 const Float_t AliTRDgeometry::fgkCcuT = 0.9;
110 // Upper Al frame
111 const Float_t AliTRDgeometry::fgkCauT = 1.5;
112
113 // Additional width of the readout chamber frames
114 const Float_t AliTRDgeometry::fgkCroW = 0.9;
115
116 // Difference of outer chamber width and pad plane width
73ae7b59 117 //const Float_t AliTRDgeometry::fgkCpadW = 1.0;
118 const Float_t AliTRDgeometry::fgkCpadW = 0.0;
de6df1b1 119 const Float_t AliTRDgeometry::fgkRpadW = 1.0;
793ff80c 120
121 //
122 // Thickness of the the material layers
123 //
db30bf0f 124 const Float_t AliTRDgeometry::fgkRaThick = 0.3646;
793ff80c 125 const Float_t AliTRDgeometry::fgkMyThick = 0.005;
0a770ac9 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;
a797f961 130 const Float_t AliTRDgeometry::fgkCuThick = 0.0072;
793ff80c 131 const Float_t AliTRDgeometry::fgkSuThick = 0.06;
132 const Float_t AliTRDgeometry::fgkFeThick = 0.0044;
133 const Float_t AliTRDgeometry::fgkCoThick = 0.02;
db30bf0f 134 const Float_t AliTRDgeometry::fgkWaThick = 0.02;
a797f961 135 const Float_t AliTRDgeometry::fgkRcThick = 0.0058;
136 const Float_t AliTRDgeometry::fgkRpThick = 0.0632;
793ff80c 137
138 //
139 // Position of the material layers
140 //
0a770ac9 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;
793ff80c 146 const Float_t AliTRDgeometry::fgkSuZpos = 0.0000;
0a770ac9 147 const Float_t AliTRDgeometry::fgkFeZpos = 0.0322;
148 const Float_t AliTRDgeometry::fgkCoZpos = 0.97;
149 const Float_t AliTRDgeometry::fgkWaZpos = 0.99;
a797f961 150 const Float_t AliTRDgeometry::fgkRcZpos = 1.04;
151 const Float_t AliTRDgeometry::fgkRpZpos = 1.0;
3551db50 152
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()) };
793ff80c 160
161//_____________________________________________________________________________
2745a409 162AliTRDgeometry::AliTRDgeometry()
163 :AliGeometry()
164 ,fMatrixArray(0)
165 ,fMatrixCorrectionArray(0)
166 ,fMatrixGeo(0)
167
f7336fa3 168{
169 //
170 // AliTRDgeometry default constructor
171 //
bd0f8685 172
2745a409 173 Init();
174
175}
176
177//_____________________________________________________________________________
178AliTRDgeometry::AliTRDgeometry(const AliTRDgeometry &g)
179 :AliGeometry(g)
180 ,fMatrixArray(g.fMatrixArray)
181 ,fMatrixCorrectionArray(g.fMatrixCorrectionArray)
182 ,fMatrixGeo(g.fMatrixGeo)
183
184{
185 //
186 // AliTRDgeometry copy constructor
187 //
bd0f8685 188
f7336fa3 189 Init();
bd0f8685 190
f7336fa3 191}
192
193//_____________________________________________________________________________
194AliTRDgeometry::~AliTRDgeometry()
195{
8230f242 196 //
197 // AliTRDgeometry destructor
198 //
bd0f8685 199
b4a9cd27 200 delete fMatrixArray;
201 delete fMatrixCorrectionArray;
bd0f8685 202
f7336fa3 203}
204
205//_____________________________________________________________________________
2745a409 206AliTRDgeometry &AliTRDgeometry::operator=(const AliTRDgeometry &g)
207{
208 //
209 // Assignment operator
210 //
211
212 if (this != &g) Init();
213 return *this;
214
215}
216
217//_____________________________________________________________________________
f7336fa3 218void AliTRDgeometry::Init()
219{
220 //
221 // Initializes the geometry parameter
222 //
f7336fa3 223 // The maximum number of pads
224 // and the position of pad 0,0,0
225 //
226 // chambers seen from the top:
227 // +----------------------------+
228 // | |
793ff80c 229 // | | ^
230 // | | rphi|
231 // | | |
232 // |0 | |
233 // +----------------------------+ +------>
f7336fa3 234 // z
793ff80c 235 // chambers seen from the side: ^
236 // +----------------------------+ drift|
237 // |0 | |
238 // | | |
239 // +----------------------------+ +------>
f7336fa3 240 // z
241 //
a2b90f83 242 // IMPORTANT: time bin 0 is now the first one in the drift region
243 // closest to the readout !!!
793ff80c 244 //
f7336fa3 245
0a770ac9 246 Int_t icham;
247 Int_t iplan;
248 Int_t isect;
249
250 // The outer width of the chambers
287c5d50 251 fCwidth[0] = 90.4;
e0d47c25 252 fCwidth[1] = 94.8;
253 fCwidth[2] = 99.3;
254 fCwidth[3] = 103.7;
255 fCwidth[4] = 108.1;
256 fCwidth[5] = 112.6;
0a770ac9 257
258 // The outer lengths of the chambers
73ae7b59 259 // Includes the spacings between the chambers!
8737e16f 260 Float_t length[kNplan][kNcham] = { { 124.0, 124.0, 110.0, 124.0, 124.0 }
e0d47c25 261 , { 124.0, 124.0, 110.0, 124.0, 124.0 }
8737e16f 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 }
e0d47c25 265 , { 147.0, 147.0, 110.0, 147.0, 147.0 } };
0a770ac9 266
267 for (icham = 0; icham < kNcham; icham++) {
268 for (iplan = 0; iplan < kNplan; iplan++) {
269 fClength[iplan][icham] = length[iplan][icham];
0a770ac9 270 }
271 }
272
793ff80c 273 // The rotation matrix elements
274 Float_t phi = 0;
275 for (isect = 0; isect < fgkNsect; isect++) {
5443e65e 276 phi = -2.0 * TMath::Pi() / (Float_t) fgkNsect * ((Float_t) isect + 0.5);
793ff80c 277 fRotA11[isect] = TMath::Cos(phi);
278 fRotA12[isect] = TMath::Sin(phi);
279 fRotA21[isect] = TMath::Sin(phi);
280 fRotA22[isect] = TMath::Cos(phi);
281 phi = -1.0 * 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);
286 }
bd0f8685 287
288 for (isect = 0; isect < fgkNsect; isect++) {
289 SetSMstatus(isect,1);
290 }
793ff80c 291
292}
293
294//_____________________________________________________________________________
bd0f8685 295void AliTRDgeometry::CreateGeometry(Int_t *idtmed)
296{
297 //
298 // Create the TRD geometry without hole
299 //
300 //
301 // Names of the TRD volumina (xx = detector number):
302 //
303 // Volume (Air) wrapping the readout chamber components
304 // UTxx includes: UAxx, UDxx, UFxx, UUxx
305 // Obs:
306 // UUxx the services volume has been reduced by 7.42 mm
307 // in order to allow shifts in radial direction
308 //
309 // Lower part of the readout chambers (gas volume + radiator)
310 //
311 // UAxx Aluminum frames (Al)
312 // UBxx G10 frames (C)
313 // UCxx Inner volumes (Air)
314 //
315 // Upper part of the readout chambers (readout plane + fee)
316 //
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)
321 //
322 // Inner material layers
323 //
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)
a797f961 330 // UNxx ROB base material (C)
331 // UOxx ROB copper (Cu)
bd0f8685 332 //
333
334 const Int_t kNparTrd = 4;
335 const Int_t kNparCha = 3;
336
337 Float_t xpos, ypos, zpos;
338
339 Float_t parTrd[kNparTrd];
340 Float_t parCha[kNparCha];
341
342 Char_t cTagV[6];
343 Char_t cTagM[5];
344
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);
352
353 //
a797f961 354 // The outer aluminum plates of the super module (Al)
355 parTrd[0] = fgkSwidth1/2.;
356 parTrd[1] = fgkSwidth2/2.;
bd0f8685 357 parTrd[2] = fgkSlenTR1/2.;
358 parTrd[3] = fgkSheight/2.;
359 gMC->Gsvolu("UTS1","TRD1",idtmed[1301-1],parTrd,kNparTrd);
360
361 // The inner part of the TRD mother volume for one sector (Air),
362 // full length in z-direction
a797f961 363 parTrd[0] = fgkSwidth1/2. - fgkSMpltT;
364 parTrd[1] = fgkSwidth2/2. - fgkSMpltT;
bd0f8685 365 parTrd[2] = fgkSlenTR1/2.;
a797f961 366 parTrd[3] = fgkSheight/2. - fgkSMpltT;
bd0f8685 367 gMC->Gsvolu("UTI1","TRD1",idtmed[1302-1],parTrd,kNparTrd);
368
369 for (Int_t icham = 0; icham < kNcham; icham++) {
370 for (Int_t iplan = 0; iplan < kNplan; iplan++) {
371
372 Int_t iDet = GetDetectorSec(iplan,icham);
373
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);
384 // The G10 frames
385 sprintf(cTagV,"UB%02d",iDet);
386 parCha[0] = fCwidth[iplan]/2. - fgkCalT;
387 parCha[1] = -1.;
388 parCha[2] = -1.;
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;
394 parCha[2] = -1.;
395 gMC->Gsvolu(cTagV,"BOX ",idtmed[1302-1],parCha,kNparCha);
396
397 // The upper part of the readout chambers (readout plane)
398 // The G10 frames
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;
411 parCha[2] = -1.;
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;
426 parCha[2] = -1.;
427 gMC->Gsvolu(cTagV,"BOX ",idtmed[1302-1],parCha,kNparCha);
428
429 // The material layers inside the chambers
430 parCha[0] = -1.;
431 parCha[1] = -1.;
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);
a797f961 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);
bd0f8685 464
465 // Position the layers in the chambers
466 xpos = 0;
467 ypos = 0;
468 // Lower part
469 // Rohacell layer (radiator)
470 zpos = fgkRaZpos;
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)
475 zpos = fgkMyZpos;
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)
480 zpos = fgkDrZpos;
481 sprintf(cTagV,"UJ%02d",iDet);
482 sprintf(cTagM,"UC%02d",iDet);
483 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
484 // Upper part
485 // Xe/Isobutane layer (amplification volume)
486 zpos = fgkAmZpos;
487 sprintf(cTagV,"UK%02d",iDet);
488 sprintf(cTagM,"UE%02d",iDet);
489 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
490 // Readout part
491 // Cu layer (pad plane)
492 zpos = fgkCuZpos;
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)
497 zpos = fgkSuZpos;
498 sprintf(cTagV,"UM%02d",iDet);
499 sprintf(cTagM,"UG%02d",iDet);
500 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
a797f961 501 // G10 layer (readout board)
502 zpos = fgkRpZpos;
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)
507 zpos = fgkRcZpos;
508 sprintf(cTagV,"UO%02d",iDet);
509 sprintf(cTagM,"UG%02d",iDet);
510 gMC->Gspos(cTagV,1,cTagM,xpos,ypos,zpos,0,"ONLY");
bd0f8685 511
512 // Position the inner volumes of the chambers in the frames
513 xpos = 0.0;
514 ypos = 0.0;
515 zpos = 0.0;
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");
532
533 // Position the frames of the chambers in the TRD mother volume
534 xpos = 0.;
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];
538 }
539 ypos += fClength[iplan][icham]/2.;
a797f961 540 zpos = fgkVrocsm + fgkCraH/2. + fgkCdrH/2. - fgkSheight/2.
541 + iplan * (fgkCH + fgkVspace);
bd0f8685 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;
559
560 }
561 }
562
563 // Create the volumes of the super module frame
564 CreateFrame(idtmed);
565
566 // Create the volumes of the services
567 CreateServices(idtmed);
568
569 for (Int_t icham = 0; icham < kNcham; icham++) {
570 for (Int_t iplan = 0; iplan < kNplan; iplan++) {
571 GroupChamber(iplan,icham,idtmed);
572 }
573 }
574
575 xpos = 0.;
576 ypos = 0.;
577 zpos = 0.;
578 gMC->Gspos("UTI1",1,"UTS1",xpos,ypos,zpos,0,"ONLY");
579
580 xpos = 0.;
581 ypos = 0.;
582 zpos = 0.;
583 gMC->Gspos("UTS1",1,"UTR1",xpos,ypos,zpos,0,"ONLY");
584
585 // Put the TRD volumes into the space frame mother volumes
586 // if enabled via status flag
587 xpos = 0.;
588 ypos = 0.;
589 zpos = 0.;
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");
594 }
595 }
596
597}
598
599//_____________________________________________________________________________
600void AliTRDgeometry::CreateFrame(Int_t *idtmed)
601{
602 //
603 // Create the geometry of the frame of the supermodule
604 //
605 // Names of the TRD services volumina
606 //
607 // USRL Support rails for the chambers (Al)
608 // USxx Support cross bars between the chambers (Al)
609 //
610
611 Int_t iplan = 0;
612
613 Float_t xpos = 0.0;
614 Float_t ypos = 0.0;
615 Float_t zpos = 0.0;
616
617 Char_t cTagV[5];
618
619 //
620 // The chamber support rails
621 //
622
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);
632
633 xpos = 0.0;
634 ypos = 0.0;
635 zpos = 0.0;
636 for (iplan = 0; iplan < kNplan; iplan++) {
637
638 xpos = fCwidth[iplan]/2. + kSRLwid/2. + kSRLdst;
639 ypos = 0.0;
a797f961 640 zpos = fgkVrocsm + fgkCraH + fgkCdrH - fgkSheight/2. - kSRLhgt/2.
bd0f8685 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");
644
645 }
646
647 //
648 // The cross bars between the chambers
649 //
650
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.;
656
657 xpos = 0.0;
658 ypos = 0.0;
659 zpos = 0.0;
660 for (iplan = 0; iplan < kNplan; iplan++) {
661
662 parSCB[0] = fCwidth[iplan]/2. + kSRLdst/2.;
663
664 sprintf(cTagV,"US0%01d",iplan);
665 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
666 xpos = 0.0;
667 ypos = fgkSlenTR1/2. - kSCBwid/2.;
a797f961 668 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 669 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
670
671 sprintf(cTagV,"US1%01d",iplan);
672 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
673 xpos = 0.0;
674 ypos = fClength[iplan][2]/2. + fClength[iplan][1];
a797f961 675 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 676 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
677
678 sprintf(cTagV,"US2%01d",iplan);
679 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
680 xpos = 0.0;
681 ypos = fClength[iplan][2]/2.;
a797f961 682 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 683 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
684
685 sprintf(cTagV,"US3%01d",iplan);
686 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
687 xpos = 0.0;
688 ypos = - fClength[iplan][2]/2.;
a797f961 689 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 690 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
691
692 sprintf(cTagV,"US4%01d",iplan);
693 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
694 xpos = 0.0;
695 ypos = - fClength[iplan][2]/2. - fClength[iplan][1];
a797f961 696 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 697 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
698
699 sprintf(cTagV,"US5%01d",iplan);
700 gMC->Gsvolu(cTagV,"BOX ",idtmed[1301-1],parSCB,kNparSCB);
701 xpos = 0.0;
702 ypos = - fgkSlenTR1/2. + kSCBwid/2.;
a797f961 703 zpos = fgkVrocsm + fgkCH/2. - fgkSheight/2. + iplan * (fgkCH + fgkVspace);
bd0f8685 704 gMC->Gspos(cTagV,1,"UTI1", xpos,ypos,zpos,0,"ONLY");
705
706 }
707
708}
709
710//_____________________________________________________________________________
711void AliTRDgeometry::CreateServices(Int_t *idtmed)
712{
713 //
714 // Create the geometry of the services
715 //
716 // Names of the TRD services volumina
717 //
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)
726 //
727
728 Int_t iplan = 0;
729 Int_t icham = 0;
730
731 Float_t xpos = 0.0;
732 Float_t ypos = 0.0;
733 Float_t zpos = 0.0;
734
735 Char_t cTagV[5];
736
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);
743
744 AliTRDCommonParam* commonParam = AliTRDCommonParam::Instance();
2745a409 745 if (!commonParam) {
746 AliError("Could not get common parameters\n");
bd0f8685 747 return;
748 }
749
750 //
751 // The cooling arterias
752 //
753
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);
773
774 xpos = 0.0;
775 ypos = 0.0;
776 zpos = 0.0;
777 gMC->Gspos("UTCW",1,"UTCL", xpos,ypos,zpos,0,"ONLY");
778
a797f961 779 for (iplan = 0; iplan < kNplan; iplan++) {
bd0f8685 780
781 xpos = fCwidth[iplan]/2. + kCOLwid/2. + kCOLposx;
782 ypos = 0.0;
a797f961 783 zpos = fgkVrocsm + kCOLhgt/2. - fgkSheight/2. + kCOLposz
784 + iplan * (fgkCH + fgkVspace);
bd0f8685 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");
788
789 }
790
791 //
792 // The power bars
793 //
794
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);
805
a797f961 806 for (iplan = 0; iplan < kNplan; iplan++) {
bd0f8685 807
808 xpos = fCwidth[iplan]/2. + kPWRwid/2. + kPWRposx;
809 ypos = 0.0;
a797f961 810 zpos = fgkVrocsm + kPWRhgt/2. - fgkSheight/2. + kPWRposz
811 + iplan * (fgkCH + fgkVspace);
bd0f8685 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");
814
815 }
816
817 //
818 // The volumes for the services at the chambers
819 //
820
821 const Int_t kNparServ = 3;
822 Float_t parServ[kNparServ];
823
824 for (icham = 0; icham < kNcham; icham++) {
825 for (iplan = 0; iplan < kNplan; iplan++) {
bd0f8685 826
827 Int_t iDet = GetDetectorSec(iplan,icham);
828
829 sprintf(cTagV,"UU%02d",iDet);
830 parServ[0] = fCwidth[iplan]/2.;
831 parServ[1] = fClength[iplan][icham]/2. - fgkHspace/2.;
a797f961 832 parServ[2] = fgkVspace/2. - 0.742/2.; //!!!!!!!!!!!!!!
bd0f8685 833 fChamberUUboxd[iDet][0] = parServ[0];
834 fChamberUUboxd[iDet][1] = parServ[1];
835 fChamberUUboxd[iDet][2] = parServ[2];
bd0f8685 836 gMC->Gsvolu(cTagV,"BOX",idtmed[1302-1],parServ,kNparServ);
a797f961 837
bd0f8685 838 xpos = 0.;
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];
842 }
843 ypos += fClength[iplan][icham]/2.;
a797f961 844 zpos = fgkVrocsm + fgkCH + fgkVspace/2. - fgkSheight/2.
845 + iplan * (fgkCH + fgkVspace);
bd0f8685 846 zpos -= 0.742/2.;
847 fChamberUUorig[iDet][0] = xpos;
848 fChamberUUorig[iDet][1] = ypos;
849 fChamberUUorig[iDet][2] = zpos;
850
851 }
852 }
853
854 //
855 // The cooling pipes inside the service volumes
856 //
857
858 const Int_t kNparTube = 3;
859 Float_t parTube[kNparTube];
860 // The aluminum pipe for the cooling
861 parTube[0] = 0.0;
862 parTube[1] = 0.0;
863 parTube[2] = 0.0;
864 gMC->Gsvolu("UTCP","TUBE",idtmed[1324-1],parTube,0);
865 // The cooling water
866 parTube[0] = 0.0;
867 parTube[1] = 0.2/2.;
868 parTube[2] = -1.;
869 gMC->Gsvolu("UTCH","TUBE",idtmed[1314-1],parTube,kNparTube);
870 // Water inside the cooling pipe
871 xpos = 0.0;
872 ypos = 0.0;
873 zpos = 0.0;
874 gMC->Gspos("UTCH",1,"UTCP",xpos,ypos,zpos,0,"ONLY");
875
876 // Position the cooling pipes in the mother volume
877 const Int_t kNpar = 3;
878 Float_t par[kNpar];
879 for (icham = 0; icham < kNcham; icham++) {
880 for (iplan = 0; iplan < kNplan; iplan++) {
bd0f8685 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++) {
888 xpos = 0.0;
889 ypos = (0.5 + iMCMrow) * ySize - 1.9
890 - fClength[iplan][icham]/2. + fgkHspace/2.;
891 zpos = 0.0 + 0.742/2.;
892 par[0] = 0.0;
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);
897 }
898 }
899 }
900
901 //
902 // The power lines
903 //
904
905 // The copper power lines
906 parTube[0] = 0.0;
907 parTube[1] = 0.0;
908 parTube[2] = 0.0;
909 gMC->Gsvolu("UTPL","TUBE",idtmed[1305-1],parTube,0);
910
911 // Position the power lines in the mother volume
912 for (icham = 0; icham < kNcham; icham++) {
913 for (iplan = 0; iplan < kNplan; iplan++) {
bd0f8685 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++) {
921 xpos = 0.0;
922 ypos = (0.5 + iMCMrow) * ySize - 1.0
923 - fClength[iplan][icham]/2. + fgkHspace/2.;
924 zpos = -0.4 + 0.742/2.;
925 par[0] = 0.0;
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);
930 }
931 }
932 }
933
934 //
935 // The MCMs
936 //
937
938 // The mother volume for the MCMs (air)
939 const Int_t kNparMCM = 3;
940 Float_t parMCM[kNparMCM];
941 parMCM[0] = 3.0/2.;
942 parMCM[1] = 3.0/2.;
943 parMCM[2] = 0.14/2.;
944 gMC->Gsvolu("UMCM","BOX",idtmed[1302-1],parMCM,kNparMCM);
945
946 // The MCM carrier G10 layer
947 parMCM[0] = 3.0/2.;
948 parMCM[1] = 3.0/2.;
949 parMCM[2] = 0.1/2.;
950 gMC->Gsvolu("UMC1","BOX",idtmed[1319-1],parMCM,kNparMCM);
951 // The MCM carrier Cu layer
952 parMCM[0] = 3.0/2.;
953 parMCM[1] = 3.0/2.;
954 parMCM[2] = 0.0162/2.;
955 gMC->Gsvolu("UMC2","BOX",idtmed[1318-1],parMCM,kNparMCM);
956 // The silicon of the chips
957 parMCM[0] = 3.0/2.;
958 parMCM[1] = 3.0/2.;
959 parMCM[2] = 0.003/2.;
960 gMC->Gsvolu("UMC3","BOX",idtmed[1320-1],parMCM,kNparMCM);
961
962 // Put the MCM material inside the MCM mother volume
963 xpos = 0.0;
964 ypos = 0.0;
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");
971
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);
982 Int_t nMCMcol = 8;
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
989 - fCwidth[iplan]/2.;
990 ypos = (0.5 + iMCMrow) * ySize + 1.0
991 - fClength[iplan][icham]/2. + fgkHspace/2.;
992 zpos = -0.4 + 0.742/2.;
993 par[0] = 0.0;
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");
998 }
999 }
1000
1001 }
1002 }
1003
1004}
1005
1006//_____________________________________________________________________________
1007void AliTRDgeometry::GroupChamber(Int_t iplan, Int_t icham, Int_t *idtmed)
f7336fa3 1008{
1009 //
bd0f8685 1010 // Group volumes UA, UD, UF, UU in a single chamber (Air)
1011 // UA, UD, UF, UU are boxes
1012 // UT will be a box
0a770ac9 1013 //
bd0f8685 1014
1015 const Int_t kNparCha = 3;
1016
1017 Int_t iDet = GetDetectorSec(iplan,icham);
1018
1019 Float_t xyzMin[3];
1020 Float_t xyzMax[3];
1021 Float_t xyzOrig[3];
1022 Float_t xyzBoxd[3];
1023
1024 Char_t cTagV[5];
1025 Char_t cTagM[5];
1026
1027 for (Int_t i = 0; i < 3; i++) {
1028 xyzMin[i] = +9999; xyzMax[i] = -9999;
1029 }
1030
1031 for (Int_t i = 0; i < 3; i++) {
1032
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]);
1035
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]);
1038
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]);
1041
a797f961 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]);
bd0f8685 1044
1045 xyzOrig[i] = 0.5*(xyzMax[i]+xyzMin[i]);
1046 xyzBoxd[i] = 0.5*(xyzMax[i]-xyzMin[i]);
1047
1048 }
1049
1050 sprintf(cTagM,"UT%02d",iDet);
1051
1052 gMC->Gsvolu(cTagM,"BOX ",idtmed[1302-1],xyzBoxd,kNparCha);
1053
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],
1059 0,"ONLY");
1060
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],
1066 0,"ONLY");
1067
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],
1073 0,"ONLY");
1074
a797f961 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],
1080 0,"ONLY");
bd0f8685 1081
1082 sprintf(cTagV,"UT%02d",iDet);
1083 gMC->Gspos(cTagV,1,"UTI1",xyzOrig[0],xyzOrig[1],xyzOrig[2],0,"ONLY");
f7336fa3 1084
1085}
1086
1087//_____________________________________________________________________________
a5cadd36 1088Bool_t AliTRDgeometry::Local2Global(Int_t idet, Double_t *local
dde59437 1089 , Double_t *global) const
f7336fa3 1090{
1091 //
1092 // Converts local pad-coordinates (row,col,time) into
1093 // global ALICE reference frame coordinates (x,y,z)
1094 //
1095
793ff80c 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)
f7336fa3 1099
dde59437 1100 return Local2Global(iplan,icham,isect,local,global);
f7336fa3 1101
1102}
1103
1104//_____________________________________________________________________________
1105Bool_t AliTRDgeometry::Local2Global(Int_t iplan, Int_t icham, Int_t isect
dde59437 1106 , Double_t *local, Double_t *global) const
f7336fa3 1107{
1108 //
1109 // Converts local pad-coordinates (row,col,time) into
1110 // global ALICE reference frame coordinates (x,y,z)
1111 //
1112
3551db50 1113 AliTRDCommonParam* commonParam = AliTRDCommonParam::Instance();
2745a409 1114 if (!commonParam) {
1115 AliError("Could not get common parameters\n");
3551db50 1116 return kFALSE;
2745a409 1117 }
5443e65e 1118
3551db50 1119 AliTRDcalibDB* calibration = AliTRDcalibDB::Instance();
2745a409 1120 if (!calibration) {
1121 AliError("Could not get calibration data\n");
3551db50 1122 return kFALSE;
2745a409 1123 }
3551db50 1124
1125 AliTRDpadPlane *padPlane = commonParam->GetPadPlane(iplan,icham);
f7336fa3 1126
a5cadd36 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;
3551db50 1131 Float_t time0 = GetTime0(iplan);
f7336fa3 1132
7754cd1f 1133 Int_t idet = GetDetector(iplan, icham, isect);
1134
a5cadd36 1135 Double_t rot[3];
7754cd1f 1136 rot[0] = time0 - (timeSlice - calibration->GetT0(idet, col, row))
1137 * calibration->GetVdrift(idet, col, row)/calibration->GetSamplingFrequency();
a5cadd36 1138 rot[1] = padPlane->GetColPos(col) - 0.5 * padPlane->GetColSize(col);
1139 rot[2] = padPlane->GetRowPos(row) - 0.5 * padPlane->GetRowSize(row);
f7336fa3 1140
1141 // Rotate back to original position
1142 return RotateBack(idet,rot,global);
1143
1144}
1145
3d7b6a24 1146//_____________________________________________________________________________
a5cadd36 1147Bool_t AliTRDgeometry::Global2Local(Int_t mode, Double_t *local, Double_t *global
bd0f8685 1148 , Int_t* index) const
3d7b6a24 1149{
1150 //
1151 // Converts local pad-coordinates (row,col,time) into
1152 // global ALICE reference frame coordinates (x,y,z)
1153 //
e0d47c25 1154 // index[0] = plane number
1155 // index[1] = chamber number
1156 // index[2] = sector number
3d7b6a24 1157 //
1158 // mode=0 - local coordinate in y, z, x - rotated global
1159 // mode=2 - local coordinate in pad, and pad row, x - rotated global
1160 //
e0d47c25 1161
bd0f8685 1162 Int_t idet = GetDetector(index[0],index[1],index[2]); // Detector number
b4a9cd27 1163 RotateBack(idet,global,local);
bd0f8685 1164 if (mode == 0) return kTRUE;
3d7b6a24 1165
1166 return kTRUE;
1167
1168}
1169
a5cadd36 1170//_____________________________________________________________________________
3551db50 1171Bool_t AliTRDgeometry::Global2Detector(Double_t global[3], Int_t index[3])
3d7b6a24 1172{
1173 //
b4a9cd27 1174 // Find detector for given global point - Ideal geometry
1175 //
1176 //
e0d47c25 1177 // input = global position
1178 // output = index
1179 // index[0] = plane number
1180 // index[1] = chamber number
1181 // index[2] = sector number
3d7b6a24 1182 //
bd0f8685 1183
3d7b6a24 1184 //
b4a9cd27 1185 // Find sector
1186 //
1187 Float_t fi = TMath::ATan2(global[1],global[0]);
bd0f8685 1188 if (fi < 0) {
1189 fi += 2*TMath::Pi();
1190 }
1191 index[2] = fgkNsect - 1 - TMath::Nint((fi - GetAlpha()/2.)/GetAlpha());
1192
3d7b6a24 1193 //
b4a9cd27 1194 // Find plane
3d7b6a24 1195 //
1196 Float_t locx = global[0] * fRotA11[index[2]] + global[1] * fRotA12[index[2]];
1197 index[0] = 0;
3551db50 1198 Float_t max = locx - GetTime0(0);
3d7b6a24 1199 for (Int_t iplane=1; iplane<fgkNplan;iplane++){
3551db50 1200 Float_t dist = TMath::Abs(locx - GetTime0(iplane));
3d7b6a24 1201 if (dist < max){
1202 index[0] = iplane;
1203 max = dist;
1204 }
1205 }
bd0f8685 1206
b4a9cd27 1207 //
1208 // Find chamber
1209 //
1210 if (TMath::Abs(global[2]) < 0.5*GetChamberLength(index[0],2)){
1211 index[1]=2;
bd0f8685 1212 }
1213 else{
b4a9cd27 1214 Double_t localZ = global[2];
bd0f8685 1215 if (global[2] > 0){
b4a9cd27 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;
1218 }
1219 else{
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;
1222 }
1223 }
bd0f8685 1224
3d7b6a24 1225 return kTRUE;
3d7b6a24 1226
bd0f8685 1227}
3d7b6a24 1228
f7336fa3 1229//_____________________________________________________________________________
a5cadd36 1230Bool_t AliTRDgeometry::Rotate(Int_t d, Double_t *pos, Double_t *rot) const
f7336fa3 1231{
1232 //
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>.
1236 //
1237
793ff80c 1238 Int_t sector = GetSector(d);
f7336fa3 1239
793ff80c 1240 rot[0] = pos[0] * fRotA11[sector] + pos[1] * fRotA12[sector];
1241 rot[1] = -pos[0] * fRotA21[sector] + pos[1] * fRotA22[sector];
f7336fa3 1242 rot[2] = pos[2];
1243
1244 return kTRUE;
1245
1246}
1247
1248//_____________________________________________________________________________
a5cadd36 1249Bool_t AliTRDgeometry::RotateBack(Int_t d, Double_t *rot, Double_t *pos) const
f7336fa3 1250{
1251 //
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>.
1255 //
1256
793ff80c 1257 Int_t sector = GetSector(d);
f7336fa3 1258
793ff80c 1259 pos[0] = rot[0] * fRotB11[sector] + rot[1] * fRotB12[sector];
1260 pos[1] = -rot[0] * fRotB21[sector] + rot[1] * fRotB22[sector];
6f1e466d 1261 pos[2] = rot[2];
f7336fa3 1262
1263 return kTRUE;
1264
1265}
1266
1267//_____________________________________________________________________________
3551db50 1268Int_t AliTRDgeometry::GetDetectorSec(Int_t p, Int_t c)
0a770ac9 1269{
1270 //
1271 // Convert plane / chamber into detector number for one single sector
1272 //
1273
1274 return (p + c * fgkNplan);
1275
1276}
1277
1278//_____________________________________________________________________________
3551db50 1279Int_t AliTRDgeometry::GetDetector(Int_t p, Int_t c, Int_t s)
f7336fa3 1280{
1281 //
1282 // Convert plane / chamber / sector into detector number
1283 //
1284
793ff80c 1285 return (p + c * fgkNplan + s * fgkNplan * fgkNcham);
f7336fa3 1286
1287}
1288
1289//_____________________________________________________________________________
afc51ac2 1290Int_t AliTRDgeometry::GetPlane(Int_t d) const
f7336fa3 1291{
1292 //
1293 // Reconstruct the plane number from the detector number
1294 //
1295
793ff80c 1296 return ((Int_t) (d % fgkNplan));
f7336fa3 1297
1298}
1299
1300//_____________________________________________________________________________
afc51ac2 1301Int_t AliTRDgeometry::GetChamber(Int_t d) const
f7336fa3 1302{
1303 //
1304 // Reconstruct the chamber number from the detector number
1305 //
1306
793ff80c 1307 return ((Int_t) (d % (fgkNplan * fgkNcham)) / fgkNplan);
f7336fa3 1308
1309}
1310
1311//_____________________________________________________________________________
afc51ac2 1312Int_t AliTRDgeometry::GetSector(Int_t d) const
f7336fa3 1313{
1314 //
1315 // Reconstruct the sector number from the detector number
1316 //
1317
793ff80c 1318 return ((Int_t) (d / (fgkNplan * fgkNcham)));
f7336fa3 1319
1320}
1321
8737e16f 1322//_____________________________________________________________________________
bdbb05bb 1323AliTRDgeometry* AliTRDgeometry::GetGeometry(AliRunLoader* runLoader)
1324{
1325 //
1326 // load the geometry from the galice file
1327 //
1328
1329 if (!runLoader) runLoader = AliRunLoader::GetRunLoader();
1330 if (!runLoader) {
2745a409 1331 //AliError("No run loader");
bdbb05bb 1332 return NULL;
1333 }
1334
1335 TDirectory* saveDir = gDirectory;
1336 runLoader->CdGAFile();
1337
ecb36af7 1338 // Try from the galice.root file
bdbb05bb 1339 AliTRDgeometry* geom = (AliTRDgeometry*) gDirectory->Get("TRDgeometry");
ecb36af7 1340
1341 if (!geom) {
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();
1346 }
2745a409 1347 if (!geom) {
1348 //AliError("Geometry not found");
1349 return NULL;
1350 }
bdbb05bb 1351
1352 saveDir->cd();
1353 return geom;
b4a9cd27 1354
bd0f8685 1355}
b4a9cd27 1356
1357//_____________________________________________________________________________
bd0f8685 1358Bool_t AliTRDgeometry::ReadGeoMatrices()
1359{
b4a9cd27 1360 //
1361 // Read geo matrices from current gGeoManager for each TRD sector
1362 //
1363
b4a9cd27 1364 if (!gGeoManager) return kFALSE;
1365 fMatrixArray = new TObjArray(kNdet);
1366 fMatrixCorrectionArray = new TObjArray(kNdet);
1367 fMatrixGeo = new TObjArray(kNdet);
1368 AliAlignObjAngles o;
bd0f8685 1369
b4a9cd27 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);
bd0f8685 1380
b4a9cd27 1381 //
2745a409 1382 // Local geo system z-x-y to x-y--z
b4a9cd27 1383 //
1384 fMatrixGeo->AddAt(new TGeoHMatrix(*m),lid);
1385
1386 TGeoRotation mchange;
1387 mchange.RotateY(90); mchange.RotateX(90);
bd0f8685 1388
b4a9cd27 1389 TGeoHMatrix gMatrix(mchange.Inverse());
1390 gMatrix.MultiplyLeft(m);
1391 fMatrixArray->AddAt(new TGeoHMatrix(gMatrix),lid);
bd0f8685 1392
b4a9cd27 1393 //
1394 // Cluster transformation matrix
1395 //
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);
bd0f8685 1402
b4a9cd27 1403 fMatrixCorrectionArray->AddAt(new TGeoHMatrix(rotMatrix),lid);
bd0f8685 1404
b4a9cd27 1405 }
1406 }
bd0f8685 1407
b4a9cd27 1408 return kTRUE;
b4a9cd27 1409
bd0f8685 1410}
b4a9cd27 1411