02820fac4b87568a1c20229c1e3aa4765ba42c16
[u/mrichter/AliRoot.git] / FMD / AliFMDGeoOldSimulator.cxx
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
16 /* $Id$ */
17
18 //____________________________________________________________________
19 //                                                                          
20 // Forward Multiplicity Detector based on Silicon wafers. This class
21 // contains the base procedures for the Forward Multiplicity detector
22 // Detector consists of 3 sub-detectors FMD1, FMD2, and FMD3, each of
23 // which has 1 or 2 rings of silicon sensors. 
24 //                                                       
25 // This is the base class for all FMD manager classes. 
26 //                    
27 // The actual code is done by various separate classes.   Below is
28 // diagram showing the relationship between the various FMD classes
29 // that handles the simulation
30 //
31 //      +--------+ 1     +-----------------+ 
32 //      | AliFMD |<>-----| AliFMDSimulator |
33 //      +--------+       +-----------------+
34 //                               ^              
35 //                               |
36 //                 +-------------+-------------+
37 //                 |                           |              
38 //        +--------------------+   +-------------------+
39 //        | AliFMDGeoSimulator |   | AliFMDG3Simulator | 
40 //        +--------------------+   +-------------------+
41 //                                           ^
42 //                                           |
43 //                                 +----------------------+
44 //                                 | AliFMDG3OldSimulator |
45 //                                 +----------------------+
46 //      
47 //
48 // *  AliFMD 
49 //    This defines the interface for the various parts of AliROOT that
50 //    uses the FMD, like AliFMDSimulator, AliFMDDigitizer, 
51 //    AliFMDReconstructor, and so on. 
52 //
53 // *  AliFMDSimulator
54 //    This is the base class for the FMD simulation tasks.   The
55 //    simulator tasks are responsible to implment the geoemtry, and
56 //    process hits. 
57 //                                                                          
58 // *  AliFMDGeoSimulator
59 //    This is a concrete implementation of the AliFMDSimulator that
60 //    uses the TGeo classes directly only.  This defines the active
61 //    volume as an ONLY XTRU shape with a divided MANY TUBS shape
62 //    inside to implement the particular shape of the silicon
63 //    sensors. 
64 //
65 // *  AliFMDG3OldSimulator
66 //    This is a concrete implementation of the AliFMDSimulator that
67 //    uses the TVirtualMC interface with GEANT 3.21-like messages.
68 //    This implements the active volume as a divided TUBS shape.  Hits
69 //    in the corners should be cut away at run time (but currently
70 //    isn't). 
71 //
72 #include <math.h>
73 #include "AliFMDGeoOldSimulator.h" // ALIFMDG3OLDSIMULATOR_H
74 #include "AliFMDGeometry.h"     // ALIFMDGEOMETRY_H
75 #include "AliFMDDetector.h"     // ALIFMDDETECTOR_H
76 #include "AliFMDRing.h"         // ALIFMDRING_H
77 #include "AliFMD1.h"            // ALIFMD1_H
78 #include "AliFMD2.h"            // ALIFMD2_H
79 #include "AliFMD3.h"            // ALIFMD3_H
80 #include "AliFMD.h"             // ALIFMD_H
81 #include <AliLog.h>             // ALILOG_H
82 #include <TVector2.h>           // ROOT_TVector2
83 #include <TVirtualMC.h>         // ROOT_TVirtualMC
84 #include <TArrayI.h>            // ROOT_TArrayI
85 #include <TGeoVolume.h>         // ROOT_TGeoVolume
86 #include <TGeoTube.h>           // ROOT_TGeoTube
87 #include <TGeoMatrix.h>         // ROOT_TGeoMatrix
88  
89 //====================================================================
90 ClassImp(AliFMDGeoOldSimulator)
91 #if 0
92   ; // This is here to keep Emacs for indenting the next line
93 #endif
94
95 //____________________________________________________________________
96 AliFMDGeoOldSimulator::AliFMDGeoOldSimulator() 
97 {
98   // Default constructor
99   fSectorOff   = 1;
100   fModuleOff   = -1;
101   fRingOff     = 3;
102   fDetectorOff = 4;
103   fUseDivided  = kTRUE;
104 }
105
106 //____________________________________________________________________
107 AliFMDGeoOldSimulator::AliFMDGeoOldSimulator(AliFMD* fmd, Bool_t detailed) 
108   : AliFMDGeoSimulator(fmd, detailed)
109 {
110   // Normal constructor
111   // 
112   // Parameters: 
113   // 
114   //      fmd           Pointer to AliFMD object 
115   //      detailed      Whether to make a detailed simulation or not 
116   // 
117   fSectorOff   = 1;
118   fModuleOff   = -1;
119   fRingOff     = 3;
120   fDetectorOff = 4;
121   fUseDivided  = kTRUE;
122 }
123
124 //____________________________________________________________________
125 TGeoVolume*
126 AliFMDGeoOldSimulator::RingGeometry(AliFMDRing* r) 
127 {
128   // Setup the geometry of a ring.    The defined TGeoVolume is
129   // returned, and should be used when setting up the rest of the
130   // volumes. 
131   // 
132   // Parameters:
133   //
134   //     r              Pointer to ring geometry object 
135   // 
136   // Returns:
137   //    true on success 
138   //
139   if (!r) { 
140     AliError("Didn't get a ring object");
141     return 0x0;
142   }
143   Char_t      id          = r->GetId();
144   Double_t    siThick     = r->GetSiThickness();
145   // const Int_t nv       = r->GetNVerticies();
146   TVector2*   a           = r->GetVertex(5);
147   TVector2*   b           = r->GetVertex(3);
148   TVector2*   c           = r->GetVertex(4);
149   Double_t    theta       = r->GetTheta();
150   Double_t    off         = (TMath::Tan(TMath::Pi() * theta / 180) 
151                              * r->GetBondingWidth());
152   Double_t    rmax        = b->Mod();
153   Double_t    rmin        = r->GetLowR();
154   Double_t    pcbThick    = r->GetPrintboardThickness();
155   Double_t    copperThick = r->GetCopperThickness(); // .01;
156   Double_t    chipThick   = r->GetChipThickness(); // .01;
157   Double_t    modSpace    = r->GetModuleSpacing();
158   Double_t    legr        = r->GetLegRadius();
159   Double_t    legl        = r->GetLegLength();
160   Double_t    legoff      = r->GetLegOffset();
161   Int_t       ns          = r->GetNStrips();
162   Int_t       nsec        = Int_t(360 / theta);
163   Double_t    stripoff    = a->Mod();
164   Double_t    dstrip      = (rmax - stripoff) / ns;
165   Double_t    par[10];
166   TString     name;
167   TString     name2;
168   TVirtualMC* mc       = TVirtualMC::GetMC();
169   
170   Int_t siId  = fFMD->GetIdtmed()->At(kSiId);
171   Int_t airId = fFMD->GetIdtmed()->At(kAirId);
172   Int_t pcbId = fFMD->GetIdtmed()->At(kPcbId);
173   Int_t plaId = fFMD->GetIdtmed()->At(kPlasticId);
174   Int_t copId = fFMD->GetIdtmed()->At(kCopperId);
175   Int_t chiId = fFMD->GetIdtmed()->At(kSiChipId);
176
177   Double_t ringWidth = (siThick + 2 * (pcbThick + copperThick + chipThick));
178   // Virtual volume shape to divide - This volume is only defined if
179   // the geometry is set to be detailed. 
180   // Ring mother volume 
181   TGeoShape* ringShape   = new TGeoTube(rmin, rmax, ringWidth / 2);
182   name                   =  Form(fgkRingName, id);
183   TGeoVolume* ringVolume = new TGeoVolume(name.Data(), ringShape, fAir);
184
185   TGeoShape* activeShape   = new TGeoTube(rmin, rmax, siThick / 2);
186   name                     = Form(fgkActiveName, id);
187   Double_t z               = - ringWidth / 2 + siThick / 2;
188   TGeoVolume* activeVolume = new TGeoVolume(name.Data(), activeShape, fSi);
189   ringVolume->AddNode(activeVolume, 1, new TGeoTranslation(0, 0, z));
190   
191   Int_t sid = activeVolume->GetNumber();
192   if (fUseDivided) {
193     name                     = Form(fgkSectorName, id);
194     TGeoVolume* sectorVolume = activeVolume->Divide(name.Data(), 2, nsec,
195                                                     0, 0, 0, "N");
196     
197     name                     = Form(fgkStripName, id);
198     TGeoVolume* stripVolume  = sectorVolume->Divide(name.Data(), 1, ns,
199                                                     0, 0, 0, "N");
200     sid                      = stripVolume->GetNumber();
201     AliDebug(10, Form("Got volume id %d for volume %s", sid, name.Data()));
202   }
203   switch (id) {
204   case 'i':
205   case 'I': fActiveId[0] = sid; break;
206   case 'o':
207   case 'O': fActiveId[2] = sid; break;
208   }
209
210   // Shape of Printed circuit Board 
211   Double_t boardThick = (pcbThick + copperThick + chipThick);
212   TGeoShape*  boardShape  =  new TGeoTube(rmin + .1, rmax - .1, boardThick/ 2);
213   name                    =  Form(fgkPCBName, id, 'B');
214   TGeoVolume* boardVolume =  new TGeoVolume(name.Data(), boardShape, fAir);
215   z                       += siThick / 2 + boardThick / 2;
216   ringVolume->AddNode(boardVolume,  0, new TGeoTranslation(0, 0, z));
217   ringVolume->AddNode(boardVolume,  1, new TGeoTranslation(0,0,z+boardThick));
218
219   // PCB
220   TGeoShape*  pcbShape    = new TGeoTube(rmin+.1, rmax-.1, pcbThick / 2);
221   name                    =  Form("F%cPC", id);
222   z                       =  -boardThick / 2 + pcbThick / 2;
223   TGeoVolume* pcbVolume   = new TGeoVolume(name.Data(), pcbShape, fPCB);
224   boardVolume->AddNode(pcbVolume, 0, new TGeoTranslation(0, 0, z));
225
226   // Copper
227   TGeoShape*  cuShape     =  new TGeoTube(rmin+.1, rmax-.1, copperThick / 2);
228   name                    =  Form("F%cCO", id);
229   z                       += -pcbThick / 2 + copperThick / 2;
230   TGeoVolume* cuVolume    =  new TGeoVolume(name.Data(), cuShape, fCopper);
231   boardVolume->AddNode(cuVolume, 0, new TGeoTranslation(0, 0, z));
232
233   // Chip
234   TGeoShape*  chipShape   = new TGeoTube(rmin+.1, rmax-.1, chipThick / 2);
235   name                    =  Form("F%cCH", id);
236   z                       =  -copperThick / 2 + chipThick / 2;
237   TGeoVolume* chipVolume  = new TGeoVolume(name.Data(), chipShape, fChip);
238   boardVolume->AddNode(chipVolume, 0, new TGeoTranslation(0, 0, z));
239
240   return ringVolume;
241 }
242
243 //____________________________________________________________________
244 //
245 // EOF
246 //