]> git.uio.no Git - u/mrichter/AliRoot.git/blame_incremental - FMD/AliFMDGeometryBuilder.cxx
Removing obsolete field maps
[u/mrichter/AliRoot.git] / FMD / AliFMDGeometryBuilder.cxx
... / ...
CommitLineData
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/* $Id$ */
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
20*/
21//____________________________________________________________________
22//
23// Builder of FMD geometry.
24//
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.
32//
33//
34
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 <TGeoTrd1.h> // ROOT_TGeoTrd1
40#include <TGeoCone.h> // ROOT_TGeoTrd1
41#include <TGeoVolume.h> // ROOT_TGeoVolume
42#include <TGeoXtru.h> // ROOT_TGeoXtru
43#include <TGeoPcon.h> // ROOT_TGeoPcon
44#include <TGeoTorus.h> // ROOT_TGeoTorus
45#include <TGeoCompositeShape.h>
46#include <TMath.h>
47#include <TVector2.h> // ROOT_TVector2
48#include <TVector3.h> // ROOT_TVector3
49//#include <TGeoMaterial.h> // ROOT_TGeoMaterial
50//#include <TGeoMedium.h> // ROOT_TGeoMedium
51//#include <TGeoPcon.h> // ROOT_TGeoPcon
52//#include <TGeoPolygon.h> // ROOT_TGeoPolygon
53
54#include "AliFMDGeometryBuilder.h" // ALIFMDGEOSIMULATOR_H
55#include "AliFMDGeometry.h" // ALIFMDGEOMETRY_H
56#include "AliFMDDetector.h" // ALIFMDDETECTOR_H
57#include "AliFMDRing.h" // ALIFMDRING_H
58#include "AliFMD1.h" // ALIFMD1_H
59#include "AliFMD2.h" // ALIFMD2_H
60#include "AliFMD3.h" // ALIFMD3_H
61// #include "AliFMD.h" // ALIFMD_H
62#include "AliFMDDebug.h" // ALILOG_H
63#include <iostream>
64
65//====================================================================
66ClassImp(AliFMDGeometryBuilder)
67#if 0
68 ; // This is here to keep Emacs for indenting the next line
69#endif
70
71//____________________________________________________________________
72const Char_t* AliFMDGeometryBuilder::fgkActiveName = "F%cAC";
73const Char_t* AliFMDGeometryBuilder::fgkSectorName = "F%cSC";
74const Char_t* AliFMDGeometryBuilder::fgkStripName = "F%cST";
75const Char_t* AliFMDGeometryBuilder::fgkSensorName = "F%cSE";
76const Char_t* AliFMDGeometryBuilder::fgkPCBName = "F%cPB";
77const Char_t* AliFMDGeometryBuilder::fgkCuName = "F%cCU";
78const Char_t* AliFMDGeometryBuilder::fgkChipName = "F%cCH";
79const Char_t* AliFMDGeometryBuilder::fgkLongLegName = "F%cLL";
80const Char_t* AliFMDGeometryBuilder::fgkShortLegName = "F%cSL";
81const Char_t* AliFMDGeometryBuilder::fgkFrontVName = "F%cFH";
82const Char_t* AliFMDGeometryBuilder::fgkBackVName = "F%cBH";
83const Char_t* AliFMDGeometryBuilder::fgkRingTopName = "F%cTV";
84const Char_t* AliFMDGeometryBuilder::fgkRingBotName = "F%cBV";
85const Char_t* AliFMDGeometryBuilder::fgkHCName = "F%dH%c";
86const Char_t* AliFMDGeometryBuilder::fgkIHCName = "F%dI%c";
87const Char_t* AliFMDGeometryBuilder::fgkNoseName = "F3SN";
88const Char_t* AliFMDGeometryBuilder::fgkBackName = "F%dSB";
89const Char_t* AliFMDGeometryBuilder::fgkTopName = "F%dSU";
90const Char_t* AliFMDGeometryBuilder::fgkBeamName = "F%dSL";
91const Char_t* AliFMDGeometryBuilder::fgkFlangeName = "F%dSF";
92const Char_t* AliFMDGeometryBuilder::fgkFMDDCuName = "F%cDC";
93const Char_t* AliFMDGeometryBuilder::fgkFMDDPCBName = "F%cDP";
94const Char_t* AliFMDGeometryBuilder::fgkFMDDChipName = "F%cDI";
95const Char_t* AliFMDGeometryBuilder::fgkFMDDName = "F%cDD";
96const Char_t* AliFMDGeometryBuilder::fgkFMDName = "F%dM%c";
97
98//____________________________________________________________________
99AliFMDGeometryBuilder::AliFMDGeometryBuilder()
100 : TTask("FMD", "Geomtry builder"),
101 fActiveId(0),
102 fDetailed(kTRUE),
103 fUseAssembly(kTRUE),
104 fSectorOff(0),
105 fModuleOff(0),
106 fRingOff(0),
107 fDetectorOff(0),
108 fSi(0),
109 fC(0),
110 fAl(0),
111 fPCB(0),
112 fChip(0),
113 fAir(0),
114 fPlastic(0),
115 fCopper(0),
116 fSteel(0)
117{
118 // Default constructor
119 fActiveId.Set(2);
120}
121
122//____________________________________________________________________
123AliFMDGeometryBuilder::AliFMDGeometryBuilder(Bool_t detailed)
124 : TTask("FMD", "Geometry builder"),
125 fActiveId(0),
126 fDetailed(detailed),
127 fUseAssembly(kTRUE),
128 fSectorOff(0),
129 fModuleOff(0),
130 fRingOff(0),
131 fDetectorOff(0),
132 fSi(0),
133 fC(0),
134 fAl(0),
135 fPCB(0),
136 fChip(0),
137 fAir(0),
138 fPlastic(0),
139 fCopper(0),
140 fSteel(0)
141{
142 // Normal constructor
143 //
144 // Parameters:
145 //
146 // fmd Pointer to AliFMD object
147 // detailed Whether to make a detailed simulation or not
148 //
149 fActiveId.Set(2);
150}
151
152//____________________________________________________________________
153TGeoShape*
154AliFMDGeometryBuilder::MakeXTRU(const TObjArray& verticies,
155 Double_t thick) const
156{
157 TArrayD xs(6);
158 TArrayD ys(6);
159 for (Int_t i = 0; i < 3; i++) {
160 TVector2* v = static_cast<TVector2*>(verticies.At(i+1));
161 xs[i] = v->Y();
162 ys[i] = -v->X();
163 xs[6-1-i] = v->Y();
164 ys[6-1-i] = v->X();
165 }
166 TGeoXtru* shape = new TGeoXtru(2);
167 shape->DefinePolygon(xs.fN, xs.fArray, ys.fArray);
168 shape->DefineSection(0, -thick/2);
169 shape->DefineSection(1, +thick/2);
170
171 return shape;
172}
173
174//____________________________________________________________________
175TGeoVolume*
176AliFMDGeometryBuilder::RingGeometry(AliFMDRing* r)
177{
178 // Setup the geometry of a ring. The defined TGeoVolume is
179 // returned, and should be used when setting up the rest of the
180 // volumes.
181 //
182 //
183 // Parameters:
184 //
185 // r Pointer to ring geometry object
186 //
187 // Returns:
188 // pointer to ring volume
189 //
190 if (!r) {
191 AliError("Didn't get a ring object");
192 return 0;
193 }
194 Char_t id = r->GetId();
195 Char_t rng = toupper(id);
196 const Char_t* lName = (rng == 'I' ? "inner" : "outer");
197 Double_t siThick = r->GetSiThickness();
198 Double_t pcbThick = r->GetPrintboardThickness();
199 Double_t cuThick = r->GetCopperThickness();
200 Double_t chipThick= r->GetChipThickness();
201 Double_t modSpace = r->GetModuleSpacing();
202 Double_t theta = r->GetTheta();
203
204 //------------------------------------------------------------------
205 // Sensor
206 // Physical sensor
207 TGeoShape* sensorShape = MakeXTRU(r->GetSensorVerticies(), siThick);
208 sensorShape->SetName(Form("FMD%c_physical_sensor", id));
209 sensorShape->SetTitle(Form("FMD %s physical sensor", lName));
210 TGeoVolume* sensorVolume = new TGeoVolume(Form(fgkSensorName, id),
211 sensorShape, fSi);
212 sensorVolume->SetTitle(Form("FMD %s Sensor", lName));
213 sensorVolume->VisibleDaughters(kFALSE);
214 Int_t sid = sensorVolume->GetNumber();
215
216 fSectorOff = -1;
217 fModuleOff = 1;
218 fRingOff = 2;
219 fDetectorOff = 3;
220 if (fDetailed) {
221 fSectorOff = 1;
222 fModuleOff = 4;
223 fRingOff = 5;
224 fDetectorOff = 6;
225 // Virtual volume shape to divide - This volume is only defined if
226 // the geometry is set to be detailed.
227 TGeoTubeSeg* activeShape = new TGeoTubeSeg(r->GetLowR(),
228 r->GetHighR(),
229 siThick / 2,
230 - theta,
231 + theta);
232 activeShape->SetName(Form(fgkActiveName, id));
233 activeShape->SetTitle(Form("FMD %s active area", lName));
234 TGeoVolume* activeVolume = new TGeoVolume(Form(fgkActiveName, id),
235 activeShape,fSi);
236 activeVolume->SetTitle(Form("FMD %s active area", lName));
237 TGeoVolume* sectorVolume = activeVolume->Divide(Form(fgkSectorName,id),
238 2, 2, -theta,
239 0,0,"N");
240
241 Int_t ns = r->GetNStrips();
242 Double_t stripoff = r->GetLowR(); // 0; // a->Mod();
243 Double_t dstrip = (r->GetHighR() - stripoff) / ns;
244
245 sectorVolume->SetTitle(Form("FMD %s sector", lName));
246 TGeoVolume* stripVolume = sectorVolume->Divide(Form(fgkStripName, id),
247 1, ns, stripoff, dstrip,
248 0, "SX");
249 stripVolume->SetTitle(Form("FMD %s strip", lName));
250 sid = stripVolume->GetNumber();
251 sensorVolume->AddNodeOverlap(activeVolume, 0);
252 }
253
254 switch (rng) {
255 case 'I': fActiveId[0] = sid; break;
256 case 'O': fActiveId[1] = sid; break;
257 }
258
259 //------------------------------------------------------------------
260 // Hybrid
261 // PCB layer of hybrid
262 TGeoShape* pcbShape = MakeXTRU(r->GetHybridVerticies(), pcbThick);
263 pcbShape->SetName(Form("FMD%c_hybrid_pcb", id));
264 pcbShape->SetTitle(Form("FMD %s hybrid PCB", lName));
265 TGeoVolume* pcbVolume = new TGeoVolume(Form(fgkPCBName, id), pcbShape, fPCB);
266 pcbVolume->SetTitle(Form("FMD %s hybrid PCB", lName));
267
268 // Copper layer
269 TGeoShape* cuShape = MakeXTRU(r->GetHybridVerticies(), cuThick);
270 cuShape->SetName(Form("FMD%c_hybrid_copper", id));
271 cuShape->SetTitle(Form("FMD %s hybrid copper", lName));
272 TGeoVolume* cuVolume = new TGeoVolume(Form(fgkCuName,id),cuShape,fCopper);
273 cuVolume->SetTitle(Form("FMD %s hybrid copper", lName));
274
275 // Chip layer
276 TGeoShape* chipShape = MakeXTRU(r->GetHybridVerticies(), chipThick);
277 chipShape->SetName(Form("FMD%c_hybrid_chip", id));
278 chipShape->SetTitle(Form("FMD %s hybrid chip", lName));
279 TGeoVolume* chipVolume = new TGeoVolume(Form(fgkChipName,id),chipShape,fChip);
280 chipVolume->SetTitle(Form("FMD %s hybrid chip", lName));
281
282 //------------------------------------------------------------------
283 // Legs
284 Double_t legr = r->GetLegRadius();
285 Double_t legl = r->GetLegLength();
286 Double_t lege = .05;
287
288 // Short leg shape
289 TGeoTube* shortLegShape = new TGeoTube(0, legr, (legl-lege) / 2);
290 shortLegShape->SetName(Form(fgkShortLegName, id));
291 shortLegShape->SetTitle(Form("FMD %s short support foot", lName));
292 TGeoVolume* shortLegVolume = new TGeoVolume(Form(fgkShortLegName, id),
293 shortLegShape, fCopper);
294 shortLegVolume->SetTitle(Form("FMD %s short support foot", lName));
295 // Long leg shape
296 TGeoTube* longLegShape = new TGeoTube(0, legr,
297 (legl - lege + modSpace) / 2);
298 longLegShape->SetName(Form(fgkLongLegName, id));
299 longLegShape->SetTitle(Form("FMD %s long support foot", lName));
300 TGeoVolume* longLegVolume = new TGeoVolume(Form(fgkLongLegName, id),
301 longLegShape, fCopper);
302 longLegVolume->SetTitle(Form("FMD %s long support foot", lName));
303
304
305
306 //------------------------------------------------------------------
307 // Placement of module volumes in assemblies
308 TArrayD xfs(3);
309 TArrayD yfs(3);
310 for (Int_t i = 0; i < 3; i++) {
311 TVector2* vv = r->GetFootPosition(i);
312 // TVector2 uu = vv->Rotate(TMath::Pi()/2);
313 xfs[i] = vv->Y();
314 yfs[i] = vv->X();
315 }
316
317 // Back container volume
318 TGeoVolume* backVolume = new TGeoVolumeAssembly(Form(fgkBackVName, id));
319 backVolume->SetTitle(Form("FMD %s back module", lName));
320 TGeoVolume* frontVolume = new TGeoVolumeAssembly(Form(fgkFrontVName, id));
321 frontVolume->SetTitle(Form("FMD %s front module", lName));
322
323 Double_t space = r->GetSpacing();
324 Double_t x = 0;
325 Double_t y = 0;
326 Double_t zb = siThick / 2;
327 Double_t zf = siThick / 2;
328 backVolume->AddNode(sensorVolume, 0, new TGeoTranslation(x, y, zb));
329 frontVolume->AddNode(sensorVolume, 0, new TGeoTranslation(x, y, zf));
330 zb += siThick / 2 + space + pcbThick / 2;
331 zf += siThick / 2 + space + pcbThick / 2;
332 backVolume->AddNode(pcbVolume, 0, new TGeoTranslation(x, y, zb));
333 frontVolume->AddNode(pcbVolume, 0, new TGeoTranslation(x, y, zf));
334 zb += (pcbThick + cuThick) / 2;
335 zf += (pcbThick + cuThick) / 2;
336 backVolume->AddNode(cuVolume, 0, new TGeoTranslation(0, 0, zf));
337 frontVolume->AddNode(cuVolume, 0, new TGeoTranslation(0, 0, zb));
338 zb += (cuThick + chipThick) / 2;
339 zf += (cuThick + chipThick) / 2;
340 backVolume->AddNode(chipVolume, 0, new TGeoTranslation(0, 0, zb));
341 frontVolume->AddNode(chipVolume, 0, new TGeoTranslation(0, 0, zf));
342 zb += pcbThick / 2 + (legl)/ 2 - lege;
343 zf += pcbThick / 2 + (legl + modSpace)/ 2 - lege;
344 for (Int_t i = 0; i < 3; i++) {
345 x = xfs[i]; // a->X() + legoff + legr;
346 y = yfs[i]; // 0;
347 backVolume->AddNode(shortLegVolume, i, new TGeoTranslation(x,y,zb));
348 frontVolume->AddNode(longLegVolume, i, new TGeoTranslation(x,y,zf));
349 }
350
351 //------------------------------------------------------------------
352 // FMDD
353 Double_t ddlr = r->GetFMDDLowR();
354 Double_t ddhr = r->GetFMDDHighR();
355 Double_t ddpt = r->GetFMDDPrintboardThickness();
356 Double_t ddct = r->GetFMDDCopperThickness();
357 Double_t ddit = r->GetFMDDChipThickness();
358 Double_t ddt = ddpt + ddct + ddit;
359
360 TString pcbName(Form(fgkFMDDPCBName, id));
361 TString cuName(Form(fgkFMDDCuName, id));
362 TString chipName(Form(fgkFMDDChipName, id));
363 new TGeoTubeSeg(Form("%s_inner", pcbName.Data()), ddlr, ddhr, ddpt/2,0,180);
364 new TGeoTubeSeg(Form("%s_inner", cuName.Data()), ddlr, ddhr, ddct/2,0,180);
365 new TGeoTubeSeg(Form("%s_inner", chipName.Data()), ddlr, ddhr, ddit/2,0,180);
366
367 Double_t clipWX = 0;
368 Double_t clipWY = 0;
369 Double_t clipY = 1;
370
371 if (rng == 'I') {
372 clipWX = ddhr;
373 clipWY = ddhr/2;
374 }
375 else {
376 clipWX = ddlr+3;
377 clipWY = ddhr/2;
378 }
379
380 new TGeoBBox(Form("%s_clip", pcbName.Data()), clipWX, clipWY, ddpt);
381 new TGeoBBox(Form("%s_clip", cuName.Data()), clipWX, clipWY, ddct);
382 new TGeoBBox(Form("%s_clip", chipName.Data()),clipWX, clipWY, ddit);
383 TGeoTranslation* trans = new TGeoTranslation(Form("%s_trans",
384 pcbName.Data()),
385 0, clipWY+clipY, 0);
386 trans->RegisterYourself();
387 TGeoShape* fmddPcbShape =
388 new TGeoCompositeShape(pcbName.Data(),
389 Form("%s_inner*%s_clip:%s_trans",
390 pcbName.Data(),
391 pcbName.Data(),
392 pcbName.Data()));
393 TGeoShape* fmddCuShape =
394 new TGeoCompositeShape(cuName.Data(),
395 Form("%s_inner*%s_clip:%s_trans",
396 cuName.Data(),
397 cuName.Data(),
398 pcbName.Data()));
399 TGeoShape* fmddChipShape =
400 new TGeoCompositeShape(chipName.Data(),
401 Form("%s_inner*%s_clip:%s_trans",
402 chipName.Data(),
403 chipName.Data(),
404 pcbName.Data()));
405 fmddPcbShape->SetTitle(Form("FMD %s digitiser PCB", lName));
406 fmddCuShape->SetTitle(Form("FMD %s digitiser copper", lName));
407 fmddChipShape->SetTitle(Form("FMD %s digitiser chip", lName));
408
409 TGeoVolume* fmddPcbVolume = new TGeoVolume(Form(fgkFMDDPCBName, id),
410 fmddPcbShape, fPCB);
411 TGeoVolume* fmddCuVolume = new TGeoVolume(Form(fgkFMDDCuName, id),
412 fmddCuShape, fCopper);
413 TGeoVolume* fmddChipVolume= new TGeoVolume(Form(fgkFMDDChipName, id),
414 fmddChipShape, fChip);
415 fmddPcbVolume->SetTitle(Form("FMD %s digitiser PCB", lName));
416 fmddCuVolume->SetTitle(Form("FMD %s digitiser copper", lName));
417 fmddChipVolume->SetTitle(Form("FMD %s digitiser chip", lName));
418
419 //------------------------------------------------------------------
420 // Half ring mother volumes.
421 TGeoVolume* ringTopVolume = new TGeoVolumeAssembly(Form(fgkRingTopName,id));
422 TGeoVolume* ringBotVolume = new TGeoVolumeAssembly(Form(fgkRingBotName,id));
423 TGeoVolume* halfRing = ringTopVolume;
424 ringTopVolume->SetTitle(Form("FMD %s top half-ring", lName));
425 ringBotVolume->SetTitle(Form("FMD %s bottom half-ring", lName));
426
427 //------------------------------------------------------------------
428 // Adding modules to half-rings
429 Int_t nmod = r->GetNModules();
430 AliFMDDebug(10, ("making %d modules in ring %c", nmod, id));
431 for (Int_t i = 0; i < nmod; i++) {
432 if (i == nmod / 2) halfRing = ringBotVolume;
433 Bool_t front = (i % 2 == (rng == 'I' ? 1 : 0));
434 TGeoVolume* vol = (front ? frontVolume : backVolume);
435 // vol->AddNode(sensorVolume, i, new TGeoTranslation(0,0,siThick/2));
436 Double_t z1 = (front ? -1 : 1) * modSpace / 2;
437 // Double_t z1 = (front ? 0 : modSpace);
438 Double_t th = (2 * i + 1) * theta;
439 TGeoMatrix* mat1 = new TGeoCombiTrans(0,0,z1,0);
440 mat1->RotateZ(th);
441 mat1->SetName(Form("FMD%c_module_%02d", id, i));
442 mat1->SetTitle(Form("FMD %s module %2d matrix", lName, i));
443 halfRing->AddNode(vol, i, mat1);
444 }
445
446 //------------------------------------------------------------------
447 // Add the FMDD
448 Double_t zi = r->GetFullDepth() - ddt;
449 Int_t n = 2;
450 for (Int_t i = 0; i < n; i++) {
451 halfRing = (i == 0 ? ringTopVolume : ringBotVolume);
452 Double_t phi = 360. / n * i;
453 TGeoRotation* rot = new TGeoRotation(Form("FMDD%c rotation %d", id, i));
454 rot->RotateZ(phi);
455 rot->SetTitle(Form("FMD %s digitiser rotation %2d", lName, i));
456 Double_t z = zi + ddpt / 2;
457 halfRing->AddNode(fmddPcbVolume, i, new TGeoCombiTrans(0,0,z,rot));
458 z += (ddpt + ddct) / 2;
459 halfRing->AddNode(fmddCuVolume, i, new TGeoCombiTrans(0,0,z,rot));
460 z += (ddct + ddit) / 2;
461 halfRing->AddNode(fmddChipVolume, i, new TGeoCombiTrans(0,0,z,rot));
462 }
463
464
465 return 0;
466}
467
468
469//____________________________________________________________________
470TGeoShape*
471AliFMDGeometryBuilder::HoneycombShape(Int_t id, Char_t ring,
472 double r1, double r2,
473 double w, double t, double c)
474{
475 // Make a honey comb shape from passed parameters.
476 // Parameters:
477 // id Detector identifier (1,2, or 3)
478 // ring Ring identifier ('I' or 'O')
479 // r1 Inner radius
480 // r2 Outer radius
481 // w width
482 // t Thickness of material
483 // c Clearing from horizontal.
484 // Return
485 // Pointer to newly allocated composite shape.
486 TString form = Form("FMD%d%c_%%c_%%c", id, ring);
487 double a1 = TMath::ATan2(c, r1) * 180 / TMath::Pi();
488
489 TString fn = Form(form.Data(),'F','1');
490 TString bn = Form(form.Data(),'B','1');
491 TString cn = Form(form.Data(),'C','O');
492 TString in = Form(form.Data(),'R','I');
493 TString on = Form(form.Data(),'R','O');
494 TString en = Form(form.Data(),'E','X');
495 double y = c;
496 double x = r1 * TMath::Cos(TMath::Pi()*a1/180);
497 new TGeoTubeSeg(fn.Data(),r1,r2,t/2,0,180);
498 new TGeoTubeSeg(bn.Data(),r1,r2,t/2,0,180);
499 new TGeoBBox(cn.Data(),(r2-r1)/2,t/2,w/2);
500 new TGeoTubeSeg(in.Data(),r1,r1+t,w/2,0,180);
501 new TGeoTubeSeg(on.Data(),r2-t,r2,w/2,0,180);
502 new TGeoBBox(en.Data(),r2+.005,c/2+.005,w/2+.005);
503
504 TString ftn = Form(form.Data(),'F','T');
505 TString btn = Form(form.Data(),'F','B');
506 TString ltn = Form(form.Data(),'C','L');
507 TString rtn = Form(form.Data(),'C','R');
508 TString etn = Form(form.Data(),'E','X');
509 (new TGeoTranslation(ftn.Data(),0,0,+w/2-t/2))->RegisterYourself();
510 (new TGeoTranslation(btn.Data(),0,0,-w/2+t/2))->RegisterYourself();
511 (new TGeoTranslation(ltn.Data(),-(x+(r2-r1)/2), y+t/2,0))->RegisterYourself();
512 (new TGeoTranslation(rtn.Data(),(x+(r2-r1)/2), y+t/2,0))->RegisterYourself();
513 (new TGeoTranslation(etn.Data(),0, c/2,0))->RegisterYourself();
514
515 TString comp(Form("(%s:%s+%s:%s+%s+%s+%s:%s+%s:%s)-%s:%s",
516 fn.Data(),ftn.Data(),
517 bn.Data(),btn.Data(),
518 in.Data(),on.Data(),
519 cn.Data(),ltn.Data(),
520 cn.Data(),rtn.Data(),
521 en.Data(),etn.Data()));
522 TGeoCompositeShape* shape = new TGeoCompositeShape(comp.Data());
523 shape->SetName(Form(fgkHCName,id,ring));
524 shape->SetTitle(Form("FMD%d%c Honeycomb shape", id, ring));
525 return shape;
526}
527
528//____________________________________________________________________
529TGeoVolume*
530AliFMDGeometryBuilder::TensionBox()
531{
532 static TGeoVolumeAssembly* tensionBox = 0;
533 if (tensionBox) return tensionBox;
534
535 TGeoBBox* tensionEndS = new TGeoBBox("FMD_tension_end", .6, 3, .25);
536 TGeoBBox* tensionTopS = new TGeoBBox("FMD_tension_top", .1, .5, 3.5);
537 TGeoVolume* tensionEndV = new TGeoVolume("FMD_tension_end", tensionEndS,fAl);
538 TGeoVolume* tensionTopV = new TGeoVolume("FMD_tension_top", tensionTopS,fAl);
539 tensionBox = new TGeoVolumeAssembly("FMD_tension_box");
540 tensionBox->AddNode(tensionEndV, 1, new TGeoTranslation(.6, 0, -3.75));
541 tensionBox->AddNode(tensionEndV, 2, new TGeoTranslation(.6, 0, +3.75));
542 tensionBox->AddNode(tensionTopV, 1, new TGeoTranslation(0.1, +2.5, 0));
543 tensionBox->AddNode(tensionTopV, 2, new TGeoTranslation(0.1, -2.5, 0));
544 tensionBox->AddNode(tensionTopV, 3, new TGeoTranslation(1.1, +2.5, 0));
545 tensionBox->AddNode(tensionTopV, 4, new TGeoTranslation(1.1, -2.5, 0));
546 return tensionBox;
547}
548
549
550//____________________________________________________________________
551TGeoVolume*
552AliFMDGeometryBuilder::DetectorGeometry(AliFMDDetector* d,
553 TGeoVolume* topMother,
554 TGeoVolume* botMother,
555 Double_t zMother,
556 TGeoVolume* innerTop,
557 TGeoVolume* innerBot,
558 TGeoVolume* outerTop,
559 TGeoVolume* outerBot)
560{
561 // Common stuff for setting up the FMD1, FMD2, and FMD3 geometries.
562 // This includes putting the Honeycomb support plates and the rings
563 // into the mother volumes.
564 //
565 // Parameeters:
566 // d The detector geometry to use
567 // mother The mother volume of the detector
568 // zmother The midpoint in global coordinates of detector vol.
569 // inner Pointer to inner ring volume
570 // outer Pointer to outer ring volume
571 //
572 // Returns:
573 // Pointer to mother (detector volume)
574 //
575 if (!d) return 0;
576 // Loop over the defined rings
577 for (int i = 0; i < 2; i++) {
578 AliFMDRing* r = 0;
579 Double_t lowr = 0;
580 Double_t highr = 0;
581 Double_t rz = 0;
582 TGeoVolume* tvol = 0;
583 TGeoVolume* bvol = 0;
584 switch (i) {
585 case 0:
586 r = d->GetInner();
587 lowr = d->GetInnerHoneyLowR();
588 highr = d->GetInnerHoneyHighR();
589 rz = d->GetInnerZ();
590 tvol = innerTop;
591 bvol = innerBot;
592 break;
593 case 1:
594 r = d->GetOuter();
595 lowr = d->GetOuterHoneyLowR();
596 highr = d->GetOuterHoneyHighR();
597 rz = d->GetOuterZ();
598 tvol = outerTop;
599 bvol = outerBot;
600 break;
601 }
602 if (!r) continue;
603 Char_t c = r->GetId();
604 Int_t id = d->GetId();
605 Double_t hcThick = r->GetHoneycombThickness();
606 Double_t alThick = r->GetAlThickness();
607 Double_t z = TMath::Abs(rz - zMother);
608
609 // Place ring in mother volume
610 // TGeoMatrix*matrix=new TGeoTranslation(Form("FMD%d%c trans",id,c),0,0,0);
611 AliFMDDebug(2, ("Placing volumes %s and %s in %s and %s at z=%f",
612 tvol->GetName(), bvol->GetName(),
613 topMother->GetName(), botMother->GetName(), z));
614 topMother->AddNode(tvol, Int_t(c), new TGeoTranslation(0,0,z));
615 botMother->AddNode(bvol, Int_t(c), new TGeoTranslation(0,0,z));
616
617 // Honeycomp
618 TGeoShape* hcSha = HoneycombShape(id, c, lowr, highr, hcThick, alThick);
619 TGeoVolume* hcVol = new TGeoVolume(Form(fgkHCName,id,c),hcSha,fAl);
620 hcVol->SetTitle(Form("FMD%d%c honeycomb shell", id, c));
621
622 z += (r->GetModuleDepth()
623 + r->GetModuleSpacing() / 2
624 + r->GetHoneycombThickness() / 2);
625
626 AliFMDDebug(15, ("Placing a copy of %s in %s and %s at z=%f",
627 hcVol->GetName(), topMother->GetName(),
628 botMother->GetName(), z));
629 // Add to top
630 topMother->AddNode(hcVol, 0, new TGeoTranslation(0, 0, z));
631
632 // Add to bottom
633 TGeoMatrix* bhcMatrix = new TGeoCombiTrans(0,0,z,0);
634 bhcMatrix->SetName(Form("FMD%d%c_honeycomp", id, c));
635 bhcMatrix->SetTitle(Form("FMD%d%c honeycomp", id, c));
636 bhcMatrix->RotateZ(180);
637 botMother->AddNode(hcVol, 1, bhcMatrix);
638 }
639 return 0;
640}
641
642//____________________________________________________________________
643TGeoVolume*
644AliFMDGeometryBuilder::FMD1Geometry(AliFMD1* fmd1,
645 TGeoVolume* innerTop,
646 TGeoVolume* innerBot)
647{
648 // Setup the FMD1 geometry. The FMD1 only has one ring, and no
649 // special support as it is at the momement.
650 //
651 // See also AliFMDGeometryBuilder::DetectorGeometry
652 //
653 if (!fmd1 || !innerTop || !innerBot) return 0;
654 AliFMDRing* r = fmd1->GetInner();
655 Double_t z = fmd1->GetInnerZ();
656
657 // `Top' or `Outside' master volume
658 TGeoVolume* fmd1TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
659 fmd1->GetId(), 'T'));
660 fmd1TopVolume->SetTitle("FMD1 top half");
661
662 // `Bottom' or `Inside' master volume
663 TGeoVolume* fmd1BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
664 fmd1->GetId(), 'B'));
665 fmd1BotVolume->SetTitle("FMD1 bottom half");
666
667 // Basic detector geometry
668 DetectorGeometry(fmd1, fmd1TopVolume, fmd1BotVolume, z,
669 innerTop, innerBot, 0, 0);
670
671 Double_t lidP[][3] = { { 0.00, 4.20, 20.95 },
672 { 0.15, 4.20, 20.95 },
673 { 0.15, 20.80, 20.95 },
674 { 3.00, 20.80, 20.95 },
675 { 3.00, 20.80, 22.30 },
676 { 3.15, 20.80, 22.30 },
677 { 3.15, 20.95, 24.65 },
678 { 3.30, 20.95, 24.65 },
679 { 3.30, 24.50, 24.65 },
680 { 6.80, 24.50, 24.65 },
681 { 6.80, 24.50, 26.00 },
682 { 6.95, 24.50, 26.00 } };
683 TGeoPcon* lidBaseS = new TGeoPcon("FMD1_lid_base", 0, 180, 12);
684 for (size_t i = 0; i < 12; i++)
685 lidBaseS->DefineSection(i, lidP[i][0], lidP[i][1], lidP[i][2]);
686
687
688 Double_t lidH[][2] = { { 7.84903, 24.15680 },
689 { 20.54900, 14.92970 },
690 { 21.99700, 12.70000 },
691 { 25.26090, 2.65502 } };
692 Double_t lidHR = .53 / 2;
693 Double_t lidHL = 0.16;
694
695 new TGeoTube("FMD1_lid_hole", 0, lidHR, lidHL/2);
696 TString lidComp("FMD1_lid_base-(");
697 TGeoTranslation* trans = 0;
698 for (size_t i = 0; i < 4; i++) {
699 trans = new TGeoTranslation(-lidH[i][0], lidH[i][1], 6.95-lidHL/2);
700 trans->SetName(Form("FMD1_lid_hole_mat%d", 2*i+0));
701 trans->RegisterYourself();
702 trans = new TGeoTranslation(+lidH[i][0], lidH[i][1], 6.95-lidHL/2);
703 trans->SetName(Form("FMD1_lid_hole_mat%d", 2*i+1));
704 trans->RegisterYourself();
705 lidComp.Append(Form("FMD1_lid_hole:FMD1_lid_hole_mat%d+"
706 "FMD1_lid_hole:FMD1_lid_hole_mat%d%c",
707 2 * i, 2 * i + 1, i == 3 ? ')' : '+'));
708 }
709 TGeoCompositeShape* lidS = new TGeoCompositeShape(lidComp.Data());
710 lidS->SetName("FMD1_lid");
711 TGeoVolume* lidV = new TGeoVolume("FMD1_lid", lidS, fC);
712 lidV->SetTransparency(63);
713
714 // Place top cover
715 Double_t lidZ = -(3.3 - r->GetModuleDepth() - r->GetModuleSpacing() / 2);
716 AliFMDDebug(1, ("FMD1 lid offset in Z=%f", lidZ));
717
718 for (Int_t i = 0; i < 2; i++) {
719 TGeoVolume* mother = (i == 0 ? fmd1TopVolume : fmd1BotVolume);
720 Double_t phi = 360. / 2 * i;
721 TGeoRotation* rot = new TGeoRotation(Form("FMD1_lid_rot%d",i));
722 rot->RotateZ(phi);
723 TGeoMatrix* matrix = new TGeoCombiTrans(Form("FMD1_lid_mat%d", i),
724 0, 0, lidZ, rot);
725 mother->AddNode(lidV, i, matrix);
726 }
727
728 // Must add this after filling the assembly.
729 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
730 // TGeoMatrix* matrix = new TGeoTranslation("FMD1 trans", 0, 0, z);
731 TGeoRotation* rot = new TGeoRotation("FMD1 rotatation");
732 rot->RotateZ(90);
733 TGeoMatrix* matrix = new TGeoCombiTrans("FMD1 trans", 0, 0, z, rot);
734
735 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
736 fmd1TopVolume->GetName(), fmd1BotVolume->GetName(), z));
737 top->AddNode(fmd1TopVolume, fmd1->GetId(), matrix);
738 top->AddNode(fmd1BotVolume, fmd1->GetId(), matrix);
739
740
741 // Survey points on V0A (screw holes for the FMD)
742 const Double_t icb[] = { +12.700, -21.997, 324.670 };
743 const Double_t ict[] = { +12.700, +21.997, 324.670 };
744 const Double_t ocb[] = { -12.700, -21.997, 324.670 };
745 const Double_t oct[] = { -12.700, +21.997, 324.670 };
746
747 TGeoTube* surveyShape = new TGeoTube("FMD1_survey_marker",
748 0, .2, .001);
749
750 TGeoMatrix* outMat = matrix;
751#if 0
752 if (gGeoManager->cd("/ALIC_1/F1MT_1"))
753 outMat = gGeoManager->GetCurrentMatrix();
754 else
755 AliWarning("Couldn't cd to /ALIC_1/F1MT_1");
756#endif
757
758 Double_t loct[3], locb[3];
759 outMat->MasterToLocal(oct, loct);
760 outMat->MasterToLocal(ocb, locb);
761 TGeoVolume* vOct = new TGeoVolume("V0L_OCT", surveyShape, fPlastic);
762 TGeoVolume* vOcb = new TGeoVolume("V0L_OCB", surveyShape, fPlastic);
763
764 fmd1TopVolume->AddNode(vOct, 1, new TGeoTranslation(loct[0],loct[1],loct[2]));
765 fmd1TopVolume->AddNode(vOcb, 1, new TGeoTranslation(locb[0],locb[1],locb[2]));
766
767
768 TGeoMatrix* inMat = matrix;
769#if 0
770 if (gGeoManager->cd("/ALIC_1/F1MT_1"))
771 inMat = gGeoManager->GetCurrentMatrix();
772 else
773 AliWarning("Couldn't cd to /ALIC_1/F1MT_1");
774#endif
775
776 Double_t lict[3], licb[3];
777 inMat->MasterToLocal(ict, lict);
778 inMat->MasterToLocal(icb, licb);
779 TGeoVolume* vIct = new TGeoVolume("V0L_ICT", surveyShape, fPlastic);
780 TGeoVolume* vIcb = new TGeoVolume("V0L_ICB", surveyShape, fPlastic);
781
782 fmd1BotVolume->AddNode(vIct, 1, new TGeoTranslation(lict[0],lict[1],lict[2]));
783 fmd1BotVolume->AddNode(vIcb, 1, new TGeoTranslation(licb[0],licb[1],licb[2]));
784
785 return 0;
786}
787
788//____________________________________________________________________
789TGeoVolume*
790AliFMDGeometryBuilder::FMD2Geometry(AliFMD2* fmd2,
791 TGeoVolume* innerTop,
792 TGeoVolume* innerBot,
793 TGeoVolume* outerTop,
794 TGeoVolume* outerBot)
795{
796 // Setup the FMD2 geometry. The FMD2 has no
797 // special support as it is at the momement.
798 //
799 // See also AliFMDGeometryBuilder::DetectorGeometry
800 //
801 if (!fmd2 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
802 AliFMDRing* r = fmd2->GetOuter();
803 Double_t z = fmd2->GetOuterZ();
804 Double_t framelr = 32.01; // fmd2->GetOuterHoneyHighR()+0.5;
805 Double_t framehr = 33.611; // fmd2->GetOuterHoneyHighR()+1.8;
806 Double_t framel = 14.8; // framehz - framelz;
807 // Double_t backth = 0.3;
808 Double_t backth = 0.03;
809 Double_t framelz = -(2.38
810 - r->GetModuleDepth()
811 - r->GetModuleSpacing() / 2);
812 // Double_t framelz = -0.8;
813 // Double_t framehz = framelz + backth + framel;
814 Double_t coverlr = 4.3; // fmd2->GetInner()->GetLowR()+1;
815 Double_t coverhr = framehr; // - 1;
816
817 TGeoVolume* fmd2TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
818 fmd2->GetId(), 'T'));
819 TGeoVolume* fmd2BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
820 fmd2->GetId(), 'B'));
821 fmd2TopVolume->SetTitle("FMD2 top half");
822 fmd2BotVolume->SetTitle("FMD2 bottom half");
823
824 DetectorGeometry(fmd2, fmd2TopVolume, fmd2BotVolume, z,
825 innerTop, innerBot, outerTop, outerBot);
826
827 TGeoVolumeAssembly* support = new TGeoVolumeAssembly("FMD2_support");
828 TGeoShape* cylinderShape = new TGeoTubeSeg(framelr,framehr,framel/2,0,180);
829 TGeoVolume* cylinderVolume = new TGeoVolume(Form(fgkBackName, fmd2->GetId()),
830 cylinderShape, fC);
831 TGeoShape* coverShape = new TGeoTubeSeg(coverlr,coverhr,backth/2,0,180);
832 TGeoVolume* coverVolume = new TGeoVolume(Form(fgkTopName, fmd2->GetId()),
833 coverShape, fC);
834 cylinderShape->SetName(Form(fgkBackName, fmd2->GetId()));
835 cylinderShape->SetTitle("FMD2 cylinder");
836 cylinderVolume->SetTitle("FMD2 cylinder");
837 cylinderVolume->SetTransparency(63);
838 coverShape->SetName(Form(fgkTopName, fmd2->GetId()));
839 coverShape->SetTitle("FMD2 cover");
840 coverVolume->SetTitle("FMD2 cover");
841 coverVolume->SetTransparency(63);
842
843 TGeoTranslation* trans = 0;
844 support->AddNode(coverVolume,1, new TGeoTranslation(0,0,backth/2));
845 support->AddNode(cylinderVolume, 1, new TGeoTranslation(0,0,backth+framel/2));
846
847
848 Double_t f1l = 15.6085;
849 Double_t f1w = 6;
850 Double_t f1d = 1;
851 Int_t nFiducialHoles = 4;
852 Double_t precHoles[][2] = { { 32.4948, 29.6663 },
853 { 33.9104, 31.0819 },
854 { 34.8177, 33.4035 },
855 { 35.5028, 32.6744 } };
856 Double_t precRadius = .25;
857 Double_t flangeA = TMath::Pi()/4;
858
859 new TGeoBBox("FMD2_flange_base", f1l/2, f1w/2, f1d/2);
860 new TGeoTube("FMD2_fiducial_hole", 0, precRadius, f1d/2+.1);
861 Double_t flangeX = framehr + f1l/2;
862 TVector2 flangeC(flangeX * TMath::Cos(flangeA),
863 flangeX * TMath::Sin(flangeA));
864 TString flangeComb("FMD2_flange_base-(");
865 new TGeoBBox("FMD2_flange_slit", 7./2, 1.5/2, f1d/2+.1);
866 trans = new TGeoTranslation(-f1l/2+1+7./2, +.5+1.5/2, 0);
867 trans->SetName("FMD2_flange_slit_mat1");
868 trans->RegisterYourself();
869 trans = new TGeoTranslation(-f1l/2+1+7./2, -.5-1.5/2, 0);
870 trans->SetName("FMD2_flange_slit_mat2");
871 trans->RegisterYourself();
872 flangeComb.Append("FMD2_flange_slit:FMD2_flange_slit_mat1+"
873 "FMD2_flange_slit:FMD2_flange_slit_mat2+");
874 for (Int_t i = 0; i < nFiducialHoles; i++) {
875 TVector2 v(precHoles[i][0], precHoles[i][1]);
876 v -= flangeC;
877 TVector2 r = v.Rotate(-flangeA);
878 TGeoTranslation* t1 = new TGeoTranslation(r.X(), r.Y(), 0);
879 TGeoTranslation* t2 = new TGeoTranslation(r.X(), -r.Y(), 0);
880 t1->SetName(Form("FMD2_fiducial_hole_rot%d", 2*i+0));
881 t2->SetName(Form("FMD2_fiducial_hole_rot%d", 2*i+1));
882 t1->RegisterYourself();
883 t2->RegisterYourself();
884 flangeComb.Append(Form("FMD2_fiducial_hole:FMD2_fiducial_hole_rot%d+"
885 "FMD2_fiducial_hole:FMD2_fiducial_hole_rot%d%c",
886 2*i+0, 2*i+1, (i == nFiducialHoles-1 ? ')' : '+')));
887 }
888 // Final flange shape, and at to full shape
889 TGeoCompositeShape* flangeS = new TGeoCompositeShape(flangeComb.Data());
890 flangeS->SetName("FMD2_flange");
891 TGeoVolume* flangeV = new TGeoVolume("FMD2_flange", flangeS, fAl);
892
893 Double_t f2l = 7;
894 Double_t f2d = 12.5;
895 Double_t f2w = 1;
896
897 new TGeoBBox("FMD2_flange_spacer_base", f2l/2, f2w/2, f2d/2);
898 new TGeoTube("FMD2_flange_spacer_hole", 0, 2.5, f2w/2+.1);
899 TGeoRotation* holeRot = new TGeoRotation();
900 holeRot->RotateY(90);
901 holeRot->RotateZ(90);
902 TGeoCombiTrans* combo = 0;
903 combo = new TGeoCombiTrans(0, 0, f2d/2-.5-2.5, holeRot);
904 combo->SetName("FMD2_flange_spacer_hole_mat1");
905 combo->RegisterYourself();
906 combo = new TGeoCombiTrans(0, 0, -f2d/2+.5+2.5, holeRot);
907 combo->SetName("FMD2_flange_spacer_hole_mat2");
908 combo->RegisterYourself();
909 TString spacerComp("FMD2_flange_spacer_base-("
910 "FMD2_flange_spacer_hole:FMD2_flange_spacer_hole_mat1+"
911 "FMD2_flange_spacer_hole:FMD2_flange_spacer_hole_mat2)");
912 TGeoCompositeShape* spacerS = new TGeoCompositeShape(spacerComp.Data());
913 TGeoVolume* spacerV = new TGeoVolume("FMD2_flange_spacer",
914 spacerS, fAl);
915
916 Double_t extraL = framehr-framelr;
917 TGeoBBox* extraS = new TGeoBBox("FMD2_flange_extra",
918 extraL/2, f1w/2, f1d/2);
919 TGeoVolume* extraV = new TGeoVolume("FMD2_flange_extra", extraS,fAl);
920 TGeoVolumeAssembly* wingV = new TGeoVolumeAssembly("FMD2_wing");
921 TGeoVolume* tension = TensionBox();
922 TGeoTube* wireS = new TGeoTube(0, .05, (framehr-coverlr)/2);
923 TGeoVolume* wireV = new TGeoVolume("FMD2_tension_wire",
924 wireS, fSteel);
925 wingV->AddNode(flangeV, 1, new TGeoTranslation(f1l/2, 0, f1d/2));
926 wingV->AddNode(flangeV, 2, new TGeoTranslation(f1l/2, 0, -f2d-f1d/2));
927 wingV->AddNode(extraV, 1, new TGeoCombiTrans(-extraL/2, 0, f1d/2, 0));
928 wingV->AddNode(spacerV, 1, new TGeoTranslation(1+f2l/2,-f2w/2+f1w/2,
929 -f2d/2));
930 wingV->AddNode(spacerV, 2, new TGeoTranslation(1+f2l/2,+f2w/2-f1w/2,
931 -f2d/2));
932 TGeoRotation* tensionR = new TGeoRotation;
933 tensionR->RotateY(90);
934 wingV->AddNode(tension, 1, new TGeoCombiTrans(4, 0, f1d+1.2, tensionR));
935 TGeoRotation* wireR = new TGeoRotation;
936 wireR->RotateY(90);
937 wingV->AddNode(wireV, 1, new TGeoCombiTrans(-(framehr-coverlr)/2, 0, f1d+1,
938 wireR));
939
940 TGeoCombiTrans* extraM1 = new TGeoCombiTrans(coverhr-extraL/2,0,0,0);
941 extraM1->RotateZ(45);
942 extraM1->RegisterYourself();
943 extraM1->SetName("FMD2_back_cover_slit1");
944 TGeoCombiTrans* extraM2 = new TGeoCombiTrans(coverhr-extraL/2,0,0,0);
945 extraM2->RotateZ(135);
946 extraM2->RegisterYourself();
947 extraM2->SetName("FMD2_back_cover_slit2");
948 TString coverComp(Form(fgkTopName, fmd2->GetId()));
949 coverComp.Append("-(FMD2_flange_extra:FMD2_back_cover_slit1"
950 "+FMD2_flange_extra:FMD2_back_cover_slit2)");
951 TGeoCompositeShape* cover2Shape = new TGeoCompositeShape(coverComp.Data());
952 cover2Shape->SetName("FMD2_back_cover");
953 TGeoVolume* cover2Volume = new TGeoVolume("FMD2_back_cover", cover2Shape,fC);
954 support->AddNode(cover2Volume,2,
955 new TGeoTranslation(0,0,backth+framel+backth/2));
956
957 TGeoCombiTrans* trans1 = new TGeoCombiTrans(framehr, 0, backth+framel, 0);
958 TGeoCombiTrans* trans2 = new TGeoCombiTrans(framehr, 0, backth+framel, 0);
959 trans1->RotateZ(45);
960 trans2->RotateZ(135);
961 support->AddNode(wingV, 1, trans1);
962 support->AddNode(wingV, 2, trans2);
963 AliFMDDebug(1, ("FMD2 support offset is %f", framelz));
964
965 for (Int_t i = 0; i < 2; i++) {
966 TGeoVolume* mother = (i < 1 ? fmd2TopVolume : fmd2BotVolume);
967
968 Double_t phi = 360. / 2 * i;
969 TGeoRotation* rot = new TGeoRotation(Form("FMD2 support rot %d",i));
970 rot->RotateZ(phi);
971 TGeoMatrix* matrix = new TGeoCombiTrans(0, 0, framelz, rot);
972 mother->AddNode(support, i, matrix);
973 }
974
975 // Must be done after filling the assemblies
976 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
977 TGeoMatrix* matrix = new TGeoTranslation("FMD2 trans", 0, 0, z);
978 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
979 fmd2TopVolume->GetName(), fmd2BotVolume->GetName(), z));
980 top->AddNode(fmd2TopVolume, fmd2->GetId(), matrix);
981 top->AddNode(fmd2BotVolume, fmd2->GetId(), matrix);
982
983
984 return 0;
985}
986
987//____________________________________________________________________
988TGeoVolume*
989AliFMDGeometryBuilder::FMD3Geometry(AliFMD3* fmd3,
990 TGeoVolume* innerTop,
991 TGeoVolume* innerBot,
992 TGeoVolume* outerTop,
993 TGeoVolume* outerBot)
994{
995 // Setup the FMD3 geometry. The FMD2 has a rather elaborate support
996 // structure, as the support will also support the vacuum
997 // beam-pipe.
998 //
999 // See also AliFMDGeometryBuilder::DetectorGeometry
1000 //
1001 if (!fmd3 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
1002
1003 //__________________________________________________________________
1004 // Basic detector set-up.
1005 TGeoVolume* fmd3TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
1006 fmd3->GetId(), 'T'));
1007 TGeoVolume* fmd3BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
1008 fmd3->GetId(), 'B'));
1009 fmd3TopVolume->SetTitle("FMD3 top half");
1010 fmd3BotVolume->SetTitle("FMD3 bottom half");
1011 DetectorGeometry(fmd3, fmd3TopVolume, fmd3BotVolume, fmd3->GetInnerZ(),
1012 innerTop, innerBot, outerTop, outerBot);
1013
1014 //__________________________________________________________________
1015 // Mother for all support material
1016 TGeoVolumeAssembly* support = new TGeoVolumeAssembly("F3SU");
1017 support->SetTitle("FMD3 support");
1018
1019 //__________________________________________________________________
1020 // Base of cone
1021 const TObjArray& radii = fmd3->ConeRadii();
1022 Int_t nRadii = radii.GetEntriesFast();
1023 TGeoPcon* coneBase = new TGeoPcon("FMD3_cone_base", 0., 180., nRadii);
1024 TVector3* r5 = 0;
1025 TVector3* r4 = 0;
1026 for (Int_t i = 0; i < nRadii; i++) {
1027 TVector3* v = static_cast<TVector3*>(radii.At(i));
1028 coneBase->DefineSection(i, v->X(), v->Y(), v->Z());
1029 if (i == 5) r5 = v;
1030 else if (i == 4) r4 = v;
1031 }
1032 TString coneComb("(FMD3_cone_base");
1033
1034 //__________________________________________________________________
1035 // Flanges
1036 double flangeDepth = fmd3->GetFlangeDepth() / 2;
1037 double flangeLength = fmd3->GetFlangeLength() / 2;
1038 double flangeWidth = fmd3->GetFlangeWidth() / 2;
1039 new TGeoBBox("FMD3_flange_base", flangeLength, flangeWidth, flangeDepth);
1040
1041 // Fiducial holes
1042 const TObjArray& fiducialHoles = fmd3->FiducialHoles();
1043 double fiducialRadius = fmd3->GetFiducialRadius();
1044#if 0
1045 TGeoTube* fiducialShape =
1046#endif
1047 new TGeoTube("FMD3_fiducial_hole", 0, fiducialRadius, flangeDepth+.1);
1048 Int_t nFiducialHoles = fiducialHoles.GetEntriesFast();
1049 double flangeAngle = TMath::Pi() / 4;
1050 double flangeX = r5->Y()+flangeLength;
1051 TVector2 flangeC(flangeX * TMath::Cos(flangeAngle),
1052 flangeX * TMath::Sin(flangeAngle));
1053 TString flangeComb("FMD3_flange_base-(");
1054#if 0// For debugging geometry
1055 TGeoVolume* fiducialVolume = new TGeoVolume("FMD3_fiducial", fiducialShape);
1056 fiducialVolume->SetLineColor(kGreen);
1057#endif
1058 for (Int_t i = 0; i < nFiducialHoles; i++) {
1059 TVector2& v = *(static_cast<TVector2*>(fiducialHoles.At(i)));
1060 v -= flangeC;
1061 TVector2 r = v.Rotate(-flangeAngle);
1062 TGeoTranslation* t1 = new TGeoTranslation(r.X(), r.Y(), 0);
1063 TGeoTranslation* t2 = new TGeoTranslation(r.X(), -r.Y(), 0);
1064 t1->SetName(Form("FMD3_fiducial_hole_rot%d", 2*i+0));
1065 t2->SetName(Form("FMD3_fiducial_hole_rot%d", 2*i+1));
1066 t1->RegisterYourself();
1067 t2->RegisterYourself();
1068 flangeComb.Append(Form("FMD3_fiducial_hole:FMD3_fiducial_hole_rot%d+"
1069 "FMD3_fiducial_hole:FMD3_fiducial_hole_rot%d%c",
1070 2*i+0, 2*i+1, (i == nFiducialHoles-1 ? ')' : '+')));
1071#if 0 // For debugging geometry
1072 support->AddNode(fiducialVolume, 2*i+0, t1);
1073 support->AddNode(fiducialVolume, 2*i+1, t2);
1074#endif
1075 }
1076
1077 // Final flange shape, and at to full shape
1078 TGeoCompositeShape* flangeShape = new TGeoCompositeShape(flangeComb.Data());
1079 flangeShape->SetName("FMD3_flange");
1080 for (Int_t i = 0; i < 2; i++) {
1081 TGeoRotation* rot = new TGeoRotation();
1082 rot->RotateZ((i+.5)*90);
1083 TVector2 v(flangeX, 0);
1084 TVector2 w = v.Rotate((i+.5) * 2 * flangeAngle);
1085 TGeoCombiTrans* trans = new TGeoCombiTrans(w.X(),w.Y(),
1086 r4->X()+flangeDepth, rot);
1087 trans->SetName(Form("FMD3_flange_matrix%d", i));
1088 trans->RegisterYourself();
1089 coneComb.Append(Form("+FMD3_flange:FMD3_flange_matrix%d", i));
1090 }
1091 coneComb.Append(")-(");
1092
1093 //__________________________________________________________________
1094 // Holes
1095 Double_t holeL = fmd3->GetHoleLength()/2;
1096 Double_t holeD = fmd3->GetHoleDepth()/2;
1097 Double_t holeLW = fmd3->GetHoleLowWidth()/2;
1098 Double_t holeHW = fmd3->GetHoleHighWidth()/2;
1099 Double_t holeA = fmd3->GetConeOuterAngle();
1100 Double_t holeA2 = TMath::Pi() - fmd3->GetConeOuterAngle();
1101 Double_t holeO = fmd3->GetHoleOffset();
1102 Double_t holeZ = (holeO
1103 + holeL * TMath::Cos(holeA)
1104 - holeD * TMath::Sin(holeA2));
1105 Double_t holeX = (fmd3->ConeR(-holeZ + fmd3->GetInnerZ() + fmd3->GetNoseZ())
1106 - holeD * TMath::Sin(holeA2));
1107 new TGeoTrd1("FMD3_cone_hole", holeLW, holeHW, holeD, holeL);
1108 TGeoTrd1* plateShape = new TGeoTrd1("FMD3_cooling_plate",
1109 holeLW, holeHW, .033, holeL);
1110 TGeoRotation* holeRot = new TGeoRotation();
1111 holeRot->SetName("FMD3_cone_hole_rotation");
1112 holeRot->RotateZ(90);
1113 holeRot->RotateY(holeA*180/TMath::Pi());
1114 TGeoCombiTrans* holeBaseTrans = new TGeoCombiTrans(holeX, 0, holeZ, holeRot);
1115 holeBaseTrans->SetName("FMD3_cone_hole_base_matrix");
1116 // TGeoRotation* plateRot = new TGeoRotation();
1117 // plateRot->SetName("FMD3_cone_plate_rotation");
1118 // plateRot->RotateZ(90);
1119 // plateRot->RotateY(plateA*180/TMath::Pi());
1120 // TGeoCombiTrans* plateBaseTrans = new
1121 // TGeoCombiTrans(plateX,0,plateZ,plateRot);
1122 TGeoVolume* plateVolume = new TGeoVolume("FMD3_cooling_plate",
1123 plateShape, fAl);
1124 plateShape->SetTitle("FMD3 cooling plate");
1125 plateVolume->SetTitle("FMD3 cooling plate");
1126 for (Int_t i = 0; i < 4; i++) {
1127 Double_t ang = 360. / 8 * (i + .5);
1128 TGeoCombiTrans* trans = new TGeoCombiTrans(*holeBaseTrans);
1129 trans->RotateZ(ang);
1130 trans->SetName(Form("FMD3_cone_hole_matrix%d", i));
1131 trans->RegisterYourself();
1132 trans = new TGeoCombiTrans(*holeBaseTrans);
1133 trans->RotateZ(ang);
1134 trans->SetName(Form("FMD3_cooling_plate_matrix%d", i));
1135 coneComb.Append(Form("FMD3_cone_hole:FMD3_cone_hole_matrix%d+", i));
1136 support->AddNode(plateVolume, i, trans);
1137 }
1138
1139 //__________________________________________________________________
1140 // Bolts
1141 Double_t boltRadius = fmd3->GetBoltRadius();
1142 Double_t boltLength = fmd3->GetBoltLength() / 2;
1143 Double_t boltZ1 = fmd3->GetInnerZ()+fmd3->GetNoseZ()-10;
1144 Double_t boltZ2 = fmd3->GetInnerZ()+fmd3->GetNoseZ()-20;
1145 Double_t boltXE = 2*boltLength*TMath::Cos(fmd3->GetConeOuterAngle());
1146 Double_t boltX1 = (fmd3->ConeR(boltZ1) - boltXE);
1147 Double_t boltX2 = (fmd3->ConeR(boltZ2) - boltXE);
1148
1149 new TGeoTube("FMD3_bolt_hole", 0, boltRadius, boltLength+.2);
1150 TGeoTube* boltShape = new TGeoTube("FMD3_bolt", 0, boltRadius, boltLength);
1151 TGeoRotation* boltRot = new TGeoRotation();
1152 boltRot->RotateY(-fmd3->GetConeOuterAngle()*180/TMath::Pi());
1153 TGeoCombiTrans* boltTrans1 = new TGeoCombiTrans(boltX1, 0, 10, boltRot);
1154 TGeoCombiTrans* boltTrans2 = new TGeoCombiTrans(boltX2, 0, 20, boltRot);
1155 TGeoCombiTrans* boltTrans3 = new TGeoCombiTrans(*boltTrans1);
1156 TGeoCombiTrans* boltTrans4 = new TGeoCombiTrans(*boltTrans2);
1157 boltTrans3->RotateZ(180);
1158 boltTrans4->RotateZ(180);
1159 boltTrans1->SetName("FMD3_bolt_matrix1");
1160 boltTrans2->SetName("FMD3_bolt_matrix2");
1161 boltTrans3->SetName("FMD3_bolt_matrix3");
1162 boltTrans4->SetName("FMD3_bolt_matrix4");
1163 boltTrans1->RegisterYourself();
1164 boltTrans2->RegisterYourself();
1165 boltTrans3->RegisterYourself();
1166 boltTrans4->RegisterYourself();
1167 coneComb.Append("FMD3_bolt_hole:FMD3_bolt_matrix1"
1168 "+FMD3_bolt_hole:FMD3_bolt_matrix2"
1169 "+FMD3_bolt_hole:FMD3_bolt_matrix3"
1170 "+FMD3_bolt_hole:FMD3_bolt_matrix4");
1171 TGeoVolume* boltVolume = new TGeoVolume("FMD3_bolt", boltShape, fSteel);
1172 support->AddNode(boltVolume, 1, boltTrans1);
1173 support->AddNode(boltVolume, 2, boltTrans2);
1174 boltShape->SetTitle("FMD3 steering bolt");
1175 boltVolume->SetTitle("FMD3 steering bolt");
1176
1177 //__________________________________________________________________
1178 // Cut-outs for tension wheel sheeve
1179 new TGeoBBox("FMD3_sheeve_hole", .55, .75, 1.16);
1180 Double_t sheeveHoleZ = fmd3->GetInnerZ() + fmd3->GetNoseZ() - .75;
1181 Double_t sheeveHoleR = fmd3->ConeR(sheeveHoleZ) - .55 + .2572222;
1182 TGeoCombiTrans* sheeveMat1 = new TGeoCombiTrans(sheeveHoleR,0,1.15,0);
1183 TGeoCombiTrans* sheeveMat2 = new TGeoCombiTrans(sheeveHoleR,0,1.15,0);
1184 sheeveMat1->RotateZ(45);
1185 sheeveMat2->RotateZ(135);
1186 sheeveMat1->SetName("FMD3_sheeve_hole_matrix1");
1187 sheeveMat2->SetName("FMD3_sheeve_hole_matrix2");
1188 sheeveMat1->RegisterYourself();
1189 sheeveMat2->RegisterYourself();
1190 coneComb.Append("+FMD3_sheeve_hole:FMD3_sheeve_hole_matrix1"
1191 "+FMD3_sheeve_hole:FMD3_sheeve_hole_matrix2)");
1192
1193 //__________________________________________________________________
1194 // Sheeve boxes
1195 Double_t sheeveL = 1.15;
1196 TGeoBBox* sheeveSideS = new TGeoBBox("FMD3_sheeve_side",
1197 .55, .25, 1.15);
1198 TGeoBBox* sheeveBackS = new TGeoBBox("FMD3_sheeve_back",
1199 .55, .25, .15);
1200 TGeoBBox* sheeveWingS = new TGeoBBox("FMD3_sheeve_wing",
1201 .15, .15, 1.15);
1202 TGeoPcon* sheeveWheelS = new TGeoPcon("FMD3_sheeve_wheel", 0, 360, 9);
1203 Double_t sheeveInnerR = 0; // .2;
1204 Double_t sheeveR = .875;
1205 Double_t sheeveWheelZ = .95;
1206 sheeveWheelS->DefineSection(0, -.25, sheeveInnerR, 1);
1207 sheeveWheelS->DefineSection(1, -.125, sheeveInnerR, 1);
1208 sheeveWheelS->DefineSection(2, -.125, sheeveInnerR, sheeveWheelZ);
1209 sheeveWheelS->DefineSection(3, -.0625, sheeveInnerR, sheeveR+.02);
1210 sheeveWheelS->DefineSection(4, 0.000, sheeveInnerR, sheeveR);
1211 sheeveWheelS->DefineSection(5, +.0625, sheeveInnerR, sheeveR+.02);
1212 sheeveWheelS->DefineSection(6, +.125, sheeveInnerR, sheeveWheelZ);
1213 sheeveWheelS->DefineSection(7, +.125, sheeveInnerR, 1);
1214 sheeveWheelS->DefineSection(8, +.25, sheeveInnerR, 1);
1215 TGeoVolume* sheeveSideV = new TGeoVolume("FMD3_sheeve_side",
1216 sheeveSideS, fPlastic);
1217 TGeoVolume* sheeveBackV = new TGeoVolume("FMD3_sheeve_back",
1218 sheeveBackS, fPlastic);
1219 TGeoVolume* sheeveWingV = new TGeoVolume("FMD3_sheeve_wing",
1220 sheeveWingS, fPlastic);
1221 TGeoVolume* sheeveWheelV= new TGeoVolume("FMD3_sheeve_wheel",
1222 sheeveWheelS, fPlastic);
1223 TGeoVolumeAssembly* sheeveBox = new TGeoVolumeAssembly("FMD3_sheeve_box");
1224 sheeveBox->AddNode(sheeveSideV, 1, new TGeoTranslation(0, -.5, 0));
1225 sheeveBox->AddNode(sheeveSideV, 2, new TGeoTranslation(0, +.5, 0));
1226 sheeveBox->AddNode(sheeveBackV, 1, new TGeoTranslation(0, 0, 2.0+.15-1.15));
1227 sheeveBox->AddNode(sheeveWingV, 1, new TGeoTranslation(.55-.15, -.90, 0));
1228 sheeveBox->AddNode(sheeveWingV, 2, new TGeoTranslation(.55-.15, +.90, 0));
1229 TGeoRotation* sheeveWheelR = new TGeoRotation;
1230 sheeveWheelR->RotateX(90);
1231 TGeoCombiTrans* sheeveWheelM = new TGeoCombiTrans(0, 0, sheeveWheelZ-sheeveL,
1232 sheeveWheelR);
1233 sheeveBox->AddNode(sheeveWheelV, 1, sheeveWheelM);
1234 support->AddNode(sheeveBox, 1, sheeveMat1);
1235 support->AddNode(sheeveBox, 2, sheeveMat2);
1236
1237
1238
1239 //__________________________________________________________________
1240 // Final cone
1241 TGeoCompositeShape* coneShape = new TGeoCompositeShape(coneComb.Data());
1242 coneShape->SetName("FMD3_cone");
1243 coneShape->SetTitle("FMD3 cone");
1244 TGeoVolume* coneVolume = new TGeoVolume("FMD3_Cone", coneShape, fC);
1245 coneVolume->SetLineColor(kRed);
1246 support->AddNode(coneVolume, 0, new TGeoTranslation(0, 0, 0));
1247
1248 //__________________________________________________________________
1249 // Tension boxes.
1250 TGeoVolume* tensionBox = TensionBox();
1251 Double_t tensionH = .6;
1252 Double_t tensionL = 4;
1253 Double_t tensionZ = 23.654;
1254 Double_t tensionR = fmd3->ConeR(fmd3->GetInnerZ() + fmd3->GetNoseZ()
1255 - tensionZ);
1256 Double_t tensionAr = fmd3->GetConeOuterAngle();
1257 Double_t tensionA = tensionAr * 180 / TMath::Pi();
1258 TGeoRotation* tensionQ = new TGeoRotation;
1259 tensionQ->RotateY(tensionA);
1260 TGeoCombiTrans* tensionM1 = new TGeoCombiTrans(tensionR,0,tensionZ, tensionQ);
1261 TGeoCombiTrans* tensionM2 = new TGeoCombiTrans(tensionR,0,tensionZ, tensionQ);
1262 tensionM1->RotateZ(45);
1263 tensionM2->RotateZ(135);
1264 support->AddNode(tensionBox, 1, tensionM1);
1265 support->AddNode(tensionBox, 2, tensionM2);
1266
1267 // Double_t tensionHR = 0.15;
1268 Double_t wireT = .1/2;
1269 Double_t wireZ1 = (tensionZ
1270 - tensionL * TMath::Cos(tensionAr)
1271 - tensionH * TMath::Sin(tensionAr));
1272 Double_t wireR1 = (tensionR
1273 - tensionL * TMath::Sin(tensionAr)
1274 + tensionH * TMath::Cos(tensionAr));
1275 AliFMDDebug(10, ("Wire Z1: %f=%f-%f*cos(%f)-%f*sin(%f)",
1276 wireZ1, tensionZ, tensionL, tensionAr, tensionH, tensionAr));
1277 AliFMDDebug(10, ("Wire R1: %f=%f-%f*sin(%f)-%f*cos(%f)",
1278 wireR1, tensionR, tensionL, tensionAr, tensionH, tensionAr));
1279
1280 Double_t wireStartA = 42.3 * TMath::Pi() / 180;
1281 Double_t wireZ2 = (sheeveWheelZ * (1 - TMath::Sin(wireStartA))
1282 // - sheeveL -
1283 - wireT * TMath::Sin(wireStartA));
1284 /* (sheeveWheelZ * (1 - TMath::Sin(wireStartA))
1285 - wireT * TMath::Sin(wireStartA)
1286 - sheeveL); */
1287 AliFMDDebug(10, ("wireZ2=%f=%f*(1-%f)", wireZ2, sheeveWheelZ,
1288 TMath::Sin(wireStartA)));
1289 Double_t wireR2 = (sheeveHoleR +
1290 sheeveWheelZ * TMath::Cos(wireStartA) +
1291 wireT * TMath::Cos(wireStartA));
1292 Double_t wireDR = wireR1-wireR2;
1293 Double_t wireDZ = wireZ1-wireZ2;
1294 Double_t wireL = TMath::Sqrt(wireDR*wireDR+wireDZ*wireDZ)-.01;
1295 Double_t wireAngle = TMath::ATan2(wireDR,wireDZ);
1296 TGeoTube* wireShape = new TGeoTube("FMD3_wire", 0, wireT, wireL/2);
1297 TGeoVolume* wireVolume = new TGeoVolume("FMD3_wire", wireShape,fSteel);
1298 TGeoRotation* wireRot = new TGeoRotation();
1299 wireRot->RotateY(180/TMath::Pi()*wireAngle);
1300 Double_t wireR = wireR2 + wireDR / 2;
1301 Double_t wireZ = wireZ2 + wireDZ / 2;
1302 TGeoCombiTrans* wireM1 = new TGeoCombiTrans(wireR, 0,wireZ, wireRot);
1303 TGeoCombiTrans* wireM2 = new TGeoCombiTrans(wireR, 0,wireZ, wireRot);
1304 wireM1->RotateZ(45);
1305 wireM2->RotateZ(135);
1306 support->AddNode(wireVolume, 1, wireM1);
1307 support->AddNode(wireVolume, 2, wireM2);
1308
1309
1310 TGeoTorus* wireTS = new TGeoTorus(sheeveWheelZ+wireT, 0, wireT, 0,
1311 90-wireStartA*180/TMath::Pi());
1312 TGeoVolume* wireTV = new TGeoVolume("FMD3_bend_wire",wireTS,fSteel);
1313 TGeoRotation* wireTR = new TGeoRotation;
1314 wireTR->RotateY(90);
1315 wireTR->RotateZ(-90);
1316 Double_t wireTZ = sheeveWheelZ;
1317 TGeoCombiTrans* wireTM1 = new TGeoCombiTrans(sheeveHoleR,0,wireTZ,wireTR);
1318 TGeoCombiTrans* wireTM2 = new TGeoCombiTrans(sheeveHoleR,0,wireTZ,wireTR);
1319 wireTM1->RotateZ(45);
1320 wireTM2->RotateZ(135);
1321 support->AddNode(wireTV, 1, wireTM1);
1322 support->AddNode(wireTV, 2, wireTM2);
1323
1324 Double_t colarR = 4.05;
1325 Double_t wireEL = sheeveHoleR - colarR;
1326 TGeoTube* wireES = new TGeoTube("FMD3_end_wire", 0, wireT, wireEL/2);
1327 TGeoVolume* wireEV = new TGeoVolume("FMD3_end_wire", wireES, fSteel);
1328 TGeoRotation* wireER = new TGeoRotation;
1329 wireER->RotateY(90);
1330 TGeoCombiTrans* wireEM1 = new TGeoCombiTrans(colarR+wireEL/2,0,
1331 -wireT,wireER);
1332 TGeoCombiTrans* wireEM2 = new TGeoCombiTrans(colarR+wireEL/2,0,
1333 -wireT,wireER);
1334 wireEM1->RotateZ(45);
1335 wireEM2->RotateZ(135);
1336 support->AddNode(wireEV, 1, wireEM1);
1337 support->AddNode(wireEV, 2, wireEM2);
1338
1339
1340
1341
1342 //__________________________________________________________________
1343 // Place support volumes in half-detector volumes
1344 Double_t z = fmd3->GetInnerZ();
1345 AliFMDDebug(1, ("FMD3 support at z=%f", -fmd3->GetNoseZ()));
1346 TGeoTranslation* t1 = new TGeoTranslation(0, 0, -fmd3->GetNoseZ());
1347 fmd3TopVolume->AddNode(support, 1, t1);
1348 TGeoCombiTrans* t2 = new TGeoCombiTrans(*t1);
1349 t2->RotateZ(180);
1350 fmd3BotVolume->AddNode(support, 2, t2);
1351
1352 TGeoRotation* rot = new TGeoRotation("FMD3 rotatation");
1353 rot->RotateY(180);
1354 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
1355 TGeoMatrix* mmatrix = new TGeoCombiTrans("FMD3 trans", 0, 0, z, rot);
1356 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
1357 fmd3TopVolume->GetName(), fmd3BotVolume->GetName(), z));
1358 top->AddNode(fmd3TopVolume, fmd3->GetId(), mmatrix);
1359 top->AddNode(fmd3BotVolume, fmd3->GetId(), mmatrix);
1360
1361 return 0;
1362}
1363
1364
1365//____________________________________________________________________
1366void
1367AliFMDGeometryBuilder::Exec(Option_t*)
1368{
1369 // Setup up the FMD geometry.
1370 AliFMDDebug(1, ("\tGeometry options: %s",
1371 (fDetailed ? "divided into strips" : "one volume")));
1372 if (!gGeoManager) {
1373 AliFatal("No TGeoManager defined");
1374 return;
1375 }
1376
1377 fSi = gGeoManager->GetMedium("FMD_Si$");
1378 fC = gGeoManager->GetMedium("FMD_Carbon$");
1379 fAl = gGeoManager->GetMedium("FMD_Aluminum$");
1380 fChip = gGeoManager->GetMedium("FMD_Si Chip$");
1381 fAir = gGeoManager->GetMedium("FMD_Air$");
1382 fPCB = gGeoManager->GetMedium("FMD_PCB$");
1383 fPlastic = gGeoManager->GetMedium("FMD_Plastic$");
1384 fCopper = gGeoManager->GetMedium("FMD_Copper$");
1385 fSteel = gGeoManager->GetMedium("FMD_Steel$");
1386
1387 if (!fSi||!fC||!fAl||!fChip||!fAir||!fPCB||!fPlastic||!fCopper||!fSteel) {
1388 AliError("Failed to get some or all tracking mediums");
1389 return;
1390 }
1391 AliFMDGeometry* fmd = AliFMDGeometry::Instance();
1392 AliFMDRing* inner = fmd->GetInner();
1393 AliFMDRing* outer = fmd->GetOuter();
1394 RingGeometry(inner);
1395 RingGeometry(outer);
1396 TGeoVolume* innerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
1397 inner->GetId()));
1398 TGeoVolume* innerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
1399 inner->GetId()));
1400 TGeoVolume* outerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
1401 outer->GetId()));
1402 TGeoVolume* outerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
1403 outer->GetId()));
1404
1405 FMD1Geometry(fmd->GetFMD1(), innerTop, innerBot);
1406 FMD2Geometry(fmd->GetFMD2(), innerTop, innerBot, outerTop, outerBot);
1407 FMD3Geometry(fmd->GetFMD3(), innerTop, innerBot, outerTop, outerBot);
1408#ifndef USE_PRE_MOVE
1409 fmd->SetSectorOff(fSectorOff);
1410 fmd->SetModuleOff(fModuleOff);
1411 fmd->SetRingOff(fRingOff);
1412 fmd->SetDetectorOff(fDetectorOff);
1413 fmd->SetActive(fActiveId.fArray, fActiveId.fN);
1414#endif
1415 // fmd->ExtractGeomInfo();
1416
1417}
1418
1419
1420//____________________________________________________________________
1421//
1422// EOF
1423//