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