]> git.uio.no Git - u/mrichter/AliRoot.git/blame_incremental - FMD/AliFMDGeometryBuilder.cxx
enabling usage of several jet finders within one train (UE), changing cone radius...
[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 Double_t lidZStart = lidP[11][0];
684 TGeoPcon* lidBaseS = new TGeoPcon("FMD1_lid_base", 0, 180, 12);
685 for (size_t i = 0; i < 12; i++)
686 lidBaseS->DefineSection(i, lidP[i][0] - lidZStart, lidP[i][1], lidP[i][2]);
687
688
689 Double_t lidH[][2] = { { 7.84903, 24.15680 },
690 { 20.54900, 14.92970 },
691 { 21.99700, 12.70000 },
692 { 25.26090, 2.65502 } };
693 Double_t lidHR = .53 / 2;
694 Double_t lidHL = 0.16;
695
696 new TGeoTube("FMD1_lid_hole", 0, lidHR, lidHL/2);
697 TString lidComp("FMD1_lid_base-(");
698 TGeoTranslation* trans = 0;
699 for (size_t i = 0; i < 4; i++) {
700 trans = new TGeoTranslation(-lidH[i][0], lidH[i][1], /*6.95*/-lidHL/2);
701 trans->SetName(Form("FMD1_lid_hole_mat%d", 2*i+0));
702 trans->RegisterYourself();
703 trans = new TGeoTranslation(+lidH[i][0], lidH[i][1], /*6.95*/-lidHL/2);
704 trans->SetName(Form("FMD1_lid_hole_mat%d", 2*i+1));
705 trans->RegisterYourself();
706 lidComp.Append(Form("FMD1_lid_hole:FMD1_lid_hole_mat%d+"
707 "FMD1_lid_hole:FMD1_lid_hole_mat%d%c",
708 2 * i, 2 * i + 1, i == 3 ? ')' : '+'));
709 }
710 TGeoCompositeShape* lidS = new TGeoCompositeShape(lidComp.Data());
711 lidS->SetName("FMD1_lid");
712 TGeoVolume* lidV = new TGeoVolume("FMD1_lid", lidS, fC);
713 lidV->SetTransparency(63);
714
715 // Place top cover
716 Double_t lidZ = (lidZStart -
717 (3.3 - r->GetModuleDepth() - r->GetModuleSpacing() / 2));
718 AliFMDDebug(1, ("FMD1 lid offset in Z=%f", lidZ));
719
720 for (Int_t i = 0; i < 2; i++) {
721 TGeoVolume* mother = (i == 0 ? fmd1TopVolume : fmd1BotVolume);
722 Double_t phi = 360. / 2 * i;
723 TGeoRotation* rot = new TGeoRotation(Form("FMD1_lid_rot%d",i));
724 rot->RotateZ(phi);
725 TGeoMatrix* matrix = new TGeoCombiTrans(Form("FMD1_lid_mat%d", i),
726 0, 0, lidZ, rot);
727 mother->AddNode(lidV, i, matrix);
728 }
729
730 // Must add this after filling the assembly.
731 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
732 // TGeoMatrix* matrix = new TGeoTranslation("FMD1 trans", 0, 0, z);
733 TGeoRotation* rot = new TGeoRotation("FMD1 rotatation");
734 rot->RotateZ(90);
735 TGeoMatrix* matrix = new TGeoCombiTrans("FMD1 trans", 0, 0, z, rot);
736
737 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
738 fmd1TopVolume->GetName(), fmd1BotVolume->GetName(), z));
739 top->AddNode(fmd1TopVolume, fmd1->GetId(), matrix);
740 top->AddNode(fmd1BotVolume, fmd1->GetId(), matrix);
741
742
743 // Survey points on V0A (screw holes for the FMD)
744 const Double_t icb[] = { +12.700, -21.997, 324.670 };
745 const Double_t ict[] = { +12.700, +21.997, 324.670 };
746 const Double_t ocb[] = { -12.700, -21.997, 324.670 };
747 const Double_t oct[] = { -12.700, +21.997, 324.670 };
748
749 TGeoTube* surveyShape = new TGeoTube("FMD1_survey_marker",
750 0, .2, .001);
751
752 TGeoMatrix* outMat = matrix;
753#if 0
754 if (gGeoManager->cd("/ALIC_1/F1MT_1"))
755 outMat = gGeoManager->GetCurrentMatrix();
756 else
757 AliWarning("Couldn't cd to /ALIC_1/F1MT_1");
758#endif
759
760 Double_t loct[3], locb[3];
761 outMat->MasterToLocal(oct, loct);
762 outMat->MasterToLocal(ocb, locb);
763 TGeoVolume* vOct = new TGeoVolume("V0L_OCT", surveyShape, fPlastic);
764 TGeoVolume* vOcb = new TGeoVolume("V0L_OCB", surveyShape, fPlastic);
765
766 fmd1TopVolume->AddNode(vOct, 1, new TGeoTranslation(loct[0],loct[1],loct[2]));
767 fmd1TopVolume->AddNode(vOcb, 1, new TGeoTranslation(locb[0],locb[1],locb[2]));
768
769
770 TGeoMatrix* inMat = matrix;
771#if 0
772 if (gGeoManager->cd("/ALIC_1/F1MT_1"))
773 inMat = gGeoManager->GetCurrentMatrix();
774 else
775 AliWarning("Couldn't cd to /ALIC_1/F1MT_1");
776#endif
777
778 Double_t lict[3], licb[3];
779 inMat->MasterToLocal(ict, lict);
780 inMat->MasterToLocal(icb, licb);
781 TGeoVolume* vIct = new TGeoVolume("V0L_ICT", surveyShape, fPlastic);
782 TGeoVolume* vIcb = new TGeoVolume("V0L_ICB", surveyShape, fPlastic);
783
784 fmd1BotVolume->AddNode(vIct, 1, new TGeoTranslation(lict[0],lict[1],lict[2]));
785 fmd1BotVolume->AddNode(vIcb, 1, new TGeoTranslation(licb[0],licb[1],licb[2]));
786
787 return 0;
788}
789
790//____________________________________________________________________
791TGeoVolume*
792AliFMDGeometryBuilder::FMD2Geometry(AliFMD2* fmd2,
793 TGeoVolume* innerTop,
794 TGeoVolume* innerBot,
795 TGeoVolume* outerTop,
796 TGeoVolume* outerBot)
797{
798 // Setup the FMD2 geometry. The FMD2 has no
799 // special support as it is at the momement.
800 //
801 // See also AliFMDGeometryBuilder::DetectorGeometry
802 //
803 if (!fmd2 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
804 AliFMDRing* ring = fmd2->GetOuter();
805 Double_t z = fmd2->GetOuterZ();
806 Double_t framelr = 32.01; // fmd2->GetOuterHoneyHighR()+0.5;
807 Double_t framehr = 33.611; // fmd2->GetOuterHoneyHighR()+1.8;
808 Double_t framel = 14.8; // framehz - framelz;
809 // Double_t backth = 0.3;
810 Double_t backth = 0.03;
811 Double_t framelz = -(2.38
812 - ring->GetModuleDepth()
813 - ring->GetModuleSpacing() / 2);
814 // Double_t framelz = -0.8;
815 // Double_t framehz = framelz + backth + framel;
816 Double_t coverlr = 4.3; // fmd2->GetInner()->GetLowR()+1;
817 Double_t coverhr = framehr; // - 1;
818
819 TGeoVolume* fmd2TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
820 fmd2->GetId(), 'T'));
821 TGeoVolume* fmd2BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
822 fmd2->GetId(), 'B'));
823 fmd2TopVolume->SetTitle("FMD2 top half");
824 fmd2BotVolume->SetTitle("FMD2 bottom half");
825
826 DetectorGeometry(fmd2, fmd2TopVolume, fmd2BotVolume, z,
827 innerTop, innerBot, outerTop, outerBot);
828
829 TGeoVolumeAssembly* support = new TGeoVolumeAssembly("FMD2_support");
830 TGeoShape* cylinderShape = new TGeoTubeSeg(framelr,framehr,framel/2,0,180);
831 TGeoVolume* cylinderVolume = new TGeoVolume(Form(fgkBackName, fmd2->GetId()),
832 cylinderShape, fC);
833 TGeoShape* coverShape = new TGeoTubeSeg(coverlr,coverhr,backth/2,0,180);
834 TGeoVolume* coverVolume = new TGeoVolume(Form(fgkTopName, fmd2->GetId()),
835 coverShape, fC);
836 cylinderShape->SetName(Form(fgkBackName, fmd2->GetId()));
837 cylinderShape->SetTitle("FMD2 cylinder");
838 cylinderVolume->SetTitle("FMD2 cylinder");
839 cylinderVolume->SetTransparency(63);
840 coverShape->SetName(Form(fgkTopName, fmd2->GetId()));
841 coverShape->SetTitle("FMD2 cover");
842 coverVolume->SetTitle("FMD2 cover");
843 coverVolume->SetTransparency(63);
844
845 TGeoTranslation* trans = 0;
846 support->AddNode(coverVolume,1, new TGeoTranslation(0,0,backth/2));
847 support->AddNode(cylinderVolume, 1, new TGeoTranslation(0,0,backth+framel/2));
848
849
850 Double_t f1l = 15.6085;
851 Double_t f1w = 6;
852 Double_t f1d = 1;
853 Int_t nFiducialHoles = 4;
854 Double_t precHoles[][2] = { { 32.4948, 29.6663 },
855 { 33.9104, 31.0819 },
856 { 34.8177, 33.4035 },
857 { 35.5028, 32.6744 } };
858 Double_t precRadius = .25;
859 Double_t flangeA = TMath::Pi()/4;
860
861 new TGeoBBox("FMD2_flange_base", f1l/2, f1w/2, f1d/2);
862 new TGeoTube("FMD2_fiducial_hole", 0, precRadius, f1d/2+.1);
863 Double_t flangeX = framehr + f1l/2;
864 TVector2 flangeC(flangeX * TMath::Cos(flangeA),
865 flangeX * TMath::Sin(flangeA));
866 TString flangeComb("FMD2_flange_base-(");
867 new TGeoBBox("FMD2_flange_slit", 7./2, 1.5/2, f1d/2+.1);
868 trans = new TGeoTranslation(-f1l/2+1+7./2, +.5+1.5/2, 0);
869 trans->SetName("FMD2_flange_slit_mat1");
870 trans->RegisterYourself();
871 trans = new TGeoTranslation(-f1l/2+1+7./2, -.5-1.5/2, 0);
872 trans->SetName("FMD2_flange_slit_mat2");
873 trans->RegisterYourself();
874 flangeComb.Append("FMD2_flange_slit:FMD2_flange_slit_mat1+"
875 "FMD2_flange_slit:FMD2_flange_slit_mat2+");
876 for (Int_t i = 0; i < nFiducialHoles; i++) {
877 TVector2 v(precHoles[i][0], precHoles[i][1]);
878 v -= flangeC;
879 TVector2 r = v.Rotate(-flangeA);
880 TGeoTranslation* t1 = new TGeoTranslation(r.X(), r.Y(), 0);
881 TGeoTranslation* t2 = new TGeoTranslation(r.X(), -r.Y(), 0);
882 t1->SetName(Form("FMD2_fiducial_hole_rot%d", 2*i+0));
883 t2->SetName(Form("FMD2_fiducial_hole_rot%d", 2*i+1));
884 t1->RegisterYourself();
885 t2->RegisterYourself();
886 flangeComb.Append(Form("FMD2_fiducial_hole:FMD2_fiducial_hole_rot%d+"
887 "FMD2_fiducial_hole:FMD2_fiducial_hole_rot%d%c",
888 2*i+0, 2*i+1, (i == nFiducialHoles-1 ? ')' : '+')));
889 }
890 // Final flange shape, and at to full shape
891 TGeoCompositeShape* flangeS = new TGeoCompositeShape(flangeComb.Data());
892 flangeS->SetName("FMD2_flange");
893 TGeoVolume* flangeV = new TGeoVolume("FMD2_flange", flangeS, fAl);
894
895 Double_t f2l = 7;
896 Double_t f2d = 12.5;
897 Double_t f2w = 1;
898
899 new TGeoBBox("FMD2_flange_spacer_base", f2l/2, f2w/2, f2d/2);
900 new TGeoTube("FMD2_flange_spacer_hole", 0, 2.5, f2w/2+.1);
901 TGeoRotation* holeRot = new TGeoRotation();
902 holeRot->RotateY(90);
903 holeRot->RotateZ(90);
904 TGeoCombiTrans* combo = 0;
905 combo = new TGeoCombiTrans(0, 0, f2d/2-.5-2.5, holeRot);
906 combo->SetName("FMD2_flange_spacer_hole_mat1");
907 combo->RegisterYourself();
908 combo = new TGeoCombiTrans(0, 0, -f2d/2+.5+2.5, holeRot);
909 combo->SetName("FMD2_flange_spacer_hole_mat2");
910 combo->RegisterYourself();
911 TString spacerComp("FMD2_flange_spacer_base-("
912 "FMD2_flange_spacer_hole:FMD2_flange_spacer_hole_mat1+"
913 "FMD2_flange_spacer_hole:FMD2_flange_spacer_hole_mat2)");
914 TGeoCompositeShape* spacerS = new TGeoCompositeShape(spacerComp.Data());
915 TGeoVolume* spacerV = new TGeoVolume("FMD2_flange_spacer",
916 spacerS, fAl);
917
918 Double_t extraL = framehr-framelr;
919 TGeoBBox* extraS = new TGeoBBox("FMD2_flange_extra",
920 extraL/2, f1w/2, f1d/2);
921 TGeoVolume* extraV = new TGeoVolume("FMD2_flange_extra", extraS,fAl);
922 TGeoVolumeAssembly* wingV = new TGeoVolumeAssembly("FMD2_wing");
923 TGeoVolume* tension = TensionBox();
924 TGeoTube* wireS = new TGeoTube(0, .05, (framehr-coverlr)/2);
925 TGeoVolume* wireV = new TGeoVolume("FMD2_tension_wire",
926 wireS, fSteel);
927 wingV->AddNode(flangeV, 1, new TGeoTranslation(f1l/2, 0, f1d/2));
928 wingV->AddNode(flangeV, 2, new TGeoTranslation(f1l/2, 0, -f2d-f1d/2));
929 wingV->AddNode(extraV, 1, new TGeoCombiTrans(-extraL/2, 0, f1d/2, 0));
930 wingV->AddNode(spacerV, 1, new TGeoTranslation(1+f2l/2,-f2w/2+f1w/2,
931 -f2d/2));
932 wingV->AddNode(spacerV, 2, new TGeoTranslation(1+f2l/2,+f2w/2-f1w/2,
933 -f2d/2));
934 TGeoRotation* tensionR = new TGeoRotation;
935 tensionR->RotateY(90);
936 wingV->AddNode(tension, 1, new TGeoCombiTrans(4, 0, f1d+1.2, tensionR));
937 TGeoRotation* wireR = new TGeoRotation;
938 wireR->RotateY(90);
939 wingV->AddNode(wireV, 1, new TGeoCombiTrans(-(framehr-coverlr)/2, 0, f1d+1,
940 wireR));
941
942 TGeoCombiTrans* extraM1 = new TGeoCombiTrans(coverhr-extraL/2,0,0,0);
943 extraM1->RotateZ(45);
944 extraM1->RegisterYourself();
945 extraM1->SetName("FMD2_back_cover_slit1");
946 TGeoCombiTrans* extraM2 = new TGeoCombiTrans(coverhr-extraL/2,0,0,0);
947 extraM2->RotateZ(135);
948 extraM2->RegisterYourself();
949 extraM2->SetName("FMD2_back_cover_slit2");
950 TString coverComp(Form(fgkTopName, fmd2->GetId()));
951 coverComp.Append("-(FMD2_flange_extra:FMD2_back_cover_slit1"
952 "+FMD2_flange_extra:FMD2_back_cover_slit2)");
953 TGeoCompositeShape* cover2Shape = new TGeoCompositeShape(coverComp.Data());
954 cover2Shape->SetName("FMD2_back_cover");
955 TGeoVolume* cover2Volume = new TGeoVolume("FMD2_back_cover", cover2Shape,fC);
956 support->AddNode(cover2Volume,2,
957 new TGeoTranslation(0,0,backth+framel+backth/2));
958
959 TGeoCombiTrans* trans1 = new TGeoCombiTrans(framehr, 0, backth+framel, 0);
960 TGeoCombiTrans* trans2 = new TGeoCombiTrans(framehr, 0, backth+framel, 0);
961 trans1->RotateZ(45);
962 trans2->RotateZ(135);
963 support->AddNode(wingV, 1, trans1);
964 support->AddNode(wingV, 2, trans2);
965 AliFMDDebug(1, ("FMD2 support offset is %f", framelz));
966
967 for (Int_t i = 0; i < 2; i++) {
968 TGeoVolume* mother = (i < 1 ? fmd2TopVolume : fmd2BotVolume);
969
970 Double_t phi = 360. / 2 * i;
971 TGeoRotation* rot = new TGeoRotation(Form("FMD2 support rot %d",i));
972 rot->RotateZ(phi);
973 TGeoMatrix* matrix = new TGeoCombiTrans(0, 0, framelz, rot);
974 mother->AddNode(support, i, matrix);
975 }
976
977 // Must be done after filling the assemblies
978 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
979 TGeoMatrix* matrix = new TGeoTranslation("FMD2 trans", 0, 0, z);
980 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
981 fmd2TopVolume->GetName(), fmd2BotVolume->GetName(), z));
982 top->AddNode(fmd2TopVolume, fmd2->GetId(), matrix);
983 top->AddNode(fmd2BotVolume, fmd2->GetId(), matrix);
984
985
986 return 0;
987}
988
989//____________________________________________________________________
990TGeoVolume*
991AliFMDGeometryBuilder::FMD3Geometry(AliFMD3* fmd3,
992 TGeoVolume* innerTop,
993 TGeoVolume* innerBot,
994 TGeoVolume* outerTop,
995 TGeoVolume* outerBot)
996{
997 // Setup the FMD3 geometry. The FMD2 has a rather elaborate support
998 // structure, as the support will also support the vacuum
999 // beam-pipe.
1000 //
1001 // See also AliFMDGeometryBuilder::DetectorGeometry
1002 //
1003 if (!fmd3 || !innerTop || !innerBot || !outerTop || !outerBot) return 0;
1004
1005 //__________________________________________________________________
1006 // Basic detector set-up.
1007 TGeoVolume* fmd3TopVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
1008 fmd3->GetId(), 'T'));
1009 TGeoVolume* fmd3BotVolume = new TGeoVolumeAssembly(Form(fgkFMDName,
1010 fmd3->GetId(), 'B'));
1011 fmd3TopVolume->SetTitle("FMD3 top half");
1012 fmd3BotVolume->SetTitle("FMD3 bottom half");
1013 DetectorGeometry(fmd3, fmd3TopVolume, fmd3BotVolume, fmd3->GetInnerZ(),
1014 innerTop, innerBot, outerTop, outerBot);
1015
1016 //__________________________________________________________________
1017 // Mother for all support material
1018 TGeoVolumeAssembly* support = new TGeoVolumeAssembly("F3SU");
1019 support->SetTitle("FMD3 support");
1020
1021 //__________________________________________________________________
1022 // Base of cone
1023 const TObjArray& radii = fmd3->ConeRadii();
1024 Int_t nRadii = radii.GetEntriesFast();
1025 TGeoPcon* coneBase = new TGeoPcon("FMD3_cone_base", 0., 180., nRadii);
1026 TVector3* r5 = 0;
1027 TVector3* r4 = 0;
1028 for (Int_t i = 0; i < nRadii; i++) {
1029 TVector3* v = static_cast<TVector3*>(radii.At(i));
1030 coneBase->DefineSection(i, v->X(), v->Y(), v->Z());
1031 if (i == 5) r5 = v;
1032 else if (i == 4) r4 = v;
1033 }
1034 TString coneComb("(FMD3_cone_base");
1035
1036 //__________________________________________________________________
1037 // Flanges
1038 double flangeDepth = fmd3->GetFlangeDepth() / 2;
1039 double flangeLength = fmd3->GetFlangeLength() / 2;
1040 double flangeWidth = fmd3->GetFlangeWidth() / 2;
1041 new TGeoBBox("FMD3_flange_base", flangeLength, flangeWidth, flangeDepth);
1042
1043 // Fiducial holes
1044 const TObjArray& fiducialHoles = fmd3->FiducialHoles();
1045 double fiducialRadius = fmd3->GetFiducialRadius();
1046#if 0
1047 TGeoTube* fiducialShape =
1048#endif
1049 new TGeoTube("FMD3_fiducial_hole", 0, fiducialRadius, flangeDepth+.1);
1050 Int_t nFiducialHoles = fiducialHoles.GetEntriesFast();
1051 double flangeAngle = TMath::Pi() / 4;
1052 double flangeX = r5->Y()+flangeLength;
1053 TVector2 flangeC(flangeX * TMath::Cos(flangeAngle),
1054 flangeX * TMath::Sin(flangeAngle));
1055 TString flangeComb("FMD3_flange_base-(");
1056#if 0// For debugging geometry
1057 TGeoVolume* fiducialVolume = new TGeoVolume("FMD3_fiducial", fiducialShape);
1058 fiducialVolume->SetLineColor(kGreen);
1059#endif
1060 for (Int_t i = 0; i < nFiducialHoles; i++) {
1061 TVector2& v = *(static_cast<TVector2*>(fiducialHoles.At(i)));
1062 v -= flangeC;
1063 TVector2 r = v.Rotate(-flangeAngle);
1064 TGeoTranslation* t1 = new TGeoTranslation(r.X(), r.Y(), 0);
1065 TGeoTranslation* t2 = new TGeoTranslation(r.X(), -r.Y(), 0);
1066 t1->SetName(Form("FMD3_fiducial_hole_rot%d", 2*i+0));
1067 t2->SetName(Form("FMD3_fiducial_hole_rot%d", 2*i+1));
1068 t1->RegisterYourself();
1069 t2->RegisterYourself();
1070 flangeComb.Append(Form("FMD3_fiducial_hole:FMD3_fiducial_hole_rot%d+"
1071 "FMD3_fiducial_hole:FMD3_fiducial_hole_rot%d%c",
1072 2*i+0, 2*i+1, (i == nFiducialHoles-1 ? ')' : '+')));
1073#if 0 // For debugging geometry
1074 support->AddNode(fiducialVolume, 2*i+0, t1);
1075 support->AddNode(fiducialVolume, 2*i+1, t2);
1076#endif
1077 }
1078
1079 // Final flange shape, and at to full shape
1080 TGeoCompositeShape* flangeShape = new TGeoCompositeShape(flangeComb.Data());
1081 flangeShape->SetName("FMD3_flange");
1082 for (Int_t i = 0; i < 2; i++) {
1083 TGeoRotation* rot = new TGeoRotation();
1084 rot->RotateZ((i+.5)*90);
1085 TVector2 v(flangeX, 0);
1086 TVector2 w = v.Rotate((i+.5) * 2 * flangeAngle);
1087 TGeoCombiTrans* trans = new TGeoCombiTrans(w.X(),w.Y(),
1088 r4->X()+flangeDepth, rot);
1089 trans->SetName(Form("FMD3_flange_matrix%d", i));
1090 trans->RegisterYourself();
1091 coneComb.Append(Form("+FMD3_flange:FMD3_flange_matrix%d", i));
1092 }
1093 coneComb.Append(")-(");
1094
1095 //__________________________________________________________________
1096 // Holes
1097 Double_t holeL = fmd3->GetHoleLength()/2;
1098 Double_t holeD = fmd3->GetHoleDepth()/2;
1099 Double_t holeLW = fmd3->GetHoleLowWidth()/2;
1100 Double_t holeHW = fmd3->GetHoleHighWidth()/2;
1101 Double_t holeA = fmd3->GetConeOuterAngle();
1102 Double_t holeA2 = TMath::Pi() - fmd3->GetConeOuterAngle();
1103 Double_t holeO = fmd3->GetHoleOffset();
1104 Double_t holeZ = (holeO
1105 + holeL * TMath::Cos(holeA)
1106 - holeD * TMath::Sin(holeA2));
1107 Double_t holeX = (fmd3->ConeR(-holeZ + fmd3->GetInnerZ() + fmd3->GetNoseZ())
1108 - holeD * TMath::Sin(holeA2));
1109 new TGeoTrd1("FMD3_cone_hole", holeLW, holeHW, holeD, holeL);
1110 TGeoTrd1* plateShape = new TGeoTrd1("FMD3_cooling_plate",
1111 holeLW, holeHW, .033, holeL);
1112 TGeoRotation* holeRot = new TGeoRotation();
1113 holeRot->SetName("FMD3_cone_hole_rotation");
1114 holeRot->RotateZ(90);
1115 holeRot->RotateY(holeA*180/TMath::Pi());
1116 TGeoCombiTrans* holeBaseTrans = new TGeoCombiTrans(holeX, 0, holeZ, holeRot);
1117 holeBaseTrans->SetName("FMD3_cone_hole_base_matrix");
1118 // TGeoRotation* plateRot = new TGeoRotation();
1119 // plateRot->SetName("FMD3_cone_plate_rotation");
1120 // plateRot->RotateZ(90);
1121 // plateRot->RotateY(plateA*180/TMath::Pi());
1122 // TGeoCombiTrans* plateBaseTrans = new
1123 // TGeoCombiTrans(plateX,0,plateZ,plateRot);
1124 TGeoVolume* plateVolume = new TGeoVolume("FMD3_cooling_plate",
1125 plateShape, fAl);
1126 plateShape->SetTitle("FMD3 cooling plate");
1127 plateVolume->SetTitle("FMD3 cooling plate");
1128 for (Int_t i = 0; i < 4; i++) {
1129 Double_t ang = 360. / 8 * (i + .5);
1130 TGeoCombiTrans* trans = new TGeoCombiTrans(*holeBaseTrans);
1131 trans->RotateZ(ang);
1132 trans->SetName(Form("FMD3_cone_hole_matrix%d", i));
1133 trans->RegisterYourself();
1134 trans = new TGeoCombiTrans(*holeBaseTrans);
1135 trans->RotateZ(ang);
1136 trans->SetName(Form("FMD3_cooling_plate_matrix%d", i));
1137 coneComb.Append(Form("FMD3_cone_hole:FMD3_cone_hole_matrix%d+", i));
1138 support->AddNode(plateVolume, i, trans);
1139 }
1140
1141 //__________________________________________________________________
1142 // Bolts
1143 Double_t boltRadius = fmd3->GetBoltRadius();
1144 Double_t boltLength = fmd3->GetBoltLength() / 2;
1145 Double_t boltZ1 = fmd3->GetInnerZ()+fmd3->GetNoseZ()-10;
1146 Double_t boltZ2 = fmd3->GetInnerZ()+fmd3->GetNoseZ()-20;
1147 Double_t boltXE = 2*boltLength*TMath::Cos(fmd3->GetConeOuterAngle());
1148 Double_t boltX1 = (fmd3->ConeR(boltZ1) - boltXE);
1149 Double_t boltX2 = (fmd3->ConeR(boltZ2) - boltXE);
1150
1151 new TGeoTube("FMD3_bolt_hole", 0, boltRadius, boltLength+.2);
1152 TGeoTube* boltShape = new TGeoTube("FMD3_bolt", 0, boltRadius, boltLength);
1153 TGeoRotation* boltRot = new TGeoRotation();
1154 boltRot->RotateY(-fmd3->GetConeOuterAngle()*180/TMath::Pi());
1155 TGeoCombiTrans* boltTrans1 = new TGeoCombiTrans(boltX1, 0, 10, boltRot);
1156 TGeoCombiTrans* boltTrans2 = new TGeoCombiTrans(boltX2, 0, 20, boltRot);
1157 TGeoCombiTrans* boltTrans3 = new TGeoCombiTrans(*boltTrans1);
1158 TGeoCombiTrans* boltTrans4 = new TGeoCombiTrans(*boltTrans2);
1159 boltTrans3->RotateZ(180);
1160 boltTrans4->RotateZ(180);
1161 boltTrans1->SetName("FMD3_bolt_matrix1");
1162 boltTrans2->SetName("FMD3_bolt_matrix2");
1163 boltTrans3->SetName("FMD3_bolt_matrix3");
1164 boltTrans4->SetName("FMD3_bolt_matrix4");
1165 boltTrans1->RegisterYourself();
1166 boltTrans2->RegisterYourself();
1167 boltTrans3->RegisterYourself();
1168 boltTrans4->RegisterYourself();
1169 coneComb.Append("FMD3_bolt_hole:FMD3_bolt_matrix1"
1170 "+FMD3_bolt_hole:FMD3_bolt_matrix2"
1171 "+FMD3_bolt_hole:FMD3_bolt_matrix3"
1172 "+FMD3_bolt_hole:FMD3_bolt_matrix4");
1173 TGeoVolume* boltVolume = new TGeoVolume("FMD3_bolt", boltShape, fSteel);
1174 support->AddNode(boltVolume, 1, boltTrans1);
1175 support->AddNode(boltVolume, 2, boltTrans2);
1176 boltShape->SetTitle("FMD3 steering bolt");
1177 boltVolume->SetTitle("FMD3 steering bolt");
1178
1179 //__________________________________________________________________
1180 // Cut-outs for tension wheel sheeve
1181 new TGeoBBox("FMD3_sheeve_hole", .55, .75, 1.16);
1182 Double_t sheeveHoleZ = fmd3->GetInnerZ() + fmd3->GetNoseZ() - .75;
1183 Double_t sheeveHoleR = fmd3->ConeR(sheeveHoleZ) - .55 + .2572222;
1184 TGeoCombiTrans* sheeveMat1 = new TGeoCombiTrans(sheeveHoleR,0,1.15,0);
1185 TGeoCombiTrans* sheeveMat2 = new TGeoCombiTrans(sheeveHoleR,0,1.15,0);
1186 sheeveMat1->RotateZ(45);
1187 sheeveMat2->RotateZ(135);
1188 sheeveMat1->SetName("FMD3_sheeve_hole_matrix1");
1189 sheeveMat2->SetName("FMD3_sheeve_hole_matrix2");
1190 sheeveMat1->RegisterYourself();
1191 sheeveMat2->RegisterYourself();
1192 coneComb.Append("+FMD3_sheeve_hole:FMD3_sheeve_hole_matrix1"
1193 "+FMD3_sheeve_hole:FMD3_sheeve_hole_matrix2)");
1194
1195 //__________________________________________________________________
1196 // Sheeve boxes
1197 Double_t sheeveL = 1.15;
1198 TGeoBBox* sheeveSideS = new TGeoBBox("FMD3_sheeve_side",
1199 .55, .25, 1.15);
1200 TGeoBBox* sheeveBackS = new TGeoBBox("FMD3_sheeve_back",
1201 .55, .25, .15);
1202 TGeoBBox* sheeveWingS = new TGeoBBox("FMD3_sheeve_wing",
1203 .15, .15, 1.15);
1204 TGeoPcon* sheeveWheelS = new TGeoPcon("FMD3_sheeve_wheel", 0, 360, 9);
1205 Double_t sheeveInnerR = 0; // .2;
1206 Double_t sheeveR = .875;
1207 Double_t sheeveWheelZ = .95;
1208 sheeveWheelS->DefineSection(0, -.25, sheeveInnerR, 1);
1209 sheeveWheelS->DefineSection(1, -.125, sheeveInnerR, 1);
1210 sheeveWheelS->DefineSection(2, -.125, sheeveInnerR, sheeveWheelZ);
1211 sheeveWheelS->DefineSection(3, -.0625, sheeveInnerR, sheeveR+.02);
1212 sheeveWheelS->DefineSection(4, 0.000, sheeveInnerR, sheeveR);
1213 sheeveWheelS->DefineSection(5, +.0625, sheeveInnerR, sheeveR+.02);
1214 sheeveWheelS->DefineSection(6, +.125, sheeveInnerR, sheeveWheelZ);
1215 sheeveWheelS->DefineSection(7, +.125, sheeveInnerR, 1);
1216 sheeveWheelS->DefineSection(8, +.25, sheeveInnerR, 1);
1217 TGeoVolume* sheeveSideV = new TGeoVolume("FMD3_sheeve_side",
1218 sheeveSideS, fPlastic);
1219 TGeoVolume* sheeveBackV = new TGeoVolume("FMD3_sheeve_back",
1220 sheeveBackS, fPlastic);
1221 TGeoVolume* sheeveWingV = new TGeoVolume("FMD3_sheeve_wing",
1222 sheeveWingS, fPlastic);
1223 TGeoVolume* sheeveWheelV= new TGeoVolume("FMD3_sheeve_wheel",
1224 sheeveWheelS, fPlastic);
1225 TGeoVolumeAssembly* sheeveBox = new TGeoVolumeAssembly("FMD3_sheeve_box");
1226 sheeveBox->AddNode(sheeveSideV, 1, new TGeoTranslation(0, -.5, 0));
1227 sheeveBox->AddNode(sheeveSideV, 2, new TGeoTranslation(0, +.5, 0));
1228 sheeveBox->AddNode(sheeveBackV, 1, new TGeoTranslation(0, 0, 2.0+.15-1.15));
1229 sheeveBox->AddNode(sheeveWingV, 1, new TGeoTranslation(.55-.15, -.90, 0));
1230 sheeveBox->AddNode(sheeveWingV, 2, new TGeoTranslation(.55-.15, +.90, 0));
1231 TGeoRotation* sheeveWheelR = new TGeoRotation;
1232 sheeveWheelR->RotateX(90);
1233 TGeoCombiTrans* sheeveWheelM = new TGeoCombiTrans(0, 0, sheeveWheelZ-sheeveL,
1234 sheeveWheelR);
1235 sheeveBox->AddNode(sheeveWheelV, 1, sheeveWheelM);
1236 support->AddNode(sheeveBox, 1, sheeveMat1);
1237 support->AddNode(sheeveBox, 2, sheeveMat2);
1238
1239
1240
1241 //__________________________________________________________________
1242 // Final cone
1243 TGeoCompositeShape* coneShape = new TGeoCompositeShape(coneComb.Data());
1244 coneShape->SetName("FMD3_cone");
1245 coneShape->SetTitle("FMD3 cone");
1246 TGeoVolume* coneVolume = new TGeoVolume("FMD3_Cone", coneShape, fC);
1247 coneVolume->SetLineColor(kRed);
1248 support->AddNode(coneVolume, 0, new TGeoTranslation(0, 0, 0));
1249
1250 //__________________________________________________________________
1251 // Tension boxes.
1252 TGeoVolume* tensionBox = TensionBox();
1253 Double_t tensionH = .6;
1254 Double_t tensionL = 4;
1255 Double_t tensionZ = 23.654;
1256 Double_t tensionR = fmd3->ConeR(fmd3->GetInnerZ() + fmd3->GetNoseZ()
1257 - tensionZ);
1258 Double_t tensionAr = fmd3->GetConeOuterAngle();
1259 Double_t tensionA = tensionAr * 180 / TMath::Pi();
1260 TGeoRotation* tensionQ = new TGeoRotation;
1261 tensionQ->RotateY(tensionA);
1262 TGeoCombiTrans* tensionM1 = new TGeoCombiTrans(tensionR,0,tensionZ, tensionQ);
1263 TGeoCombiTrans* tensionM2 = new TGeoCombiTrans(tensionR,0,tensionZ, tensionQ);
1264 tensionM1->RotateZ(45);
1265 tensionM2->RotateZ(135);
1266 support->AddNode(tensionBox, 1, tensionM1);
1267 support->AddNode(tensionBox, 2, tensionM2);
1268
1269 // Double_t tensionHR = 0.15;
1270 Double_t wireT = .1/2;
1271 Double_t wireZ1 = (tensionZ
1272 - tensionL * TMath::Cos(tensionAr)
1273 - tensionH * TMath::Sin(tensionAr));
1274 Double_t wireR1 = (tensionR
1275 - tensionL * TMath::Sin(tensionAr)
1276 + tensionH * TMath::Cos(tensionAr));
1277 AliFMDDebug(10, ("Wire Z1: %f=%f-%f*cos(%f)-%f*sin(%f)",
1278 wireZ1, tensionZ, tensionL, tensionAr, tensionH, tensionAr));
1279 AliFMDDebug(10, ("Wire R1: %f=%f-%f*sin(%f)-%f*cos(%f)",
1280 wireR1, tensionR, tensionL, tensionAr, tensionH, tensionAr));
1281
1282 Double_t wireStartA = 42.3 * TMath::Pi() / 180;
1283 Double_t wireZ2 = (sheeveWheelZ * (1 - TMath::Sin(wireStartA))
1284 // - sheeveL -
1285 - wireT * TMath::Sin(wireStartA));
1286 /* (sheeveWheelZ * (1 - TMath::Sin(wireStartA))
1287 - wireT * TMath::Sin(wireStartA)
1288 - sheeveL); */
1289 AliFMDDebug(10, ("wireZ2=%f=%f*(1-%f)", wireZ2, sheeveWheelZ,
1290 TMath::Sin(wireStartA)));
1291 Double_t wireR2 = (sheeveHoleR +
1292 sheeveWheelZ * TMath::Cos(wireStartA) +
1293 wireT * TMath::Cos(wireStartA));
1294 Double_t wireDR = wireR1-wireR2;
1295 Double_t wireDZ = wireZ1-wireZ2;
1296 Double_t wireL = TMath::Sqrt(wireDR*wireDR+wireDZ*wireDZ)-.01;
1297 Double_t wireAngle = TMath::ATan2(wireDR,wireDZ);
1298 TGeoTube* wireShape = new TGeoTube("FMD3_wire", 0, wireT, wireL/2);
1299 TGeoVolume* wireVolume = new TGeoVolume("FMD3_wire", wireShape,fSteel);
1300 TGeoRotation* wireRot = new TGeoRotation();
1301 wireRot->RotateY(180/TMath::Pi()*wireAngle);
1302 Double_t wireR = wireR2 + wireDR / 2;
1303 Double_t wireZ = wireZ2 + wireDZ / 2;
1304 TGeoCombiTrans* wireM1 = new TGeoCombiTrans(wireR, 0,wireZ, wireRot);
1305 TGeoCombiTrans* wireM2 = new TGeoCombiTrans(wireR, 0,wireZ, wireRot);
1306 wireM1->RotateZ(45);
1307 wireM2->RotateZ(135);
1308 support->AddNode(wireVolume, 1, wireM1);
1309 support->AddNode(wireVolume, 2, wireM2);
1310
1311
1312 TGeoTorus* wireTS = new TGeoTorus(sheeveWheelZ+wireT, 0, wireT, 0,
1313 90-wireStartA*180/TMath::Pi());
1314 TGeoVolume* wireTV = new TGeoVolume("FMD3_bend_wire",wireTS,fSteel);
1315 TGeoRotation* wireTR = new TGeoRotation;
1316 wireTR->RotateY(90);
1317 wireTR->RotateZ(-90);
1318 Double_t wireTZ = sheeveWheelZ;
1319 TGeoCombiTrans* wireTM1 = new TGeoCombiTrans(sheeveHoleR,0,wireTZ,wireTR);
1320 TGeoCombiTrans* wireTM2 = new TGeoCombiTrans(sheeveHoleR,0,wireTZ,wireTR);
1321 wireTM1->RotateZ(45);
1322 wireTM2->RotateZ(135);
1323 support->AddNode(wireTV, 1, wireTM1);
1324 support->AddNode(wireTV, 2, wireTM2);
1325
1326 Double_t colarR = 4.05;
1327 Double_t wireEL = sheeveHoleR - colarR;
1328 TGeoTube* wireES = new TGeoTube("FMD3_end_wire", 0, wireT, wireEL/2);
1329 TGeoVolume* wireEV = new TGeoVolume("FMD3_end_wire", wireES, fSteel);
1330 TGeoRotation* wireER = new TGeoRotation;
1331 wireER->RotateY(90);
1332 TGeoCombiTrans* wireEM1 = new TGeoCombiTrans(colarR+wireEL/2,0,
1333 -wireT,wireER);
1334 TGeoCombiTrans* wireEM2 = new TGeoCombiTrans(colarR+wireEL/2,0,
1335 -wireT,wireER);
1336 wireEM1->RotateZ(45);
1337 wireEM2->RotateZ(135);
1338 support->AddNode(wireEV, 1, wireEM1);
1339 support->AddNode(wireEV, 2, wireEM2);
1340
1341
1342
1343
1344 //__________________________________________________________________
1345 // Place support volumes in half-detector volumes
1346 Double_t z = fmd3->GetInnerZ();
1347 AliFMDDebug(1, ("FMD3 support at z=%f", -fmd3->GetNoseZ()));
1348 TGeoTranslation* t1 = new TGeoTranslation(0, 0, -fmd3->GetNoseZ());
1349 fmd3TopVolume->AddNode(support, 1, t1);
1350 TGeoCombiTrans* t2 = new TGeoCombiTrans(*t1);
1351 t2->RotateZ(180);
1352 fmd3BotVolume->AddNode(support, 2, t2);
1353
1354 TGeoRotation* rot = new TGeoRotation("FMD3 rotatation");
1355 rot->RotateY(180);
1356 TGeoVolume* top = gGeoManager->GetVolume("ALIC");
1357 TGeoMatrix* mmatrix = new TGeoCombiTrans("FMD3 trans", 0, 0, z, rot);
1358 AliFMDDebug(5, ("Placing volumes %s and %s in ALIC at z=%f",
1359 fmd3TopVolume->GetName(), fmd3BotVolume->GetName(), z));
1360 top->AddNode(fmd3TopVolume, fmd3->GetId(), mmatrix);
1361 top->AddNode(fmd3BotVolume, fmd3->GetId(), mmatrix);
1362
1363 return 0;
1364}
1365
1366
1367//____________________________________________________________________
1368void
1369AliFMDGeometryBuilder::Exec(Option_t*)
1370{
1371 // Setup up the FMD geometry.
1372 AliFMDDebug(1, ("\tGeometry options: %s",
1373 (fDetailed ? "divided into strips" : "one volume")));
1374 if (!gGeoManager) {
1375 AliFatal("No TGeoManager defined");
1376 return;
1377 }
1378
1379 fSi = gGeoManager->GetMedium("FMD_Si$");
1380 fC = gGeoManager->GetMedium("FMD_Carbon$");
1381 fAl = gGeoManager->GetMedium("FMD_Aluminum$");
1382 fChip = gGeoManager->GetMedium("FMD_Si Chip$");
1383 fAir = gGeoManager->GetMedium("FMD_Air$");
1384 fPCB = gGeoManager->GetMedium("FMD_PCB$");
1385 fPlastic = gGeoManager->GetMedium("FMD_Plastic$");
1386 fCopper = gGeoManager->GetMedium("FMD_Copper$");
1387 fSteel = gGeoManager->GetMedium("FMD_Steel$");
1388
1389 if (!fSi||!fC||!fAl||!fChip||!fAir||!fPCB||!fPlastic||!fCopper||!fSteel) {
1390 AliError("Failed to get some or all tracking mediums");
1391 return;
1392 }
1393 AliFMDGeometry* fmd = AliFMDGeometry::Instance();
1394 AliFMDRing* inner = fmd->GetInner();
1395 AliFMDRing* outer = fmd->GetOuter();
1396 RingGeometry(inner);
1397 RingGeometry(outer);
1398 TGeoVolume* innerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
1399 inner->GetId()));
1400 TGeoVolume* innerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
1401 inner->GetId()));
1402 TGeoVolume* outerTop = gGeoManager->GetVolume(Form(fgkRingTopName,
1403 outer->GetId()));
1404 TGeoVolume* outerBot = gGeoManager->GetVolume(Form(fgkRingBotName,
1405 outer->GetId()));
1406
1407 FMD1Geometry(fmd->GetFMD1(), innerTop, innerBot);
1408 FMD2Geometry(fmd->GetFMD2(), innerTop, innerBot, outerTop, outerBot);
1409 FMD3Geometry(fmd->GetFMD3(), innerTop, innerBot, outerTop, outerBot);
1410#ifndef USE_PRE_MOVE
1411 fmd->SetSectorOff(fSectorOff);
1412 fmd->SetModuleOff(fModuleOff);
1413 fmd->SetRingOff(fRingOff);
1414 fmd->SetDetectorOff(fDetectorOff);
1415 fmd->SetActive(fActiveId.fArray, fActiveId.fN);
1416#endif
1417 // fmd->ExtractGeomInfo();
1418
1419}
1420
1421
1422//____________________________________________________________________
1423//
1424// EOF
1425//