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 **************************************************************************/
16 /** @file AliFMDGeometryBuilder.cxx
17 @author Christian Holm Christensen <cholm@nbi.dk>
18 @date Mon Mar 27 12:41:17 2006
19 @brief Class to build the FMD geometry
21 //____________________________________________________________________
23 // Builder of FMD geometry.
25 // This class takes care of actually building the geometry using the
26 // TGeo classes. Various parameters are fecthed from the
27 // AliFMDGeometry manager.
28 // Forward Multiplicity Detector based on Silicon wafers. This class
29 // contains the base procedures for the Forward Multiplicity detector
30 // Detector consists of 3 sub-detectors FMD1, FMD2, and FMD3, each of
31 // which has 1 or 2 rings of silicon sensors.
35 #include <TArrayD.h> // ROOT_TArrayD
36 #include <TGeoManager.h> // ROOT_TGeoManager
37 #include <TGeoMatrix.h> // ROOT_TGeoMatrix
38 #include <TGeoTube.h> // ROOT_TGeoTube
39 #include <TGeoTube.h> // ROOT_TGeoTube
40 #include <TGeoVolume.h> // ROOT_TGeoVolume
41 #include <TGeoXtru.h> // ROOT_TGeoXtru
43 #include <TVector2.h> // ROOT_TVector2
44 //#include <TGeoMaterial.h> // ROOT_TGeoMaterial
45 //#include <TGeoMedium.h> // ROOT_TGeoMedium
46 //#include <TGeoPcon.h> // ROOT_TGeoPcon
47 //#include <TGeoPolygon.h> // ROOT_TGeoPolygon
49 #include "AliFMDGeometryBuilder.h" // ALIFMDGEOSIMULATOR_H
50 #include "AliFMDGeometry.h" // ALIFMDGEOMETRY_H
51 #include "AliFMDDetector.h" // ALIFMDDETECTOR_H
52 #include "AliFMDRing.h" // ALIFMDRING_H
53 #include "AliFMD1.h" // ALIFMD1_H
54 #include "AliFMD2.h" // ALIFMD2_H
55 #include "AliFMD3.h" // ALIFMD3_H
56 // #include "AliFMD.h" // ALIFMD_H
57 #include "AliFMDDebug.h" // ALILOG_H
59 //====================================================================
60 ClassImp(AliFMDGeometryBuilder)
62 ; // This is here to keep Emacs for indenting the next line
65 //____________________________________________________________________
66 const Char_t* AliFMDGeometryBuilder::fgkActiveName = "F%cAC";
67 const Char_t* AliFMDGeometryBuilder::fgkSectorName = "F%cSC";
68 const Char_t* AliFMDGeometryBuilder::fgkStripName = "F%cST";
69 const Char_t* AliFMDGeometryBuilder::fgkSensorName = "F%cSE";
70 const Char_t* AliFMDGeometryBuilder::fgkPCBName = "F%cPB";
71 const Char_t* AliFMDGeometryBuilder::fgkCuName = "F%cCU";
72 const Char_t* AliFMDGeometryBuilder::fgkChipName = "F%cCH";
73 const Char_t* AliFMDGeometryBuilder::fgkLongLegName = "F%cLL";
74 const Char_t* AliFMDGeometryBuilder::fgkShortLegName = "F%cSL";
75 const Char_t* AliFMDGeometryBuilder::fgkFrontVName = "F%cFH";
76 const Char_t* AliFMDGeometryBuilder::fgkBackVName = "F%cBH";
77 const Char_t* AliFMDGeometryBuilder::fgkRingTopName = "F%cTV";
78 const Char_t* AliFMDGeometryBuilder::fgkRingBotName = "F%cBV";
79 const Char_t* AliFMDGeometryBuilder::fgkHCName = "F%dH%c";
80 const Char_t* AliFMDGeometryBuilder::fgkIHCName = "F%dI%c";
81 const Char_t* AliFMDGeometryBuilder::fgkNoseName = "F3SN";
82 const Char_t* AliFMDGeometryBuilder::fgkBackName = "F3SB";
83 const Char_t* AliFMDGeometryBuilder::fgkBeamName = "F3SL";
84 const Char_t* AliFMDGeometryBuilder::fgkFlangeName = "F3SF";
85 const Char_t* AliFMDGeometryBuilder::fgkFMDName = "F%dM%c";
87 //____________________________________________________________________
88 AliFMDGeometryBuilder::AliFMDGeometryBuilder()
89 : TTask("FMD", "Geomtry builder"),
106 // Default constructor
110 //____________________________________________________________________
111 AliFMDGeometryBuilder::AliFMDGeometryBuilder(Bool_t detailed)
112 : TTask("FMD", "Geometry builder"),
129 // Normal constructor
133 // fmd Pointer to AliFMD object
134 // detailed Whether to make a detailed simulation or not
140 //____________________________________________________________________
142 AliFMDGeometryBuilder::RingGeometry(AliFMDRing* r)
144 // Setup the geometry of a ring. The defined TGeoVolume is
145 // returned, and should be used when setting up the rest of the
151 // r Pointer to ring geometry object
154 // pointer to ring volume
157 AliError("Didn't get a ring object");
160 Char_t id = r->GetId();
161 Double_t siThick = r->GetSiThickness();
162 const Int_t knv = r->GetNVerticies();
163 TVector2* a = r->GetVertex(5);
164 TVector2* b = r->GetVertex(3);
165 TVector2* c = r->GetVertex(4);
166 Double_t theta = r->GetTheta();
167 Double_t off = (TMath::Tan(TMath::Pi() * theta / 180)
168 * r->GetBondingWidth());
169 Double_t rmax = b->Mod();
170 Double_t rmin = r->GetLowR();
171 Double_t pcbThick = r->GetPrintboardThickness();
172 Double_t cuThick = r->GetCopperThickness();
173 Double_t chipThick= r->GetChipThickness();
174 Double_t modSpace = r->GetModuleSpacing();
175 Double_t legr = r->GetLegRadius();
176 Double_t legl = r->GetLegLength();
177 Double_t legoff = r->GetLegOffset();
178 Int_t ns = r->GetNStrips();
179 Double_t stripoff = a->Mod();
180 Double_t dstrip = (rmax - stripoff) / ns;
181 Double_t space = r->GetSpacing();
184 for (Int_t i = 0; i < knv; i++) {
186 TVector2* vv = r->GetVertex(knv - 1 - i);
188 AliError(Form("Failed to get vertex # %d", knv - 1 - i));
195 // Shape of actual sensor
196 TGeoXtru* sensorShape = new TGeoXtru(2);
197 sensorShape->DefinePolygon(knv, xs.fArray, ys.fArray);
198 sensorShape->DefineSection(0, - siThick/2);
199 sensorShape->DefineSection(1, siThick/2);
200 TGeoVolume* sensorVolume = new TGeoVolume(Form(fgkSensorName, id),
202 sensorVolume->VisibleDaughters(kFALSE);
203 Int_t sid = sensorVolume->GetNumber();
213 // Virtual volume shape to divide - This volume is only defined if
214 // the geometry is set to be detailed.
215 TGeoTubeSeg* activeShape = new TGeoTubeSeg(rmin, rmax, siThick/2,
217 TGeoVolume* activeVolume = new TGeoVolume(Form(fgkActiveName, id),
219 TGeoVolume* sectorVolume = activeVolume->Divide(Form(fgkSectorName,id),
220 2, 2, -theta,0,0,"N");
221 TGeoVolume* stripVolume = sectorVolume->Divide(Form(fgkStripName, id),
222 1, ns, stripoff, dstrip,
224 sid = stripVolume->GetNumber();
225 sensorVolume->AddNodeOverlap(activeVolume, 0);
229 case 'i': case 'I': fActiveId[0] = sid; break;
230 case 'o': case 'O': fActiveId[1] = sid; break;
233 // Shape of Printed circuit Board
234 for (Int_t i = 0; i < knv / 2; i++) ys[i] -= off;
235 for (Int_t i = knv / 2; i < knv; i++) ys[i] += off;
236 TGeoXtru* pcbShape = new TGeoXtru(2);
237 pcbShape->DefinePolygon(knv, xs.fArray, ys.fArray);
238 pcbShape->DefineSection(0, - pcbThick/2);
239 pcbShape->DefineSection(1, pcbThick/2);
240 TGeoVolume* pcbVolume = new TGeoVolume(Form(fgkPCBName, id),
244 TGeoXtru* cuShape = new TGeoXtru(2);
245 cuShape->DefinePolygon(6, xs.fArray, ys.fArray);
246 cuShape->DefineSection(0, - cuThick/2);
247 cuShape->DefineSection(1, cuThick/2);
248 TGeoVolume* cuVolume = new TGeoVolume(Form(fgkCuName,id),cuShape,fCopper);
251 TGeoXtru* chipShape = new TGeoXtru(2);
252 chipShape->DefinePolygon(6, xs.fArray, ys.fArray);
253 chipShape->DefineSection(0, - chipThick/2);
254 chipShape->DefineSection(1, chipThick/2);
255 TGeoVolume* chipVolume = new TGeoVolume(Form(fgkChipName,id),
259 TGeoTube* shortLegShape = new TGeoTube(0, legr, legl / 2);
260 TGeoVolume* shortLegVolume = new TGeoVolume(Form(fgkShortLegName, id),
261 shortLegShape, fPlastic);
264 TGeoTube* longLegShape = new TGeoTube(0, legr, (legl + modSpace) / 2);
265 TGeoVolume* longLegVolume = new TGeoVolume(Form(fgkLongLegName, id),
266 longLegShape, fPlastic);
269 // Back container volume
270 TGeoVolume* backVolume = new TGeoVolumeAssembly(Form(fgkBackVName, id));
273 Double_t z = pcbThick / 2;
274 backVolume->AddNode(pcbVolume, 0, new TGeoTranslation(x,y,z));
275 z += (pcbThick + cuThick) / 2;
276 backVolume->AddNode(cuVolume, 0, new TGeoTranslation(0, 0, z));
277 z += (cuThick + chipThick) / 2;
278 backVolume->AddNode(chipVolume, 0, new TGeoTranslation(0, 0, z));
279 x = a->X() + legoff + legr;
281 z += pcbThick / 2 + legl / 2;
282 backVolume->AddNode(shortLegVolume, 0, new TGeoTranslation(x,y,z));
284 y = c->Y() - legoff - legr - off;
285 backVolume->AddNode(shortLegVolume, 1, new TGeoTranslation(x,y,z));
287 backVolume->AddNode(shortLegVolume, 2, new TGeoTranslation(x,y,z));
289 // Front container volume
290 TGeoVolume* frontVolume = new TGeoVolumeAssembly(Form(fgkFrontVName, id));
294 frontVolume->AddNode(pcbVolume, 1, new TGeoTranslation(x,y,z));
295 z += (pcbThick + cuThick) / 2;
296 frontVolume->AddNode(cuVolume, 0, new TGeoTranslation(0, 0, z));
297 z += (cuThick + chipThick) / 2;
298 frontVolume->AddNode(chipVolume, 0, new TGeoTranslation(0, 0, z));
299 x = a->X() + legoff + legr;
301 z += pcbThick / 2 + (legl + modSpace)/ 2;
302 frontVolume->AddNode(longLegVolume, 0, new TGeoTranslation(x,y,z));
304 y = c->Y() - legoff - legr - off;
305 frontVolume->AddNode(longLegVolume, 1, new TGeoTranslation(x,y,z));
307 frontVolume->AddNode(longLegVolume, 2, new TGeoTranslation(x,y,z));
309 // Half ring mother volumes.
310 TGeoVolume* ringTopVolume = new TGeoVolumeAssembly(Form(fgkRingTopName,id));
311 TGeoVolume* ringBotVolume = new TGeoVolumeAssembly(Form(fgkRingBotName,id));
312 TGeoVolume* halfRing = ringTopVolume;
314 // Adding modules to half-rings
315 Int_t nmod = r->GetNModules();
316 AliFMDDebug(10, ("making %d modules in ring %c", nmod, id));
317 for (Int_t i = 0; i < nmod; i++) {
318 if (i == nmod / 2) halfRing = ringBotVolume;
319 Bool_t front = (i % 2 == 0);
320 Double_t z1 = siThick / 2 + (i % 2) * modSpace;
321 Double_t z2 = z1 + siThick / 2 + space;
322 Double_t th = (2 * i + 1) * theta;
323 TGeoVolume* vol = (front ? frontVolume : backVolume);
324 AliFMDDebug(20, ("Placing copy %d of %s and %s in %s at z=%f and %f, "
325 "and theta=%f", i, sensorVolume->GetName(),
326 vol->GetName(), halfRing->GetName(), z1, z2, th));
327 TGeoMatrix* mat1 = new TGeoCombiTrans(0,0,z1,0);
329 halfRing->AddNode(sensorVolume, i, mat1);
330 TGeoMatrix* mat2 = new TGeoCombiTrans(0,0,z2,0);
332 halfRing->AddNode(vol, i, mat2);
338 //____________________________________________________________________
340 AliFMDGeometryBuilder::DetectorGeometry(AliFMDDetector* d,
341 TGeoVolume* topMother,
342 TGeoVolume* botMother,
344 TGeoVolume* innerTop,
345 TGeoVolume* innerBot,
346 TGeoVolume* outerTop,
347 TGeoVolume* outerBot)
349 // Common stuff for setting up the FMD1, FMD2, and FMD3 geometries.
350 // This includes putting the Honeycomb support plates and the rings
351 // into the mother volumes.
354 // d The detector geometry to use
355 // mother The mother volume of the detector
356 // zmother The midpoint in global coordinates of detector vol.
357 // inner Pointer to inner ring volume
358 // outer Pointer to outer ring volume
361 // Pointer to mother (detector volume)
364 // Loop over the defined rings
365 for (int i = 0; i < 2; i++) {
370 TGeoVolume* tvol = 0;
371 TGeoVolume* bvol = 0;
375 lowr = d->GetInnerHoneyLowR();
376 highr = d->GetInnerHoneyHighR();
383 lowr = d->GetOuterHoneyLowR();
384 highr = d->GetOuterHoneyHighR();
391 Char_t c = r->GetId();
392 Int_t id = d->GetId();
393 Double_t hcThick = d->GetHoneycombThickness();
394 Double_t alThick = d->GetAlThickness();
395 Double_t z = TMath::Abs(rz - zMother);
397 // Place ring in mother volume
398 // TGeoMatrix*matrix=new TGeoTranslation(Form("FMD%d%c trans",id,c),0,0,0);
399 AliFMDDebug(5, ("Placing volumes %s and %s in %s and %s at z=%f",
400 tvol->GetName(), bvol->GetName(),
401 topMother->GetName(), botMother->GetName(), z));
402 topMother->AddNode(tvol, Int_t(c), new TGeoTranslation(0,0,z));
403 botMother->AddNode(bvol, Int_t(c), new TGeoTranslation(0,0,z));
406 TGeoTubeSeg* hcSha = new TGeoTubeSeg(lowr, highr, hcThick/2, 0, 180);
407 TGeoVolume* hcVol = new TGeoVolume(Form(fgkHCName,id,c),hcSha,fAl);
408 // Air in top of honeycomb
409 TGeoTubeSeg* ihcSha = new TGeoTubeSeg(lowr+alThick, highr - alThick,
410 (hcThick-alThick)/2, 0, 180);
411 TGeoVolume* ihcVol = new TGeoVolume(Form(fgkIHCName,id,c),ihcSha,fAir);
412 hcVol->AddNode(ihcVol, 0);
413 hcVol->VisibleDaughters(kFALSE);
414 hcVol->SetVisibility(kTRUE);
416 z += (r->GetSiThickness() +
418 r->GetPrintboardThickness() +
419 r->GetCopperThickness() +
420 r->GetChipThickness() +
421 r->GetModuleSpacing() +
425 AliFMDDebug(15, ("Placing a copy of %s in %s and %s at z=%f",
426 hcVol->GetName(), topMother->GetName(),
427 botMother->GetName(), z));
429 topMother->AddNode(hcVol, 0, new TGeoTranslation(0, 0, z));
432 TGeoMatrix* bhcMatrix = new TGeoCombiTrans(0,0,z,0);
433 bhcMatrix->RotateZ(180);
434 botMother->AddNode(hcVol, 1, bhcMatrix);
439 //____________________________________________________________________
441 AliFMDGeometryBuilder::FMD1Geometry(AliFMD1* fmd1,
442 TGeoVolume* innerTop,
443 TGeoVolume* innerBot)
445 // Setup the FMD1 geometry. The FMD1 only has one ring, and no
446 // special support as it is at the momement.
448 // See also AliFMDGeometryBuilder::DetectorGeometry
450 if (!fmd1 || !innerTop || !innerBot) return 0;
451 Double_t z = fmd1->GetInnerZ();
452 TGeoVolume* fmd1TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
453 fmd1->GetId(), 'T'));
454 TGeoVolume* fmd1BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
455 fmd1->GetId(), 'B'));
457 // Basic detector geometry
458 DetectorGeometry(fmd1, fmd1TopVolume, fmd1BotVolume, z,
459 innerTop, innerBot, 0, 0);
461 // Must add this after filling the assembly.
462 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
463 TGeoMatrix* matrix = new TGeoTranslation("FMD1 trans", 0, 0, z);
464 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
465 fmd1TopVolume->GetName(), fmd1BotVolume->GetName(), z));
466 top->AddNode(fmd1TopVolume, fmd1->GetId(), matrix);
467 top->AddNode(fmd1BotVolume, fmd1->GetId(), matrix);
472 //____________________________________________________________________
474 AliFMDGeometryBuilder::FMD2Geometry(AliFMD2* fmd2,
475 TGeoVolume* innerTop,
476 TGeoVolume* innerBot,
477 TGeoVolume* outerTop,
478 TGeoVolume* outerBot)
480 // Setup the FMD2 geometry. The FMD2 has no
481 // special support as it is at the momement.
483 // See also AliFMDGeometryBuilder::DetectorGeometry
485 if (!fmd2 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
486 Double_t z = fmd2->GetOuterZ();
487 TGeoVolume* fmd2TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
488 fmd2->GetId(), 'T'));
489 TGeoVolume* fmd2BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
490 fmd2->GetId(), 'B'));
492 DetectorGeometry(fmd2, fmd2TopVolume, fmd2BotVolume, z,
493 innerTop, innerBot, outerTop, outerBot);
495 // Must be done after filling the assemblies
496 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
497 TGeoMatrix* matrix = new TGeoTranslation("FMD2 trans", 0, 0, z);
498 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
499 fmd2TopVolume->GetName(), fmd2BotVolume->GetName(), z));
500 top->AddNode(fmd2TopVolume, fmd2->GetId(), matrix);
501 top->AddNode(fmd2BotVolume, fmd2->GetId(), matrix);
506 //____________________________________________________________________
508 AliFMDGeometryBuilder::FMD3Geometry(AliFMD3* fmd3,
509 TGeoVolume* innerTop,
510 TGeoVolume* innerBot,
511 TGeoVolume* outerTop,
512 TGeoVolume* outerBot)
514 // Setup the FMD3 geometry. The FMD2 has a rather elaborate support
515 // structure, as the support will also support the vacuum
518 // See also AliFMDGeometryBuilder::DetectorGeometry
520 if (!fmd3 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
521 Double_t nlen = fmd3->GetNoseLength();
522 Double_t nz = fmd3->GetNoseZ();
523 Double_t noser1 = fmd3->GetNoseLowR();
524 Double_t noser2 = fmd3->GetNoseHighR();
525 Double_t conel = fmd3->GetConeLength();
526 Double_t backl = fmd3->GetBackLength();
527 Double_t backr1 = fmd3->GetBackLowR();
528 Double_t backr2 = fmd3->GetBackHighR();
529 Double_t zdist = conel - backl - nlen;
530 Double_t tdist = backr2 - noser2;
531 Double_t beaml = TMath::Sqrt(zdist * zdist + tdist * tdist);
532 Double_t theta = -180. * TMath::ATan2(tdist, zdist) / TMath::Pi();
533 Double_t flanger = fmd3->GetFlangeR();
534 Double_t z = fmd3->GetInnerZ(); // fmd3->GetZ();
537 TGeoVolume* fmd3TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
538 fmd3->GetId(), 'T'));
539 TGeoVolume* fmd3BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
540 fmd3->GetId(), 'B'));
543 DetectorGeometry(fmd3, fmd3TopVolume, fmd3BotVolume, z,
544 innerTop, innerBot, outerTop, outerBot);
548 TGeoTubeSeg* noseShape = new TGeoTubeSeg(noser1, noser2, nlen / 2, 0, 180);
549 TGeoVolume* noseVolume = new TGeoVolume(fgkNoseName, noseShape, fC);
550 zi = -nz + nlen / 2 + z;
552 fmd3TopVolume->AddNode(noseVolume, 0, new TGeoTranslation(0, 0, zi));
553 TGeoMatrix* nmatrix = new TGeoCombiTrans(0, 0, zi, 0);
554 nmatrix->RotateZ(180);
555 fmd3BotVolume->AddNode(noseVolume, 1, nmatrix);
558 TGeoTubeSeg* backShape = new TGeoTubeSeg(backr1, backr2, backl / 2, 0, 180);
559 TGeoVolume* backVolume = new TGeoVolume(fgkBackName, backShape, fC);
560 zi = -nz + conel - backl / 2 + z;
561 fmd3TopVolume->AddNode(backVolume, 0, new TGeoTranslation(0, 0, zi));
562 TGeoMatrix* bmatrix = new TGeoCombiTrans(0, 0, zi, 0);
563 bmatrix->RotateZ(180);
564 fmd3BotVolume->AddNode(backVolume, 1, bmatrix);
570 TGeoBBox* flangeShape = new TGeoBBox((flanger - backr2) / 2,
571 fmd3->GetBeamWidth() / 2,
573 TGeoVolume* flangeVolume = new TGeoVolume(fgkFlangeName, flangeShape, fC);
574 n = fmd3->GetNFlange();
575 r = backr2 + (flanger - backr2) / 2;
576 TGeoVolume* mother = fmd3TopVolume;
577 for (Int_t i = 0; i < n; i++) {
578 if (i >= n / 2) mother = fmd3BotVolume;
579 Double_t phi = 360. / n * i + 180. / n;
580 Double_t x = r * TMath::Cos(TMath::Pi() / 180 * phi);
581 Double_t y = r * TMath::Sin(TMath::Pi() / 180 * phi);
582 AliFMDDebug(15, ("Placing flange %d in %s at (%f,%f,%f) r=%f, phi=%f",
583 i, mother->GetName(), x, y, zi, r, phi));
584 TGeoRotation* rot = new TGeoRotation;
586 TGeoMatrix* matrix = new TGeoCombiTrans(x, y, zi, rot);
587 mother->AddNode(flangeVolume, i, matrix);
591 TGeoBBox* beamShape = new TGeoBBox(fmd3->GetBeamThickness() / 2,
592 fmd3->GetBeamWidth() / 2 - .1,
594 TGeoVolume* beamVolume = new TGeoVolume(fgkBeamName, beamShape, fC);
595 n = fmd3->GetNBeam();
596 r = noser2 + tdist / 2;
597 zi = - nz + nlen + zdist / 2 + z;
598 mother = fmd3TopVolume;
599 for (Int_t i = 0; i < n; i++) {
600 if (i >= n / 2) mother = fmd3BotVolume;
601 Double_t phi = 360. / n * i;
602 Double_t x = r * TMath::Cos(TMath::Pi() / 180 * phi);
603 Double_t y = r * TMath::Sin(TMath::Pi() / 180 * phi);
604 TGeoRotation* rot = new TGeoRotation(Form("FMD3 beam rotation %d", i));
605 // Order is important
606 rot->RotateY(-theta);
608 TGeoMatrix* matrix = new TGeoCombiTrans(Form("FMD3 beam trans %d", i),
610 mother->AddNode(beamVolume, i, matrix);
613 z = fmd3->GetInnerZ();
614 TGeoRotation* rot = new TGeoRotation("FMD3 rotatation");
616 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
617 TGeoMatrix* mmatrix = new TGeoCombiTrans("FMD3 trans", 0, 0, z, rot);
618 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
619 fmd3TopVolume->GetName(), fmd3BotVolume->GetName(), z));
620 top->AddNode(fmd3TopVolume, fmd3->GetId(), mmatrix);
621 top->AddNode(fmd3BotVolume, fmd3->GetId(), mmatrix);
626 //____________________________________________________________________
628 AliFMDGeometryBuilder::Exec(Option_t*)
630 // Setup up the FMD geometry.
631 AliFMDDebug(1, ("\tGeometry options: %s",
632 (fDetailed ? "divided into strips" : "one volume")));
634 AliFatal("No TGeoManager defined");
638 fSi = gGeoManager->GetMedium("FMD_Si$");
639 fC = gGeoManager->GetMedium("FMD_Carbon$");
640 fAl = gGeoManager->GetMedium("FMD_Aluminum$");
641 fChip = gGeoManager->GetMedium("FMD_Si Chip$");
642 fAir = gGeoManager->GetMedium("FMD_Air$");
643 fPCB = gGeoManager->GetMedium("FMD_PCB$");
644 fPlastic = gGeoManager->GetMedium("FMD_Plastic$");
645 fCopper = gGeoManager->GetMedium("FMD_Copper$");
647 if (!fSi||!fC||!fAl||!fChip||!fAir||!fPCB||!fPlastic||!fCopper) {
648 AliError("Failed to get some or all tracking mediums");
651 AliFMDGeometry* fmd = AliFMDGeometry::Instance();
652 AliFMDRing* inner = fmd->GetInner();
653 AliFMDRing* outer = fmd->GetOuter();
656 TGeoVolume* innerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
658 TGeoVolume* innerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
660 TGeoVolume* outerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
662 TGeoVolume* outerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
665 FMD1Geometry(fmd->GetFMD1(), innerTop, innerBot);
666 FMD2Geometry(fmd->GetFMD2(), innerTop, innerBot, outerTop, outerBot);
667 FMD3Geometry(fmd->GetFMD3(), innerTop, innerBot, outerTop, outerBot);
669 fmd->SetSectorOff(fSectorOff);
670 fmd->SetModuleOff(fModuleOff);
671 fmd->SetRingOff(fRingOff);
672 fmd->SetDetectorOff(fDetectorOff);
673 fmd->SetActive(fActiveId.fArray, fActiveId.fN);
675 // fmd->ExtractGeomInfo();
680 //____________________________________________________________________