]>
Commit | Line | Data |
---|---|---|
1 | /************************************************************************** | |
2 | * Copyright(c) 2007-2010, 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 | // This class is a helper, producing ITS aligmnent objects. | |
21 | // It provides also some useful functions | |
22 | // See the parameters of the misalignment at the end of this script. | |
23 | // | |
24 | // Main author: L. Gaudichet | |
25 | // Contact: andrea.dainese@lnl.infn.it | |
26 | // | |
27 | //======================================================================== | |
28 | ||
29 | #include <TClonesArray.h> | |
30 | #include <TMath.h> | |
31 | #include <TClass.h> | |
32 | #include <TGeoManager.h> | |
33 | #include "AliLog.h" | |
34 | #include "AliAlignObjParams.h" | |
35 | #include "AliITSMisAligner.h" | |
36 | #include "AliITSSurveyToAlign.h" | |
37 | #include "AliMathBase.h" | |
38 | ||
39 | ClassImp(AliITSMisAligner) | |
40 | ||
41 | const Int_t AliITSMisAligner::fgkNLadders[AliITSMisAligner::kNLayers] = {20,40,14,22,34,38}; | |
42 | const Int_t AliITSMisAligner::fgkNDetectors[AliITSMisAligner::kNLayers] = {4,4,6,8,22,25}; | |
43 | ||
44 | const Double_t kRadToDeg = 180./TMath::Pi(); | |
45 | ||
46 | //________________________________________________________________________ | |
47 | AliITSMisAligner::AliITSMisAligner(): | |
48 | AliMisAligner(), | |
49 | fRnd(), | |
50 | fInd(0), | |
51 | fAlignObjArray(NULL), | |
52 | fStrSPD("ITS/SPD"), | |
53 | fStrSDD("ITS/SDD"), | |
54 | fStrSSD("ITS/SSD"), | |
55 | fStrStave("/Stave"), | |
56 | fStrHalfStave("/HalfStave"), | |
57 | fStrLadder("/Ladder"), | |
58 | fStrSector("/Sector"), | |
59 | fStrSensor("/Sensor"), | |
60 | fUnifSPDSector(kFALSE), | |
61 | fUnifSPDHS(kFALSE), | |
62 | fUnifSDDLadder(kFALSE), | |
63 | fUnifSSDLadder(kFALSE), | |
64 | fUnifSPDLadder(kFALSE), | |
65 | fUnifSDDModule(kFALSE), | |
66 | fUnifSSDModule(kFALSE) | |
67 | { | |
68 | // | |
69 | // defaul constructor | |
70 | // | |
71 | fRnd.SetSeed(38217945); | |
72 | fAlignObjArray = new TClonesArray("AliAlignObjParams",4000); | |
73 | for(Int_t ii=0; ii<6; ii++) | |
74 | { | |
75 | fWholeITS[ii]=0.; | |
76 | fSPDSector[ii]=0.; | |
77 | fSPDHB[ii]=0.; | |
78 | fSPDBarrel[ii]=0.; | |
79 | fSPDHS[ii]=0.; | |
80 | fSPDLadder[ii]=0.; | |
81 | fSDDLayer[ii]=0.; | |
82 | fSDDBarrel[ii]=0.; | |
83 | fSDDLadder[ii]=0.; | |
84 | fSDDModule[ii]=0.; | |
85 | fSSDBarrel[ii]=0.; | |
86 | fSSDLayer[ii]=0.; | |
87 | fSSDLadder[ii]=0.; | |
88 | fSSDModule[ii]=0.; | |
89 | fSPDLadderShiftT[ii]=0.; | |
90 | fSPDLadderShiftB[ii]=0.; | |
91 | fSDDLadderShift1[ii]=0.; | |
92 | fSDDLadderShift2[ii]=0.; | |
93 | } | |
94 | } | |
95 | ||
96 | //________________________________________________________________________ | |
97 | AliITSMisAligner::AliITSMisAligner(const AliITSMisAligner &mAligner): | |
98 | AliMisAligner(), | |
99 | fRnd(mAligner.fRnd), | |
100 | fInd(0), | |
101 | fAlignObjArray(mAligner.fAlignObjArray), | |
102 | fStrSPD("ITS/SPD"), | |
103 | fStrSDD("ITS/SDD"), | |
104 | fStrSSD("ITS/SSD"), | |
105 | fStrStave("/Stave"), | |
106 | fStrHalfStave("/HalfStave"), | |
107 | fStrLadder("/Ladder"), | |
108 | fStrSector("/Sector"), | |
109 | fStrSensor("/Sensor"), | |
110 | fUnifSPDSector(kFALSE), | |
111 | fUnifSPDHS(kFALSE), | |
112 | fUnifSDDLadder(kFALSE), | |
113 | fUnifSSDLadder(kFALSE), | |
114 | fUnifSPDLadder(kFALSE), | |
115 | fUnifSDDModule(kFALSE), | |
116 | fUnifSSDModule(kFALSE) | |
117 | { | |
118 | // | |
119 | // copy constructor | |
120 | // | |
121 | ||
122 | SetMisalType(mAligner.GetMisalType()); | |
123 | } | |
124 | ||
125 | //________________________________________________________________________ | |
126 | AliITSMisAligner &AliITSMisAligner::operator= (const AliITSMisAligner &mAligner) | |
127 | { | |
128 | // | |
129 | // assignment operator | |
130 | // | |
131 | fRnd = mAligner.fRnd; | |
132 | fInd = 0; | |
133 | fAlignObjArray = mAligner.fAlignObjArray; | |
134 | fStrSPD = "ITS/SPD"; | |
135 | fStrSDD = "ITS/SDD"; | |
136 | fStrSSD = "ITS/SSD"; | |
137 | fStrStave = "/Stave"; | |
138 | fStrHalfStave = "/HalfStave"; | |
139 | fStrLadder = "/Ladder"; | |
140 | fStrSector = "/Sector"; | |
141 | fStrSensor = "/Sensor"; | |
142 | fUnifSPDSector = mAligner.fUnifSPDSector; | |
143 | fUnifSPDHS = kFALSE; | |
144 | fUnifSDDLadder = kFALSE; | |
145 | fUnifSSDLadder = kFALSE; | |
146 | fUnifSPDLadder = kFALSE; | |
147 | fUnifSDDModule = kFALSE; | |
148 | fUnifSSDModule = kFALSE; | |
149 | return (*this); | |
150 | } | |
151 | ||
152 | //_______________________________________________________________________________________ | |
153 | TClonesArray* AliITSMisAligner::MakeAlObjsArray() { | |
154 | // Make the array of alignment objects, depending on the misalignment scenario (Zero, Residual, Full) | |
155 | // | |
156 | ||
157 | // Setting default values for ideal, residual or full misalignment | |
158 | SetWholeITSMisAlignment(); | |
159 | SetSPDMisAlignment(); | |
160 | SetSDDMisAlignment(); | |
161 | SetSSDMisAlignment(); | |
162 | ||
163 | // Get array of alignment objects from survey (based on which we build later the SSD objects) | |
164 | AliITSSurveyToAlign* s2a = new AliITSSurveyToAlign(); | |
165 | s2a->Run(); | |
166 | TClonesArray* surveyArray = dynamic_cast<TClonesArray*> (s2a->GetAlignObjsArray()); | |
167 | if(!surveyArray){ | |
168 | Printf("SSD survey array was not build! Probably you missed to connect to alien"); | |
169 | return 0; | |
170 | }else{ | |
171 | Printf("survey array contains %d entries", surveyArray->GetEntriesFast()); | |
172 | } | |
173 | char strtemp[5]="ITS"; | |
174 | AddAlignObj(strtemp,fWholeITS[0],fWholeITS[1],fWholeITS[2],fWholeITS[3],fWholeITS[4],fWholeITS[5],"fixed"); | |
175 | ||
176 | AddSectorAlignObj(1,5,fSPDSector[0],fSPDSector[1],fSPDSector[2],fSPDSector[3],fSPDSector[4],fSPDSector[5], | |
177 | fSPDLadderShiftT[0],fSPDLadderShiftT[1],fSPDLadderShiftT[2],fSPDLadderShiftT[3],fSPDLadderShiftT[4],fSPDLadderShiftT[5],fUnifSPDSector); | |
178 | AddSectorAlignObj(6,10,fSPDSector[0],fSPDSector[1],fSPDSector[2],fSPDSector[3],fSPDSector[4],fSPDSector[5], | |
179 | fSPDLadderShiftB[0],fSPDLadderShiftB[1],fSPDLadderShiftB[2],fSPDLadderShiftB[3],fSPDLadderShiftB[4],fSPDLadderShiftB[5],fUnifSPDSector); | |
180 | ||
181 | //=**************************************** | |
182 | // misalignment at the level of half-staves (SPD)/ladders (SDD,SSD) : | |
183 | //=**************************************** | |
184 | AddAlignObj(0,-1,fSPDHS[0],fSPDHS[1],fSPDHS[2],fSPDHS[3],fSPDHS[4],fSPDHS[5], | |
185 | 0,0,0,0,0,0,fUnifSPDHS); // all SPD1 half-staves | |
186 | AddAlignObj(1,-1,fSPDHS[0],fSPDHS[1],fSPDHS[2],fSPDHS[3],fSPDHS[4],fSPDHS[5], | |
187 | 0,0,0,0,0,0,fUnifSPDHS); // all SPD2 half-staves | |
188 | ||
189 | AddAlignObj(2,-1,fSDDLadder[0],fSDDLadder[1],fSDDLadder[2],fSDDLadder[3], | |
190 | fSDDLadder[4],fSDDLadder[5],fSDDLadderShift1[0],fSDDLadderShift1[1],fSDDLadderShift1[2],fSDDLadderShift1[3],fSDDLadderShift1[4],fSDDLadderShift1[5],fUnifSDDLadder); // all SDD1 ladders | |
191 | AddAlignObj(3,-1,fSDDLadder[0],fSDDLadder[1],fSDDLadder[2],fSDDLadder[3], | |
192 | fSDDLadder[4],fSDDLadder[5],fSDDLadderShift2[0],fSDDLadderShift2[1],fSDDLadderShift2[2],fSDDLadderShift2[3],fSDDLadderShift2[4],fSDDLadderShift2[5],fUnifSDDLadder); // all SDD2 ladders | |
193 | ||
194 | // all SSD ladders as from survey, + shift and smearing in the "residual" and "full" case | |
195 | for(Int_t ii=0; ii<surveyArray->GetEntriesFast(); ii++) | |
196 | { | |
197 | AliAlignObjParams* aop = dynamic_cast<AliAlignObjParams*> (surveyArray->UncheckedAt(ii)); | |
198 | TString sName(aop->GetSymName()); | |
199 | ||
200 | if(sName.Contains("SSD") && !sName.Contains("Sensor")) | |
201 | { | |
202 | ||
203 | if(!(TString(GetMisalType())=="ideal")) | |
204 | { | |
205 | // First we shift all SSD ladders by the same quantity to reproduce a barrel shift | |
206 | ShiftAlignObj(*aop,fSSDBarrel[0],fSSDBarrel[1],fSSDBarrel[2],fSSDBarrel[3],fSSDBarrel[4],fSSDBarrel[5]); | |
207 | ||
208 | // Then we smear according to the sigmas given by the misalignment scenario | |
209 | if(sName.Contains("SSD4")){ | |
210 | // we correct with the factor 1.13 for the fact that, in the inner SSD layer, z lever arm is 45.135cm instead of 51cm | |
211 | SmearAlignObj(*aop,fSSDLadder[0],fSSDLadder[1],fSSDLadder[2],fSSDLadder[3]*1.13,fSSDLadder[4]*1.13,fSSDLadder[5]); | |
212 | }else if(sName.Contains("SSD5")){ | |
213 | SmearAlignObj(*aop,fSSDLadder[0],fSSDLadder[1],fSSDLadder[2],fSSDLadder[3],fSSDLadder[4],fSSDLadder[5]); | |
214 | } | |
215 | } | |
216 | ||
217 | new((*fAlignObjArray)[fInd++]) AliAlignObjParams(*aop); | |
218 | aop->ApplyToGeometry(); // this we need to correctly build objects for SSD ladders below | |
219 | } | |
220 | } | |
221 | ||
222 | //=**************************************** | |
223 | // misalignment at the level of ladders (SPD)/modules (SDD,SSD) : | |
224 | //=**************************************** | |
225 | AddAlignObj(0,fSPDLadder[0],fSPDLadder[1],fSPDLadder[2],fSPDLadder[3],fSPDLadder[4],fSPDLadder[5],fUnifSPDLadder);// all SPD1 ladders | |
226 | AddAlignObj(1,fSPDLadder[0],fSPDLadder[1],fSPDLadder[2],fSPDLadder[3],fSPDLadder[4],fSPDLadder[5],fUnifSPDLadder);// all SPD2 ladders | |
227 | ||
228 | AddAlignObj(2,fSDDModule[0],fSDDModule[1],fSDDModule[2],fSDDModule[3],fSDDModule[4],fSDDModule[5],fUnifSDDModule);// all SDD1 modules | |
229 | AddAlignObj(3,fSDDModule[0],fSDDModule[1],fSDDModule[2],fSDDModule[3],fSDDModule[4],fSDDModule[5],fUnifSDDModule);// all SDD2 modules | |
230 | ||
231 | // all SSD modules | |
232 | for(Int_t ii=0; ii<surveyArray->GetEntriesFast(); ii++) | |
233 | { | |
234 | AliAlignObjParams* aop = dynamic_cast<AliAlignObjParams*> (surveyArray->UncheckedAt(ii)); | |
235 | TString sName(aop->GetSymName()); | |
236 | if(sName.Contains("SSD") && sName.Contains("Sensor")) | |
237 | { | |
238 | if(!(TString(GetMisalType())=="ideal")) | |
239 | SmearAlignObj(*aop,fSSDModule[0],fSSDModule[1],fSSDModule[2],fSSDModule[3],fSSDModule[4],fSSDModule[5]); | |
240 | new((*fAlignObjArray)[fInd++]) AliAlignObjParams(*aop); | |
241 | } | |
242 | } | |
243 | ||
244 | return fAlignObjArray; | |
245 | } | |
246 | ||
247 | //_______________________________________________________________________________________ | |
248 | void AliITSMisAligner::ShiftAlignObj(AliAlignObjParams &alObj, Double_t dx, Double_t dy, Double_t dz, Double_t dpsi, Double_t dtheta, Double_t dphi) | |
249 | { | |
250 | // | |
251 | // Shift the parameters of the alignment object passed as first argument by the quantities defined by the arguments | |
252 | // | |
253 | Double_t shifts[3]; Double_t angles[3]; | |
254 | alObj.GetPars(shifts, angles); | |
255 | alObj.SetPars(shifts[0]+dx, shifts[1]+dy, shifts[2]+dz, angles[0]+dpsi, angles[1]+dtheta, angles[2]+dphi); | |
256 | } | |
257 | ||
258 | //_______________________________________________________________________________________ | |
259 | void AliITSMisAligner::SmearAlignObj(AliAlignObjParams &alObj, Double_t sx, Double_t sy, Double_t sz, Double_t spsi, Double_t stheta, Double_t sphi) | |
260 | { | |
261 | // | |
262 | // Smear the parameters of the alignment object passed as first argument in the range defined by the subsequent arguments | |
263 | // | |
264 | Double_t shifts[3]; Double_t angles[3]; | |
265 | alObj.GetLocalPars(shifts, angles); | |
266 | Double_t x = AliMathBase::TruncatedGaus(shifts[0], sx, 3.*sx); | |
267 | Double_t y = AliMathBase::TruncatedGaus(shifts[1], sy, 3.*sy); | |
268 | Double_t z = AliMathBase::TruncatedGaus(shifts[2], sz, 3.*sz); | |
269 | Double_t psi = AliMathBase::TruncatedGaus(angles[0], spsi, 3.*spsi); | |
270 | Double_t theta = AliMathBase::TruncatedGaus(angles[1], stheta, 3.*stheta); | |
271 | Double_t phi = AliMathBase::TruncatedGaus(angles[2], sphi, 3.*sphi); | |
272 | alObj.SetLocalPars(x, y, z, psi, theta, phi); | |
273 | } | |
274 | ||
275 | //_______________________________________________________________________________________ | |
276 | void AliITSMisAligner::SetWholeITSMisAlignment() | |
277 | { | |
278 | // Set misalignment for the whole ITS for the standar scenarios (zero, residual, full) | |
279 | // To make custom misalignments set directly the misalignments at each level (methods "SetS?D*Pars") | |
280 | // | |
281 | if(TString(GetMisalType())=="ideal") | |
282 | { | |
283 | // overall ITS misalignment according to survey as reported by Werner Riegler (18/07/2008) | |
284 | SetWholeITSPars(-0.12, -0.07, 0.29, 0., 0.03, 0.04); | |
285 | }else if(TString(GetMisalType())=="residual"){ | |
286 | // overall ITS misalignment according to survey as reported by Werner Riegler (18/07/2008) | |
287 | // no smearing added (would clash with vertex constraint) | |
288 | SetWholeITSPars(-0.12, -0.07, 0.29, 0., 0.03, 0.04); | |
289 | }else if(TString(GetMisalType())=="full"){ | |
290 | // overall ITS misalignment according to survey as reported by Werner Riegler (18/07/2008) plus smearing | |
291 | Double_t sigmatrW = 0.01; | |
292 | Double_t sigmarotW = 0.006; | |
293 | SetWholeITSPars(AliMathBase::TruncatedGaus(-0.12,sigmatrW,3.*sigmatrW), | |
294 | AliMathBase::TruncatedGaus(-0.07,sigmatrW,3.*sigmatrW), | |
295 | AliMathBase::TruncatedGaus(0.29,sigmatrW,3.*sigmatrW), | |
296 | AliMathBase::TruncatedGaus(0.,sigmarotW,3.*sigmarotW), | |
297 | AliMathBase::TruncatedGaus(0.03,sigmarotW,3.*sigmarotW), | |
298 | AliMathBase::TruncatedGaus(0.04,sigmarotW,3.*sigmarotW)); | |
299 | } | |
300 | } | |
301 | ||
302 | //_______________________________________________________________________________________ | |
303 | void AliITSMisAligner::SetSPDMisAlignment() | |
304 | { | |
305 | // Set misalignment for SPD alignable volumes for the standar scenarios (zero, residual, full) | |
306 | // To make custom misalignments set directly the misalignments at each level (methods "SetSPD*Pars") | |
307 | // | |
308 | if(TString(GetMisalType())=="ideal") | |
309 | { | |
310 | // misalignment for SPD at all levels equal to zero (identical transformations) | |
311 | SetSPDBarrelSigmas(0., 0., 0., 0., 0., 0.); | |
312 | SetSPDHBSigmas(0., 0., 0., 0., 0., 0.); | |
313 | SetSPDSectorSigmas(0., 0., 0., 0., 0., 0.); | |
314 | SetSPDHSSigmas(0., 0., 0., 0., 0., 0.); | |
315 | SetSPDLadderSigmas(0., 0., 0., 0., 0., 0.); | |
316 | }else if(TString(GetMisalType())=="residual"){ | |
317 | // misalignment at the level of SPD barrel and half-barrels left to zero | |
318 | SetSPDBarrelSigmas(0., 0., 0., 0., 0., 0.); | |
319 | SetSPDHBSigmas(0., 0., 0., 0., 0., 0.); | |
320 | ||
321 | // misalignment at the level of SPD sectors (source: A.Pepato) | |
322 | SetSPDSectorSigmas( 0.0050/5., // 50 micron (~tangetial, i.e. rphi) | |
323 | 0.0100/5., // 100 micron (~radial) | |
324 | 0.0100/5., // 100 micron | |
325 | 0.0100/30.*kRadToDeg/5., // so as to have 100 micron difference at the two extremes | |
326 | 0.0100/30.*kRadToDeg/5., // so as to have 100 micron difference at the two extremes | |
327 | 0.0050/1.5*kRadToDeg/5.); // so as to have 50 micron difference at the two extremes | |
328 | fUnifSPDSector=kFALSE; | |
329 | ||
330 | // misalignment at the level of half-staves (SPD) (source: S.Moretto) | |
331 | SetSPDHSSigmas( 0.0100/4., // 100 micron | |
332 | 0.0020/4., // 20 micron | |
333 | 0.0020/4., // 20 micron | |
334 | 0.0020/7.*kRadToDeg/4., // so as to have 20 micron difference at the two extremes | |
335 | 0.0050/7.*kRadToDeg/4., // so as to have 50 micron difference at the two extremes | |
336 | 0.0050/0.7*kRadToDeg/4.);// so as to have 50 micron difference at the two extremes | |
337 | fUnifSPDHS=kFALSE; | |
338 | ||
339 | // misalignment at the level of ladders (SPD) (source: R.Santoro) | |
340 | SetSPDLadderSigmas( 0.0010/5., // 10 micron | |
341 | 0.0050/5., // 50 micron | |
342 | 0.0010/5., // 10 micron | |
343 | 0.0001*kRadToDeg/5., // 0.1 mrad | |
344 | 0.0001*kRadToDeg/5., // 0.1 mrad | |
345 | 0.0001*kRadToDeg/5.);// 0.1 mrad | |
346 | fUnifSPDLadder=kFALSE; | |
347 | ||
348 | }else if(TString(GetMisalType())=="full"){ | |
349 | // misalignment at the level of SPD barrel (source: A.Pepato) | |
350 | SetSPDBarrelSigmas( 0.1000, // 1 mm (very pessimistic) | |
351 | 0.1000, // 1 mm (very pessimistic) | |
352 | 0.1000, // 1 mm (very pessimistic) | |
353 | 0.0500/30.*kRadToDeg, // so as to have 500 micron difference at the two extremes | |
354 | 0.0500/30.*kRadToDeg, // so as to have 500 micron difference at the two extremes | |
355 | 0.0500/7.*kRadToDeg); // so as to have 500 micron difference at the two extremes | |
356 | ||
357 | // misalignment at the level of SPD half-barrels (source: A.Pepato) | |
358 | SetSPDHBSigmas( 0.0200, // 200 micron | |
359 | 0.0200, // 200 micron | |
360 | 0.0200, // 200 micron | |
361 | 0.0100/30.*kRadToDeg, // so as to have 100 micron difference at the two extremes | |
362 | 0.0100/30.*kRadToDeg, // so as to have 100 micron difference at the two extremes | |
363 | 0.0100/7.*kRadToDeg); // so as to have 100 micron difference at the two extremes | |
364 | ||
365 | // misalignment at the level of SPD sectors (source: A.Pepato) | |
366 | SetSPDSectorSigmas( 0.0050, // 50 micron (~tangetial, i.e. rphi) | |
367 | 0.0100, // 100 micron (~radial) | |
368 | 0.0100, // 100 micron | |
369 | 0.0100/30.*kRadToDeg, // so as to have 100 micron difference at the two extremes | |
370 | 0.0100/30.*kRadToDeg, // so as to have 100 micron difference at the two extremes | |
371 | 0.0050/1.5*kRadToDeg); // so as to have 50 micron difference at the two extremes | |
372 | fUnifSPDSector=kTRUE; | |
373 | ||
374 | // misalignment at the level of half-staves (SPD) (source: S.Moretto) | |
375 | SetSPDHSSigmas( 0.0100, // 100 micron // normal to plane | |
376 | 0.0020, // 20 micron | |
377 | 0.0020, // 20 micron | |
378 | 0.0020/7.*kRadToDeg, // so as to have 20 micron difference at the two extremes | |
379 | 0.0050/7.*kRadToDeg, // so as to have 50 micron difference at the two extremes | |
380 | 0.0050/0.7*kRadToDeg); // so as to have 50 micron difference at the two extremes | |
381 | fUnifSPDHS=kTRUE; | |
382 | ||
383 | // misalignment at the level of ladders (SPD) (source: R.Santoro) | |
384 | SetSPDLadderSigmas( 0.0010, // 10 micron | |
385 | 0.0030, // 50 micron | |
386 | 0.0010, // 10 micron | |
387 | 0.0001*kRadToDeg, // 0.1 mrad | |
388 | 0.0001*kRadToDeg, // 0.1 mrad | |
389 | 0.0001*kRadToDeg); // 0.1 mrad | |
390 | fUnifSPDLadder=kTRUE; | |
391 | ||
392 | ||
393 | // misalignment at the level of SPD barrel, half-barrels, and at the level | |
394 | // of SPD sectors | |
395 | Double_t shBtop[6], shBbot[6]; //top and bottom barrel shifts | |
396 | for(Int_t ii=0; ii<6; ii++){ | |
397 | shBtop[ii] = AliMathBase::TruncatedGaus(0.,fSPDBarrel[ii]/3,fSPDBarrel[ii]); | |
398 | shBbot[ii] = shBtop[ii]; | |
399 | } | |
400 | ||
401 | for(Int_t ii=0; ii<6; ii++){ | |
402 | shBtop[ii] += AliMathBase::TruncatedGaus(0.,fSPDHB[ii]/3,fSPDHB[ii]); | |
403 | shBbot[ii] += AliMathBase::TruncatedGaus(0.,fSPDHB[ii]/3,fSPDHB[ii]); | |
404 | } | |
405 | SetSPDLadderShiftT(shBtop); | |
406 | SetSPDLadderShiftB(shBbot); | |
407 | } | |
408 | } | |
409 | ||
410 | //_______________________________________________________________________________________ | |
411 | void AliITSMisAligner::SetSDDMisAlignment() | |
412 | { | |
413 | // Set misalignment for SDD alignable volumes for the standar scenarios (zero, residual, full) | |
414 | // To make custom misalignments set directly the misalignments at each level (methods "SetSDD*Pars") | |
415 | // | |
416 | if(TString(GetMisalType())=="ideal") | |
417 | { | |
418 | // misalignment for SDD at all levels equal to zero | |
419 | SetSDDLayerSigmas(0., 0., 0., 0., 0., 0.); | |
420 | SetSDDBarrelSigmas(0., 0., 0., 0., 0., 0.); | |
421 | SetSDDLadderSigmas(0., 0., 0., 0., 0., 0.); | |
422 | SetSDDModuleSigmas(0., 0., 0., 0., 0., 0.); | |
423 | }else if(TString(GetMisalType())=="residual"){ | |
424 | // misalignment at the level of SDD and SSD layers(source: B.Giraudo) | |
425 | SetSDDLayerSigmas(0., 0., 0., 0., 0., 0.); | |
426 | SetSDDBarrelSigmas(0., 0., 0., 0., 0., 0.); | |
427 | ||
428 | // misalignment at the level of half-staves (SPD) (source: S.Moretto) | |
429 | SetSDDLadderSigmas( 0.0005, // 5 micron | |
430 | 0.0005, // 5 micron | |
431 | 0.0005, // 5 micron | |
432 | 0.00, // ? | |
433 | 0.00, // ? | |
434 | 0.00); // ? | |
435 | fUnifSDDLadder=kFALSE; | |
436 | ||
437 | // misalignment at the level of SDD modules(source: L.Gaudichet) | |
438 | SetSDDModuleSigmas( 0.0045/5., // 45 micron | |
439 | 0.0045/5., // 45 micron | |
440 | 0.0105/5., // 105 micron | |
441 | 0.00, // ? | |
442 | 0.00, // ? | |
443 | 0.00);// ? | |
444 | fUnifSDDModule=kFALSE; | |
445 | ||
446 | }else if(TString(GetMisalType())=="full"){ | |
447 | // misalignment at the level of SDD layers(source: B.Giraudo) | |
448 | SetSDDBarrelSigmas( 0.0020, // 20 micron | |
449 | 0.0020, // 20 micron | |
450 | 0.0020, // 20 micron | |
451 | 0.0020/52.*kRadToDeg, // so as to have 20 micron difference at the two extremes | |
452 | 0.0020/52.*kRadToDeg, // so as to have 20 micron difference at the two extremes | |
453 | 0.0020/20.*kRadToDeg); // so as to have 20 micron difference at the two extremes | |
454 | ||
455 | SetSDDLayerSigmas( 0.0010, // 10 micron | |
456 | 0.0010, // 10 micron | |
457 | 0.0010, // 10 micron | |
458 | 0.0010/52.*kRadToDeg, // so as to have 10 micron difference at the two extremes | |
459 | 0.0010/52.*kRadToDeg, // so as to have 10 micron difference at the two extremes | |
460 | 0.0010/20.*kRadToDeg); // so as to have 10 micron difference at the two extremes | |
461 | ||
462 | // misalignment at the level of SDD ladders | |
463 | SetSDDLadderSigmas( 0.0005, // 5 micron | |
464 | 0.0005, // 5 micron | |
465 | 0.0005, // 5 micron | |
466 | 0.00, // ? | |
467 | 0.00, // ? | |
468 | 0.00);// ? | |
469 | fUnifSDDLadder=kTRUE; | |
470 | ||
471 | // misalignment at the level of SDD modules (source: L.Gaudichet) | |
472 | SetSDDModuleSigmas( 0.0045, // 45 micron | |
473 | 0.0045, // 45 micron | |
474 | 0.0105, // 105 micron | |
475 | 0.00, // ? | |
476 | 0.00, // ? | |
477 | 0.00);// ? | |
478 | fUnifSDDModule=kTRUE; | |
479 | } | |
480 | ||
481 | fSDDLadderShift1[0] = GetUnif(-fSDDBarrel[0],fSDDBarrel[0]); | |
482 | fSDDLadderShift1[1] = GetUnif(-fSDDBarrel[1],fSDDBarrel[1]); | |
483 | fSDDLadderShift1[2] = GetUnif(-fSDDBarrel[2],fSDDBarrel[2]); | |
484 | fSDDLadderShift1[3] = GetUnif(-fSDDBarrel[3],fSDDBarrel[3]); | |
485 | fSDDLadderShift1[4] = GetUnif(-fSDDBarrel[4],fSDDBarrel[4]); | |
486 | fSDDLadderShift1[5] = GetUnif(-fSDDBarrel[5],fSDDBarrel[5]); | |
487 | ||
488 | for(Int_t ii=0; ii<6; ii++) | |
489 | fSDDLadderShift2[ii] = fSDDLadderShift1[ii]; | |
490 | ||
491 | // layer SDD1 | |
492 | fSDDLadderShift1[0] += GetUnif(-fSDDLayer[0],fSDDLayer[0]); | |
493 | fSDDLadderShift1[1] += GetUnif(-fSDDLayer[1],fSDDLayer[1]); | |
494 | fSDDLadderShift1[2] += GetUnif(-fSDDLayer[2],fSDDLayer[2]); | |
495 | fSDDLadderShift1[3] += GetUnif(-fSDDLayer[3],fSDDLayer[3]); | |
496 | fSDDLadderShift1[4] += GetUnif(-fSDDLayer[4],fSDDLayer[4]); | |
497 | fSDDLadderShift1[5] += GetUnif(-fSDDLayer[5],fSDDLayer[5]); | |
498 | ||
499 | // layer SDD2 | |
500 | fSDDLadderShift2[0] += GetUnif(-fSDDLayer[0],fSDDLayer[0]); | |
501 | fSDDLadderShift2[1] += GetUnif(-fSDDLayer[1],fSDDLayer[1]); | |
502 | fSDDLadderShift2[2] += GetUnif(-fSDDLayer[2],fSDDLayer[2]); | |
503 | fSDDLadderShift2[3] += GetUnif(-fSDDLayer[3],fSDDLayer[3]); | |
504 | fSDDLadderShift2[4] += GetUnif(-fSDDLayer[4],fSDDLayer[4]); | |
505 | fSDDLadderShift2[5] += GetUnif(-fSDDLayer[5],fSDDLayer[5]); | |
506 | ||
507 | } | |
508 | ||
509 | //_______________________________________________________________________________________ | |
510 | void AliITSMisAligner::SetSSDMisAlignment() | |
511 | { | |
512 | // Set misalignment for SSD alignable volumes for the standar scenarios (zero, residual, full) | |
513 | // To make custom misalignments set directly the misalignments at each level (methods "SetSSD*Pars") | |
514 | // | |
515 | if(TString(GetMisalType())=="ideal"){ | |
516 | ||
517 | // zero misalignment at the level of SSD barrel | |
518 | SetSSDBarrelPars(0.,0.,0.,0.,0.,0.); | |
519 | // zero misalignment at the level of SSD ladders | |
520 | SetSSDLadderSigmas(0.,0.,0.,0.,0.,0.); | |
521 | // zero misalignment at the level of SSD modules | |
522 | SetSSDModuleSigmas(0.,0.,0.,0.,0.,0.); | |
523 | ||
524 | }else if(TString(GetMisalType())=="residual"){ | |
525 | ||
526 | // zero misalignment at the level of SSD barrel | |
527 | SetSSDBarrelPars(0.,0.,0.,0.,0.,0.); | |
528 | // misalignment at the level of SSD ladders (source: M. Van Leeuwen) | |
529 | // values set so that overall maximum displacement (combined effect of shift and rotation | |
530 | // of the ladder) for any point of the ladder cannot exceed 10um in x, 100 um in y, 50um in z | |
531 | SetSSDLadderSigmas( 0.0005, // 5 microns | |
532 | 0.0033, // 33 microns | |
533 | 0.0050, // 50 microns | |
534 | 0.000067*kRadToDeg, // 0.067 mrads | |
535 | 0.00001*kRadToDeg, // 0.01 mrads | |
536 | 0.001*kRadToDeg); // 1 mrad | |
537 | fUnifSSDLadder=kTRUE; | |
538 | ||
539 | // misalignment at the level of SSD modules (source: M. Van Leeuwen) | |
540 | // values set so that overall maximum displacement (combined effect of shift and rotation | |
541 | // of the ladder) for any point of the module cannot exceed 5um in x, 10 um in y, 5um in z | |
542 | SetSSDModuleSigmas( 0.00025, // 2.5 microns | |
543 | 0.00034, // 3.4 microns | |
544 | 0.0005, // 5 microns | |
545 | 0.00017*kRadToDeg, // 0.17 mrads | |
546 | 0.000125*kRadToDeg, // 0.125 mrads | |
547 | 0.0001*kRadToDeg); // 0.1 mrads | |
548 | fUnifSSDModule=kTRUE; | |
549 | ||
550 | }else if(TString(GetMisalType())=="full"){ | |
551 | // misalignment at the level of SSD layers (source: B. Giraudo) | |
552 | SetSSDBarrelPars( GetUnif(-0.0020,0.0020), // 20 micron | |
553 | GetUnif(-0.0020,0.0020), // 20 micron | |
554 | GetUnif(-0.0020,0.0020), // 20 micron | |
555 | GetUnif(-0.0020/90.*kRadToDeg,0.0020), // so as to have 20 micron difference at the two extremes | |
556 | GetUnif(-0.0020/90.*kRadToDeg,0.0020), // so as to have 20 micron difference at the two extremes | |
557 | GetUnif(-0.0020/40.*kRadToDeg,0.0020)); // so as to have 20 micron difference at the two extremes | |
558 | ||
559 | // misalignment at the level of SSD ladders (source: M. Van Leeuwen) | |
560 | // values set so that overall maximum displacement (combined effect of shift and rotation | |
561 | // of the ladder) for any point of the ladder cannot exceed 20um in x, 100 um in y, 50um in z | |
562 | SetSSDLadderSigmas( 0.0010, // 10 microns | |
563 | 0.0033, // 33 microns | |
564 | 0.0050, // 50 microns | |
565 | 0.000067*kRadToDeg, // 0.067 mrads | |
566 | 0.00002*kRadToDeg, // 0.02 mrads | |
567 | 0.001*kRadToDeg); // 1 mrad | |
568 | fUnifSSDLadder=kTRUE; | |
569 | ||
570 | // misalignment at the level of SSD modules (source: M. Van Leeuwen) | |
571 | // values set so that overall maximum displacement (combined effect of shift and rotation | |
572 | // of the ladder) for any point of the module cannot exceed 5um in x, 10 um in y, 5um in z | |
573 | SetSSDModuleSigmas( 0.00025, // 2.5 microns | |
574 | 0.00034, // 3.4 microns | |
575 | 0.0005, // 5 microns | |
576 | 0.00017*kRadToDeg, // 0.17 mrads | |
577 | 0.000125*kRadToDeg, // 0.125 mrads | |
578 | 0.0001*kRadToDeg); // 0.1 mrads | |
579 | fUnifSSDModule=kTRUE; | |
580 | } | |
581 | ||
582 | } | |
583 | ||
584 | //_______________________________________________________________________________________ | |
585 | AliCDBMetaData* AliITSMisAligner::GetCDBMetaData() const { | |
586 | // Returns the AliCDBMetaData to be associated with AliCDBEntry which will contain | |
587 | // the array of alignment objects for ITS misalignment | |
588 | // Presently "responsible" and "comment" are filled. | |
589 | // | |
590 | AliCDBMetaData* md = new AliCDBMetaData(); | |
591 | md->SetResponsible("A. Dainese, M. Van Leeuwen, R. Grosso"); | |
592 | ||
593 | if(TString(GetMisalType())=="ideal") | |
594 | md->SetComment( | |
595 | Form("Alignment objects for ITS ideal misalignment. It includes:" | |
596 | "\n survey of whole ITS;" | |
597 | "\n survey of SSD ladders and modules")); | |
598 | if(TString(GetMisalType())=="residual") | |
599 | md->SetComment( | |
600 | Form("Alignment objects for ITS residual misalignment. It includes:" | |
601 | "\n survey of whole ITS;" | |
602 | "\n survey of SSD ladders and modules")); | |
603 | if(TString(GetMisalType())=="full") | |
604 | md->SetComment( | |
605 | Form("Alignment objects for ITS full misalignment. It includes:" | |
606 | "\n survey of whole ITS;" | |
607 | "\n survey of SSD ladders and modules")); | |
608 | return md; | |
609 | } | |
610 | ||
611 | //________________________________________________________________________ | |
612 | Bool_t AliITSMisAligner::AddAlignObj(char* name,Double_t dx,Double_t dy,Double_t dz, | |
613 | Double_t dpsi,Double_t dtheta,Double_t dphi,const char* distrib) { | |
614 | // | |
615 | // misalignment by symname | |
616 | // | |
617 | Double_t vx=0.,vy=0.,vz=0.,vpsi=0.,vtheta=0.,vphi=0.; | |
618 | ||
619 | TString sdistrib(distrib); | |
620 | ||
621 | if(sdistrib==TString("gaussian")) { | |
622 | vx = AliMathBase::TruncatedGaus(0.,dx/3.,dx); // mean, sigma, max absolute value | |
623 | vy = AliMathBase::TruncatedGaus(0.,dy/3.,dy); | |
624 | vz = AliMathBase::TruncatedGaus(0.,dz/3.,dz); | |
625 | vpsi = AliMathBase::TruncatedGaus(0.,dpsi/3., dpsi ); | |
626 | vtheta = AliMathBase::TruncatedGaus(0.,dtheta/3.,dtheta); | |
627 | vphi = AliMathBase::TruncatedGaus(0.,dphi/3., dphi); | |
628 | }else if(sdistrib==TString("uniform")){ | |
629 | vx = fRnd.Uniform(-dx,dx); | |
630 | vy = fRnd.Uniform(-dy,dy); | |
631 | vz = fRnd.Uniform(-dz,dz); | |
632 | vpsi = fRnd.Uniform(-dpsi,dpsi); | |
633 | vtheta = fRnd.Uniform(-dtheta,dtheta); | |
634 | vphi = fRnd.Uniform(-dphi,dphi); | |
635 | }else if(sdistrib==TString("fixed")){ | |
636 | vx=dx; | |
637 | vy=dy; | |
638 | vz=dz; | |
639 | vpsi=dpsi; | |
640 | vtheta=dtheta; | |
641 | vphi=dphi; | |
642 | }else{ | |
643 | AliFatal(Form("Invalid string \"%s\" specifying the misalignment type for the volume \"%s\"")); | |
644 | } | |
645 | ||
646 | new((*fAlignObjArray)[fInd]) AliAlignObjParams(name,0,vx,vy,vz,vpsi,vtheta,vphi,kFALSE); | |
647 | ||
648 | AliAlignObjParams* itsalobj = (AliAlignObjParams*) fAlignObjArray->UncheckedAt(fInd); | |
649 | itsalobj->ApplyToGeometry(); | |
650 | ||
651 | fInd++; | |
652 | ||
653 | return kTRUE; | |
654 | } | |
655 | ||
656 | ||
657 | //________________________________________________________________________ | |
658 | Bool_t AliITSMisAligner::AddAlignObj(Int_t lay,Double_t dx,Double_t dy,Double_t dz, | |
659 | Double_t dpsi,Double_t dtheta,Double_t dphi,Bool_t unif) { | |
660 | // | |
661 | // misalignment at the level of sensitive alignable volumes (SPD ladders/ SDD,SSD modules) | |
662 | // done for all ladders/modules of the given layer | |
663 | // | |
664 | lay+=1; // layers are numbered from 1 to 6 in AliGeomManager | |
665 | ||
666 | printf("LAYER %d MODULES %d\n",lay,AliGeomManager::LayerSize(lay)); | |
667 | ||
668 | for (Int_t iModule = 0; iModule < AliGeomManager::LayerSize(lay); iModule++) { | |
669 | ||
670 | Double_t vx,vy,vz,vpsi,vtheta,vphi; | |
671 | ||
672 | if(!unif) { | |
673 | vx = AliMathBase::TruncatedGaus(0.,dx/3.,dx); // mean, sigma, max absolute value | |
674 | vy = AliMathBase::TruncatedGaus(0.,dy/3.,dy); | |
675 | vz = AliMathBase::TruncatedGaus(0.,dz/3.,dz); | |
676 | vpsi = AliMathBase::TruncatedGaus(0.,dpsi/3.,dpsi); | |
677 | vtheta = AliMathBase::TruncatedGaus(0.,dtheta/3.,dtheta); | |
678 | vphi = AliMathBase::TruncatedGaus(0.,dphi/3.,dphi); | |
679 | } else { | |
680 | vx = fRnd.Uniform(-dx,dx); | |
681 | vy = fRnd.Uniform(-dy,dy); | |
682 | vz = fRnd.Uniform(-dz,dz); | |
683 | vpsi = fRnd.Uniform(-dpsi,dpsi); | |
684 | vtheta = fRnd.Uniform(-dtheta,dtheta); | |
685 | vphi = fRnd.Uniform(-dphi,dphi); | |
686 | } | |
687 | ||
688 | UShort_t volid = AliGeomManager::LayerToVolUID(lay,iModule); | |
689 | const char *symname = AliGeomManager::SymName(volid); | |
690 | ||
691 | new((*fAlignObjArray)[fInd]) AliAlignObjParams(symname,volid,vx,vy,vz,vpsi,vtheta,vphi,kFALSE); | |
692 | fInd++; | |
693 | } | |
694 | ||
695 | return kTRUE; | |
696 | } | |
697 | ||
698 | //________________________________________________________________________ | |
699 | Bool_t AliITSMisAligner::AddAlignObj(Int_t lay,Int_t ladd,Double_t dx,Double_t dy,Double_t dz, | |
700 | Double_t dpsi,Double_t dtheta,Double_t dphi, | |
701 | Double_t xShift,Double_t yShift,Double_t zShift, | |
702 | Double_t psiShift,Double_t thetaShift,Double_t phiShift, | |
703 | Bool_t unif) { | |
704 | // | |
705 | // misalignment at the level of half-staves/ladders (ladd=-1 means that all ladders are scanned) | |
706 | // | |
707 | Double_t vx,vy,vz,vpsi,vtheta,vphi; | |
708 | Double_t tr[3],rot[3]; | |
709 | ||
710 | Int_t laddMin = ladd; | |
711 | Int_t laddMax = laddMin+1; | |
712 | if (ladd<0) { | |
713 | laddMin = 0; | |
714 | laddMax = fgkNLadders[lay]; | |
715 | } | |
716 | ||
717 | for (Int_t iLadd=laddMin; iLadd<laddMax; iLadd++) { | |
718 | ||
719 | Int_t nHS = 1; | |
720 | if (lay<2) nHS = 2; | |
721 | for (Int_t iHalfStave=0; iHalfStave<nHS; iHalfStave++) { | |
722 | ||
723 | if(!unif) { | |
724 | vx = AliMathBase::TruncatedGaus(0.,dx/3.,dx); // mean, sigma, max absolute value | |
725 | vy = AliMathBase::TruncatedGaus(0.,dy/3.,dy); | |
726 | vz = AliMathBase::TruncatedGaus(0.,dz/3.,dz); | |
727 | vpsi = AliMathBase::TruncatedGaus(0.,dpsi/3.,dpsi); | |
728 | vtheta = AliMathBase::TruncatedGaus(0.,dtheta/3.,dtheta); | |
729 | vphi = AliMathBase::TruncatedGaus(0.,dphi/3.,dphi); | |
730 | } else { | |
731 | vx = fRnd.Uniform(-dx,dx); | |
732 | vy = fRnd.Uniform(-dy,dy); | |
733 | vz = fRnd.Uniform(-dz,dz); | |
734 | vpsi = fRnd.Uniform(-dpsi,dpsi); | |
735 | vtheta = fRnd.Uniform(-dtheta,dtheta); | |
736 | vphi = fRnd.Uniform(-dphi,dphi); | |
737 | } | |
738 | ||
739 | TString name(GetHalfStaveLadderSymbName(lay,iLadd,iHalfStave)); | |
740 | ||
741 | // first apply half-stave / ladder level misalignment | |
742 | AliAlignObjParams aaop(name.Data(),0,vx,vy,vz,vpsi,vtheta,vphi,kFALSE); // set them as local | |
743 | aaop.GetPars(tr,rot); // global | |
744 | ||
745 | // then, apply layer-level misalignment (only for SDD and SSD) | |
746 | if(lay>1) { | |
747 | tr[0] += xShift; | |
748 | tr[1] += yShift; | |
749 | tr[2] += zShift; | |
750 | rot[0] += psiShift; | |
751 | rot[1] += thetaShift; | |
752 | rot[2] += phiShift; | |
753 | } | |
754 | new((*fAlignObjArray)[fInd]) AliAlignObjParams(name.Data(),0,tr[0],tr[1],tr[2],rot[0],rot[1],rot[2],kTRUE); // set them as global | |
755 | ||
756 | AliAlignObjParams* itsalobj = (AliAlignObjParams*) fAlignObjArray->UncheckedAt(fInd); | |
757 | itsalobj->ApplyToGeometry(); | |
758 | fInd++; | |
759 | } | |
760 | } | |
761 | ||
762 | return kTRUE; | |
763 | } | |
764 | ||
765 | ||
766 | //________________________________________________________________________ | |
767 | Bool_t AliITSMisAligner::AddSectorAlignObj(Int_t sectMin,Int_t sectMax, | |
768 | Double_t dx,Double_t dy,Double_t dz, | |
769 | Double_t dpsi,Double_t dtheta,Double_t dphi, | |
770 | Double_t xShift,Double_t yShift,Double_t zShift, | |
771 | Double_t psiShift,Double_t thetaShift,Double_t phiShift,Bool_t unif) { | |
772 | // | |
773 | // misalignment at the level of SPD sectors and half-barrels | |
774 | // | |
775 | ||
776 | if ((sectMin<1) || (sectMax>10)) return kFALSE; | |
777 | Double_t vx,vy,vz,vpsi,vtheta,vphi; | |
778 | Double_t tr[3],rot[3]; | |
779 | ||
780 | for (Int_t iSect = sectMin-1; iSect<sectMax; iSect++) { | |
781 | ||
782 | // first, apply sector level misalignment | |
783 | if(!unif) { | |
784 | vx = AliMathBase::TruncatedGaus(0.,dx/3.,dx); // mean, sigma, max absolute value | |
785 | vy = AliMathBase::TruncatedGaus(0.,dy/3.,dy); | |
786 | vz = AliMathBase::TruncatedGaus(0.,dz/3.,dz); | |
787 | vpsi = AliMathBase::TruncatedGaus(0.,dpsi/3.,dpsi); | |
788 | vtheta = AliMathBase::TruncatedGaus(0.,dtheta/3.,dtheta); | |
789 | vphi = AliMathBase::TruncatedGaus(0.,dphi/3.,dphi); | |
790 | } else { | |
791 | vx = fRnd.Uniform(-dx,dx); | |
792 | vy = fRnd.Uniform(-dy,dy); | |
793 | vz = fRnd.Uniform(-dz,dz); | |
794 | vpsi = fRnd.Uniform(-dpsi,dpsi); | |
795 | vtheta = fRnd.Uniform(-dtheta,dtheta); | |
796 | vphi = fRnd.Uniform(-dphi,dphi); | |
797 | } | |
798 | ||
799 | TString name(GetSymbName(0)); | |
800 | name += fStrSector; | |
801 | name += iSect; | |
802 | ||
803 | ||
804 | AliAlignObjParams aaop(name.Data(),0,vx,vy,vz,vpsi,vtheta,vphi,kFALSE); // set them as local | |
805 | aaop.GetPars(tr,rot); // global | |
806 | ||
807 | // then, apply half-barrel level misalignment | |
808 | tr[0] += xShift; | |
809 | tr[1] += yShift; | |
810 | tr[2] += zShift; | |
811 | rot[0] += psiShift; | |
812 | rot[1] += thetaShift; | |
813 | rot[2] += phiShift; | |
814 | ||
815 | new((*fAlignObjArray)[fInd]) AliAlignObjParams(name.Data(),0,tr[0],tr[1],tr[2],rot[0],rot[1],rot[2],kTRUE); // set them as global | |
816 | ||
817 | AliAlignObjParams* itsalobj = (AliAlignObjParams*) fAlignObjArray->UncheckedAt(fInd); | |
818 | itsalobj->ApplyToGeometry(); | |
819 | fInd++; | |
820 | } | |
821 | return kTRUE; | |
822 | } | |
823 | ||
824 | //________________________________________________________________________ | |
825 | const char* AliITSMisAligner::GetSymbName(Int_t layer) const { | |
826 | // | |
827 | // be careful : SPD0 and SPD1 are not physically separated | |
828 | // | |
829 | TString name; | |
830 | switch (layer) { | |
831 | case 0: | |
832 | case 1: name = fStrSPD; name += layer; break; | |
833 | case 2: | |
834 | case 3: name = fStrSDD; name += layer; break; | |
835 | case 4: | |
836 | case 5: name = fStrSSD; name += layer; break; | |
837 | default: AliFatal("Wrong layer index"); | |
838 | } | |
839 | return name.Data(); | |
840 | } | |
841 | ||
842 | //________________________________________________________________________ | |
843 | const char* AliITSMisAligner::GetSymbName(Int_t layer, Int_t ladder, Int_t det) const { | |
844 | // | |
845 | // symname from layer, ladder, detector | |
846 | // | |
847 | TString symname(GetHalfStaveLadderSymbName(layer,ladder,det)); | |
848 | if(layer<=2){ | |
849 | symname+="Ladder"; | |
850 | }else if(layer<=6){ | |
851 | symname+="Sensor"; | |
852 | }else{ | |
853 | AliError("Invalid layer!"); | |
854 | return 0; | |
855 | } | |
856 | symname+=det; | |
857 | return symname.Data(); | |
858 | } | |
859 | ||
860 | //________________________________________________________________________ | |
861 | const char* AliITSMisAligner::GetSymbName(Int_t layer,Int_t ladd) const { | |
862 | // | |
863 | // Get logical names at the level of staves / ladders | |
864 | // | |
865 | TString name(GetSymbName(layer)); | |
866 | if (layer==0) { // SPD1 | |
867 | ||
868 | int sector = ladd/2; | |
869 | name += fStrSector; | |
870 | name += sector; | |
871 | int stave = ladd-sector*2; | |
872 | name += fStrStave; | |
873 | name += stave; | |
874 | } | |
875 | else if (layer==1) { // SPD2 | |
876 | ||
877 | int sector = ladd/4; | |
878 | name += fStrSector; | |
879 | name += sector; | |
880 | int stave = ladd-sector*4; | |
881 | name += fStrStave; | |
882 | name += stave; | |
883 | } | |
884 | else if (layer>=2 && layer<=5) { // SDD and SSD | |
885 | name += fStrLadder; | |
886 | name += ladd; | |
887 | } | |
888 | else { | |
889 | AliFatal("Wrong layer index"); | |
890 | } | |
891 | return name.Data(); | |
892 | } | |
893 | ||
894 | //________________________________________________________________________ | |
895 | const char* AliITSMisAligner::GetHalfStaveLadderSymbName(Int_t layer,Int_t ladd,Int_t halfStave) const { | |
896 | // | |
897 | // Get logical names at the level of half-staves (SPD) or ladders (SDD and SSD) | |
898 | // | |
899 | TString name(GetSymbName(layer)); | |
900 | if (layer==0) { // SPD1 | |
901 | ||
902 | int sector = ladd/2; | |
903 | name += fStrSector; | |
904 | name += sector; | |
905 | int stave = ladd-sector*2; | |
906 | name += fStrStave; | |
907 | name += stave; | |
908 | name += fStrHalfStave; | |
909 | name += halfStave; | |
910 | } | |
911 | else if (layer==1) { // SPD2 | |
912 | ||
913 | int sector = ladd/4; | |
914 | name += fStrSector; | |
915 | name += sector; | |
916 | int stave = ladd-sector*4; | |
917 | name += fStrStave; | |
918 | name += stave; | |
919 | name += fStrHalfStave; | |
920 | name += halfStave; | |
921 | } | |
922 | else if (layer>=2 && layer<=5) { // SDD and SSD | |
923 | name += fStrLadder; | |
924 | name += ladd; | |
925 | } | |
926 | else { | |
927 | AliFatal("Wrong layer index"); | |
928 | } | |
929 | return name.Data(); | |
930 | } | |
931 | ||
932 | //________________________________________________________________________ | |
933 | const char* AliITSMisAligner::GetParentSymName(const char* symname) { | |
934 | // | |
935 | // symnane of parent volume | |
936 | // | |
937 | TString parent(symname); | |
938 | // Give the symname of | |
939 | if(parent.BeginsWith('/')) parent.Remove(TString::kLeading,'/'); | |
940 | if(parent.EndsWith("/")) parent.Remove(TString::kTrailing,'/'); | |
941 | ||
942 | if(!parent.CountChar('/')) AliErrorClass("Not a valid symbolic name"); | |
943 | ||
944 | Int_t layer,level; | |
945 | GetLayerAndLevel(symname,layer,level); | |
946 | if(level==1) return "ITS"; | |
947 | ||
948 | parent.Remove(parent.Last('/')); | |
949 | ||
950 | if((layer==0 || layer==1) && level==2){ | |
951 | parent.Remove(parent.Last('/')); | |
952 | parent[7]='0'; | |
953 | } | |
954 | ||
955 | return parent.Data(); | |
956 | } | |
957 | ||
958 | //________________________________________________________________________ | |
959 | Bool_t AliITSMisAligner::GetLayerAndLevel(const char* symname, Int_t &layer, Int_t &level) { | |
960 | // | |
961 | // given the symbolic name set layer and level | |
962 | // | |
963 | const char* basename[6] = {"ITS/SPD0/Sector","ITS/SPD1/Sector","ITS/SDD2/Ladder","ITS/SDD3/Ladder","ITS/SSD4/Ladder","ITS/SSD5/Ladder"}; | |
964 | TString strSym(symname); | |
965 | if(strSym=="ITS"){ | |
966 | level=0; | |
967 | layer=-1; | |
968 | return kTRUE; | |
969 | } | |
970 | Int_t i; | |
971 | for(i=0; i<6; i++){ | |
972 | if(strSym.BeginsWith(basename[i])) break; | |
973 | } | |
974 | ||
975 | if(i>=6){ | |
976 | AliErrorClass(Form("%s is not a valid symbolic name for an ITS alignable volume",strSym.Data())); | |
977 | return kFALSE; | |
978 | } | |
979 | ||
980 | layer=i; | |
981 | //The part above could be replaced by just | |
982 | // TString seventh = strSym[7]; | |
983 | // layer = seventh.Atoi(); | |
984 | // if we don't need to check the validity of the symname | |
985 | ||
986 | level=1; | |
987 | switch(layer){ | |
988 | case 0: | |
989 | case 1: | |
990 | if(strSym.Contains("Stave")) level=2; | |
991 | if(strSym.Contains("Ladder")) level=3; | |
992 | break; | |
993 | case 2: | |
994 | case 3: | |
995 | case 4: | |
996 | case 5: | |
997 | if(strSym.Contains("Sensor")) level=2; | |
998 | } | |
999 | ||
1000 | return kTRUE; | |
1001 | } | |
1002 | ||
1003 | //________________________________________________________________________ | |
1004 | Int_t AliITSMisAligner::GetNSisters(const char* symname) { | |
1005 | // | |
1006 | // number of volumes on same level | |
1007 | // | |
1008 | Int_t layer,level; | |
1009 | if(!GetLayerAndLevel(symname,layer,level)) return -1; | |
1010 | if(level==0) return -1; | |
1011 | if(level==1) return GetNLadders(layer); | |
1012 | if(level==2) return GetNDetectors(layer); | |
1013 | AliErrorClass(Form("Invalid layer and level")); | |
1014 | return -1; | |
1015 | } | |
1016 | ||
1017 | //________________________________________________________________________ | |
1018 | Int_t AliITSMisAligner::GetNDaughters(const char* symname) { | |
1019 | // | |
1020 | // number of daughter volumes | |
1021 | // | |
1022 | Int_t layer,level; | |
1023 | if(!GetLayerAndLevel(symname,layer,level)) return -1; | |
1024 | if(level==0) { | |
1025 | Int_t nLadders = 0; | |
1026 | for(Int_t lay=0; lay<6; lay++) nLadders += GetNLadders(lay); | |
1027 | return nLadders; | |
1028 | } | |
1029 | if(level==1) return GetNDetectors(layer); | |
1030 | if(level==2){ | |
1031 | AliWarningClass(Form("Volume %s is a sensitive volume and has no alignable dauthers",symname)); | |
1032 | return -1; | |
1033 | } | |
1034 | AliErrorClass(Form("Invalid layer and level")); | |
1035 | return -1; | |
1036 | } | |
1037 | ||
1038 | /* | |
1039 | //________________________________________________________________________ | |
1040 | TString AliITSMisAligner::GetSymbName(Int_t layer,Int_t ladd,Int_t mod) const { | |
1041 | ||
1042 | // Get logical names at the level of SPD ladders / SDD and SSD modules | |
1043 | ||
1044 | Int_t halfStave = mod/2; | |
1045 | TString name = GetHalfStaveLadderSymbName(layer,ladd,halfStave); | |
1046 | ||
1047 | if (layer<2) { // SPD | |
1048 | name += fStrLadder; | |
1049 | name += mod; | |
1050 | } | |
1051 | else if (layer>=2 && layer<=5) { // SDD and SSD | |
1052 | name += fStrSensor; | |
1053 | name += mod; | |
1054 | } | |
1055 | else { | |
1056 | AliFatal("Wrong layer index"); | |
1057 | } | |
1058 | return name; | |
1059 | } | |
1060 | */ |