Fix coding rule violations
[u/mrichter/AliRoot.git] / TPC / AliTPCTransform.cxx
CommitLineData
022ee144 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//-------------------------------------------------------
17// Implementation of the TPC transformation class
18//
19// Origin: Marian Ivanov Marian.Ivanov@cern.ch
20// Magnus Mager
21//
22// Class for tranformation of the coordinate frame
66954e3f 23// Transformation
022ee144 24// local coordinate frame (sector, padrow, pad, timebine) ==>
25// rotated global (tracking) cooridnate frame (sector, lx,ly,lz)
26//
27// Unisochronity - (substract time0 - pad by pad)
28// Drift velocity - Currently common drift velocity - functionality of AliTPCParam
29// ExB effect -
30//
003b43ed 31// Time of flight correction -
32// - Depends on the vertex position
33// - by default
34//
022ee144 35// Usage:
36// AliTPCclustererMI::AddCluster
37// AliTPCtrackerMI::Transform
38//
39//-------------------------------------------------------
c1bdda91 40
41/* To test it:
42 cdb=AliCDBManager::Instance()
43 cdb->SetDefaultStorage("local:///u/mmager/mycalib1")
44 c=AliTPCcalibDB::Instance()
45 c->SetRun(0)
46 Double_t x[]={1.0,2.0,3.0}
47 Int_t i[]={4}
48 AliTPCTransform trafo
49 trafo.Transform(x,i,0,1)
50 */
51
022ee144 52/* $Id$ */
53
54#include "AliTPCROC.h"
55#include "AliTPCCalPad.h"
56#include "AliTPCCalROC.h"
57#include "AliTPCcalibDB.h"
58#include "AliTPCParam.h"
59#include "TMath.h"
60#include "AliLog.h"
61#include "AliTPCExB.h"
66954e3f 62#include "TGeoMatrix.h"
9430b11a 63#include "AliTPCRecoParam.h"
64#include "AliTPCCalibVdrift.h"
022ee144 65#include "AliTPCTransform.h"
1e6337b1 66#include <AliCTPTimeParams.h>
022ee144 67
66954e3f 68ClassImp(AliTPCTransform)
022ee144 69
70
9430b11a 71AliTPCTransform::AliTPCTransform():
72 AliTransform(),
73 fCurrentRecoParam(0), //! current reconstruction parameters
74 fCurrentRun(0), //! current run
75 fCurrentTimeStamp(0) //! current time stamp
76{
77 //
78 // Speed it up a bit!
79 //
80 for (Int_t i=0;i<18;++i) {
81 Double_t alpha=TMath::DegToRad()*(10.+20.*(i%18));
82 fSins[i]=TMath::Sin(alpha);
83 fCoss[i]=TMath::Cos(alpha);
84 }
85 fPrimVtx[0]=0;
86 fPrimVtx[1]=0;
87 fPrimVtx[2]=0;
88}
89AliTPCTransform::AliTPCTransform(const AliTPCTransform& transform):
90 AliTransform(transform),
91 fCurrentRecoParam(transform.fCurrentRecoParam), //! current reconstruction parameters
92 fCurrentRun(transform.fCurrentRun), //! current run
93 fCurrentTimeStamp(transform.fCurrentTimeStamp) //! current time stamp
003b43ed 94{
24db6af7 95 //
c1bdda91 96 // Speed it up a bit!
24db6af7 97 //
c1bdda91 98 for (Int_t i=0;i<18;++i) {
99 Double_t alpha=TMath::DegToRad()*(10.+20.*(i%18));
100 fSins[i]=TMath::Sin(alpha);
101 fCoss[i]=TMath::Cos(alpha);
102 }
003b43ed 103 fPrimVtx[0]=0;
104 fPrimVtx[1]=0;
105 fPrimVtx[2]=0;
c1bdda91 106}
107
108AliTPCTransform::~AliTPCTransform() {
24db6af7 109 //
110 // Destructor
111 //
c1bdda91 112}
113
003b43ed 114void AliTPCTransform::SetPrimVertex(Double_t *vtx){
115 //
116 //
117 //
118 fPrimVtx[0]=vtx[0];
119 fPrimVtx[1]=vtx[1];
120 fPrimVtx[2]=vtx[2];
121}
122
123
24db6af7 124void AliTPCTransform::Transform(Double_t *x,Int_t *i,UInt_t /*time*/,
003b43ed 125 Int_t /*coordinateType*/) {
24db6af7 126 // input: x[0] - pad row
127 // x[1] - pad
c1bdda91 128 // x[2] - time in us
129 // i[0] - sector
130 // output: x[0] - x (all in the rotated global coordinate frame)
131 // x[1] - y
132 // x[2] - z
ecc5dd8f 133 //
134 // primvtx - position of the primary vertex
135 // used for the TOF correction
136 // TOF of particle calculated assuming the speed-of-light and
137 // line approximation
138 //
139
24db6af7 140 Int_t row=TMath::Nint(x[0]);
141 Int_t pad=TMath::Nint(x[1]);
c1bdda91 142 Int_t sector=i[0];
9430b11a 143 AliTPCcalibDB* calib=AliTPCcalibDB::Instance();
24db6af7 144 //
145 AliTPCCalPad * time0TPC = calib->GetPadTime0();
2293155b 146 AliTPCCalPad * distortionMapY = calib->GetDistortionMap(0);
147 AliTPCCalPad * distortionMapZ = calib->GetDistortionMap(1);
24db6af7 148 AliTPCParam * param = calib->GetParameters();
149 if (!time0TPC){
150 AliFatal("Time unisochronity missing");
151 }
c1bdda91 152
24db6af7 153 if (!param){
154 AliFatal("Parameters missing");
155 }
c1bdda91 156
24db6af7 157 Double_t xx[3];
158 // Apply Time0 correction - Pad by pad fluctuation
159 //
160 x[2]-=time0TPC->GetCalROC(sector)->GetValue(row,pad);
161 //
162 // Tranform from pad - time coordinate system to the rotated global (tracking) system
163 //
164 Local2RotatedGlobal(sector,x);
165 //
166 //
167 //
c1bdda91 168 // Alignment
169 //TODO: calib->GetParameters()->GetClusterMatrix(sector)->LocalToMaster(x,xx);
c1bdda91 170 RotatedGlobal2Global(sector,x);
24db6af7 171 //
172 //
173 // ExB correction
174 //
3ce45991 175 if(fCurrentRecoParam&&fCurrentRecoParam->GetUseExBCorrection()) {
176
177 calib->GetExB()->Correct(x,xx);
178
179 } else {
180
181 xx[0] = x[0];
182 xx[1] = x[1];
183 xx[2] = x[2];
184 }
185
ecc5dd8f 186 //
187 // Time of flight correction
003b43ed 188 //
9430b11a 189 if (fCurrentRecoParam&&fCurrentRecoParam->GetUseTOFCorrection()){
190 const Int_t kNIS=param->GetNInnerSector(), kNOS=param->GetNOuterSector();
191 Float_t sign=1;
192 if (sector < kNIS) {
193 sign = (sector < kNIS/2) ? 1 : -1;
194 } else {
195 sign = ((sector-kNIS) < kNOS/2) ? 1 : -1;
196 }
197 Float_t deltaDr =0;
198 Float_t dist=0;
199 dist+=(fPrimVtx[0]-x[0])*(fPrimVtx[0]-x[0]);
200 dist+=(fPrimVtx[1]-x[1])*(fPrimVtx[1]-x[1]);
201 dist+=(fPrimVtx[2]-x[2])*(fPrimVtx[2]-x[2]);
202 dist = TMath::Sqrt(dist);
203 // drift length correction because of TOF
204 // the drift velocity is in cm/s therefore multiplication by 0.01
205 deltaDr = (dist*(0.01*param->GetDriftV()))/TMath::C();
206 xx[2]+=sign*deltaDr;
ecc5dd8f 207 }
9430b11a 208 //
209 //
210 //
211
ecc5dd8f 212 //
c1bdda91 213 Global2RotatedGlobal(sector,xx);
2293155b 214
215 //
216 // Apply non linear distortion correction
217 //
218 if (distortionMapY ){
219 //can be switch on for each dimension separatelly
220 if (fCurrentRecoParam->GetUseFieldCorrection()&0x2)
221 xx[1]-=distortionMapY->GetCalROC(sector)->GetValue(row,pad);
222 if (fCurrentRecoParam->GetUseFieldCorrection()&0x4)
223 xx[2]-=distortionMapZ->GetCalROC(sector)->GetValue(row,pad);
224 }
225
226
003b43ed 227 //
c1bdda91 228 x[0]=xx[0];x[1]=xx[1];x[2]=xx[2];
229}
230
24db6af7 231void AliTPCTransform::Local2RotatedGlobal(Int_t sector, Double_t *x) const {
232 //
233 //
022ee144 234 // Tranform coordinate from
235 // row, pad, time to x,y,z
24db6af7 236 //
022ee144 237 // Drift Velocity
238 // Current implementation - common drift velocity - for full chamber
24db6af7 239 // TODO: use a map or parametrisation!
240 //
241 //
242 //
9430b11a 243 const Int_t kMax =60; // cache for 60 seconds
244 static Int_t lastStamp=-1; //cached values
245 static Double_t lastCorr = 1;
246 //
66954e3f 247 AliTPCcalibDB* calib=AliTPCcalibDB::Instance();
24db6af7 248 AliTPCParam * param = calib->GetParameters();
9430b11a 249 AliTPCCalibVdrift *driftCalib = AliTPCcalibDB::Instance()->GetVdrift(fCurrentRun);
250 Double_t driftCorr = 1.;
251 if (driftCalib){
252 //
253 // caching drift correction - temp. fix
254 // Extremally slow procedure
255 if ( TMath::Abs((lastStamp)-Int_t(fCurrentTimeStamp))<kMax){
256 driftCorr = lastCorr;
257 }else{
258 driftCorr = 1.+(driftCalib->GetPTRelative(fCurrentTimeStamp,0)+ driftCalib->GetPTRelative(fCurrentTimeStamp,1))*0.5;
259 lastCorr=driftCorr;
260 lastStamp=fCurrentTimeStamp;
261
262 }
263 }
43a74775 264 //
a8f8b6a1 265 // simple caching non thread save
266 static Double_t vdcorrectionTime=1;
267 static Double_t time0corrTime=0;
268 static Int_t lastStampT=-1;
269 //
817766d5 270 if (lastStampT!=(Int_t)fCurrentTimeStamp){
a8f8b6a1 271 lastStampT=fCurrentTimeStamp;
272 if(fCurrentRecoParam&&fCurrentRecoParam->GetUseDriftCorrectionTime()>0) {
273 vdcorrectionTime = (1+AliTPCcalibDB::Instance()->
274 GetVDriftCorrectionTime(fCurrentTimeStamp,
fefec90f 275 fCurrentRun,
a8f8b6a1 276 sector%36>=18,
277 fCurrentRecoParam->GetUseDriftCorrectionTime()));
278 time0corrTime= AliTPCcalibDB::Instance()->
279 GetTime0CorrectionTime(fCurrentTimeStamp,
fefec90f 280 fCurrentRun,
a8f8b6a1 281 sector%36>=18,
282 fCurrentRecoParam->GetUseDriftCorrectionTime());
283 }
284 //
285 if(fCurrentRecoParam&&fCurrentRecoParam->GetUseDriftCorrectionGY()>0) {
286 Float_t xyzPad[3];
287 AliTPCROC::Instance()->GetPositionGlobal(sector, TMath::Nint(x[0]) ,TMath::Nint(x[1]), xyzPad);
288
289 Double_t corrGy= (1+(xyzPad[1])*AliTPCcalibDB::Instance()->
290 GetVDriftCorrectionGy(fCurrentTimeStamp,
291 AliTPCcalibDB::Instance()->GetRun(),
292 sector%36>=18,
293 fCurrentRecoParam->GetUseDriftCorrectionGY()));
294 vdcorrectionTime *=corrGy;
295 }
43a74775 296 }
9430b11a 297
298
24db6af7 299 if (!param){
300 AliFatal("Parameters missing");
301 }
302 Int_t row=TMath::Nint(x[0]);
9389f9a4 303 // Int_t pad=TMath::Nint(x[1]);
24db6af7 304 //
305 const Int_t kNIS=param->GetNInnerSector(), kNOS=param->GetNOuterSector();
306 Double_t sign = 1.;
502d13b5 307 Double_t zwidth = param->GetZWidth()*driftCorr;
308 if (AliTPCRecoParam:: GetUseTimeCalibration()) zwidth*=vdcorrectionTime;
24db6af7 309 Double_t padWidth = 0;
310 Double_t padLength = 0;
311 Double_t maxPad = 0;
312 //
313 if (sector < kNIS) {
314 maxPad = param->GetNPadsLow(row);
315 sign = (sector < kNIS/2) ? 1 : -1;
316 padLength = param->GetPadPitchLength(sector,row);
317 padWidth = param->GetPadPitchWidth(sector);
318 } else {
319 maxPad = param->GetNPadsUp(row);
320 sign = ((sector-kNIS) < kNOS/2) ? 1 : -1;
321 padLength = param->GetPadPitchLength(sector,row);
322 padWidth = param->GetPadPitchWidth(sector);
323 }
324 //
325 // X coordinate
022ee144 326 x[0] = param->GetPadRowRadii(sector,row); // padrow X position - ideal
24db6af7 327 //
328 // Y coordinate
329 //
330 x[1]=(x[1]-0.5*maxPad)*padWidth;
afbaa016 331 // pads are mirrorred on C-side
332 if (sector%36>17){
333 x[1]*=-1;
334 }
335
336 //
337
24db6af7 338 //
339 // Z coordinate
340 //
1e6337b1 341 if (AliTPCcalibDB::Instance()->IsTrgL0()){
342 // by defualt we assume L1 trigger is used - make a correction in case of L0
343 AliCTPTimeParams* ctp = AliTPCcalibDB::Instance()->GetCTPTimeParams();
3d1b41c1 344 if (ctp){
345 //for TPC standalone runs no ctp info
346 Double_t delay = ctp->GetDelayL1L0()*0.000000025;
347 x[2]-=delay/param->GetTSample();
348 }
1e6337b1 349 }
350 x[2]-= param->GetNTBinsL1();
24db6af7 351 x[2]*= zwidth; // tranform time bin to the distance to the ROC
1e6337b1 352 x[2]-= 3.*param->GetZSigma() + time0corrTime;
24db6af7 353 // subtract the time offsets
354 x[2] = sign*( param->GetZLength(sector) - x[2]);
c1bdda91 355}
356
c2da420d 357void AliTPCTransform::RotatedGlobal2Global(Int_t sector,Double_t *x) const {
24db6af7 358 //
359 // transform possition rotated global to the global
360 //
c1bdda91 361 Double_t cos,sin;
362 GetCosAndSin(sector,cos,sin);
363 Double_t tmp=x[0];
e81544f7 364 x[0]= cos*tmp-sin*x[1];
365 x[1]=+sin*tmp+cos*x[1];
c1bdda91 366}
367
c2da420d 368void AliTPCTransform::Global2RotatedGlobal(Int_t sector,Double_t *x) const {
24db6af7 369 //
370 // tranform possition Global2RotatedGlobal
371 //
c1bdda91 372 Double_t cos,sin;
373 GetCosAndSin(sector,cos,sin);
374 Double_t tmp=x[0];
e81544f7 375 x[0]= cos*tmp+sin*x[1];
376 x[1]= -sin*tmp+cos*x[1];
c1bdda91 377}
378
c2da420d 379void AliTPCTransform::GetCosAndSin(Int_t sector,Double_t &cos,
c1bdda91 380 Double_t &sin) const {
381 cos=fCoss[sector%18];
382 sin=fSins[sector%18];
383}
384
c1bdda91 385
43a74775 386void AliTPCTransform::ApplyTransformations(Double_t */*xyz*/, Int_t /*volID*/){
387 //
388 // Modify global position
389 // xyz - global xyz position
390 // volID - volID of detector (sector number)
391 //
392 //
393
394}