Set values to zero in constructor. Added print function.
[u/mrichter/AliRoot.git] / HLT / src / AliL3Track.cxx
1 // @(#) $Id$
2
3 // Author: Anders Vestbo <mailto:vestbo$fi.uib.no>, Uli Frankenfeld <mailto:franken@fi.uib.no>
4 //*-- Copyright &copy ALICE HLT Group
5
6 #include "AliL3StandardIncludes.h"
7 #include "AliL3RootTypes.h"
8 #include "AliL3RootTypes.h"
9 #include "AliL3Logging.h"
10 #include "AliL3Track.h"
11 #include "AliL3Transform.h"
12 #include "AliL3Vertex.h"
13 #include "AliL3SpacePointData.h"
14
15 #if __GNUC__ == 3
16 using namespace std;
17 #endif
18
19 /** \class AliL3Track
20 //<pre>
21 //_____________________________________________________________
22 // AliL3Track
23 //
24 // Track base class
25 //Begin_Html
26 //<img src="track_coordinates.gif">
27 //End_Html
28 </pre>
29 */
30
31 ClassImp(AliL3Track)
32
33
34 AliL3Track::AliL3Track()
35 {
36   //Constructor
37   fNHits = 0;
38   fMCid = -1;
39   fKappa=0;
40   fRadius=0;
41   fCenterX=0;
42   fCenterY=0;
43   ComesFromMainVertex(false);
44   fQ = 0;
45   fPhi0=0;
46   fPsi=0;
47   fR0=0;
48   fTanl=0;
49   fZ0=0;
50   fPt=0;
51   fLength=0;
52   fIsLocal=true;
53   fRowRange[0]=0;
54   fRowRange[1]=0;
55   SetFirstPoint(0,0,0);
56   SetLastPoint(0,0,0);
57   memset(fHitNumbers,0,159*sizeof(UInt_t));
58   fPID = 0;
59
60   fSector=0;
61   fPterr=0;
62   fPsierr=0;
63   fZ0err=0;
64   fTanlerr=0;
65   fPoint[0]=fPoint[1]=fPoint[2]=0;
66   fPointPsi=0;
67 }
68
69 void AliL3Track::Set(AliL3Track *tpt)
70 {
71   //setter
72   SetRowRange(tpt->GetFirstRow(),tpt->GetLastRow());
73   SetPhi0(tpt->GetPhi0());
74   SetKappa(tpt->GetKappa());
75   SetNHits(tpt->GetNHits());
76   SetFirstPoint(tpt->GetFirstPointX(),tpt->GetFirstPointY(),tpt->GetFirstPointZ());
77   SetLastPoint(tpt->GetLastPointX(),tpt->GetLastPointY(),tpt->GetLastPointZ());
78   SetPt(tpt->GetPt());
79   SetPsi(tpt->GetPsi());
80   SetTgl(tpt->GetTgl());
81   SetCharge(tpt->GetCharge());
82   SetHits(tpt->GetNHits(),(UInt_t *)tpt->GetHitNumbers());
83 #ifdef do_mc
84   SetMCid(tpt->GetMCid());
85 #endif
86   SetPID(tpt->GetPID());
87   SetSector(tpt->GetSector());
88 }
89
90 Int_t AliL3Track::Compare(const AliL3Track *track) const
91 {
92   // compare tracks
93   if(track->GetNHits() < GetNHits()) return 1;
94   if(track->GetNHits() > GetNHits()) return -1;
95   return 0;
96 }
97
98 AliL3Track::~AliL3Track()
99 {
100   //Nothing to do
101 }
102
103 Double_t AliL3Track::GetP() const
104 {
105   // Returns total momentum.  
106   return fabs(GetPt())*sqrt(1. + GetTgl()*GetTgl());
107 }
108
109 Double_t AliL3Track::GetPseudoRapidity() const
110 { //get pseudo rap
111   return 0.5 * log((GetP() + GetPz()) / (GetP() - GetPz()));
112 }
113
114 /*
115 Double_t AliL3Track::GetEta() const
116 {
117   return GetPseudoRapidity();
118 }
119 */
120
121 Double_t AliL3Track::GetRapidity() const
122
123   //get rap
124   const Double_t kmpi = 0.13957;
125   return 0.5 * log((kmpi + GetPz()) / (kmpi - GetPz()));
126 }
127
128 void AliL3Track::Rotate(Int_t slice,Bool_t tolocal)
129 {
130   //Rotate track to global parameters
131   //If flag tolocal is set, the track is rotated
132   //to local coordinates.
133
134   Float_t psi[1] = {GetPsi()};
135   if(!tolocal)
136     AliL3Transform::Local2GlobalAngle(psi,slice);
137   else
138     AliL3Transform::Global2LocalAngle(psi,slice);
139   SetPsi(psi[0]);
140   Float_t first[3];
141   first[0] = GetFirstPointX();
142   first[1] = GetFirstPointY();
143   first[2] = GetFirstPointZ();
144   if(!tolocal)
145     AliL3Transform::Local2Global(first,slice);
146   else
147     AliL3Transform::Global2LocHLT(first,slice);
148   //AliL3Transform::Global2Local(first,slice,kTRUE);
149   
150   SetFirstPoint(first[0],first[1],first[2]);
151   Float_t last[3];
152   last[0] = GetLastPointX();
153   last[1] = GetLastPointY();
154   last[2] = GetLastPointZ();
155   if(!tolocal)
156     AliL3Transform::Local2Global(last,slice);
157   else
158     AliL3Transform::Global2LocHLT(last,slice);    
159   //AliL3Transform::Global2Local(last,slice,kTRUE);
160   SetLastPoint(last[0],last[1],last[2]);
161   
162   Float_t center[3] = {GetCenterX(),GetCenterY(),0};
163   if(!tolocal)
164     AliL3Transform::Local2Global(center,slice);
165   else
166     AliL3Transform::Global2LocHLT(center,slice);
167   //AliL3Transform::Global2Local(center,slice,kTRUE);
168   SetCenterX(center[0]);
169   SetCenterY(center[1]);
170   
171   SetPhi0(atan2(fFirstPoint[1],fFirstPoint[0]));
172   SetR0(sqrt(fFirstPoint[0]*fFirstPoint[0]+fFirstPoint[1]*fFirstPoint[1]));
173   
174   if(!tolocal)
175     fIsLocal=kFALSE;
176   else
177     fIsLocal=kTRUE;
178 }
179
180 void AliL3Track::CalculateHelix()
181 {
182   //Calculate Radius, CenterX and CenterY from Psi, X0, Y0
183   fRadius = fPt / (AliL3Transform::GetBFieldValue());
184   if(fRadius) fKappa = -fQ*1./fRadius;
185   else fRadius = 999999;  //just zero
186   Double_t trackPhi0 = fPsi + fQ * AliL3Transform::PiHalf();
187
188   fCenterX = fFirstPoint[0] - fRadius *  cos(trackPhi0);
189   fCenterY = fFirstPoint[1] - fRadius *  sin(trackPhi0);
190   
191   SetPhi0(atan2(fFirstPoint[1],fFirstPoint[0]));
192   SetR0(sqrt(fFirstPoint[0]*fFirstPoint[0]+fFirstPoint[1]*fFirstPoint[1]));
193 }
194
195 Double_t AliL3Track::GetCrossingAngle(Int_t padrow,Int_t slice) 
196 {
197   //Calculate the crossing angle between track and given padrow.
198   //Take the dot product of the tangent vector of the track, and
199   //vector perpendicular to the padrow.
200   //In order to do this, we need the tangent vector to the track at the
201   //point. This is done by rotating the radius vector by 90 degrees;
202   //rotation matrix: (  0  1 )
203   //                 ( -1  0 )
204
205   Float_t angle=0;//Angle perpendicular to the padrow in local coordinates
206   if(slice>=0)//Global coordinates
207     {
208       AliL3Transform::Local2GlobalAngle(&angle,slice);
209       if(!CalculateReferencePoint(angle,AliL3Transform::Row2X(padrow)))
210         cerr<<"AliL3Track::GetCrossingAngle : Track does not cross line in slice "<<slice<<" row "<<padrow<<endl;
211     }
212   else //should be in local coordinates
213     {
214       Float_t xyz[3];
215       GetCrossingPoint(padrow,xyz);
216       fPoint[0] = xyz[0];
217       fPoint[1] = xyz[1];
218       fPoint[2] = xyz[2];
219     }
220     
221   Double_t tangent[2];
222   
223   tangent[0] = (fPoint[1] - GetCenterY())/GetRadius();
224   tangent[1] = -1.*(fPoint[0] - GetCenterX())/GetRadius();
225
226   Double_t perppadrow[2] = {cos(angle),sin(angle)}; 
227   Double_t cosbeta = fabs(tangent[0]*perppadrow[0] + tangent[1]*perppadrow[1]);
228   if(cosbeta > 1) cosbeta=1;
229   return acos(cosbeta);
230 }
231
232 Bool_t AliL3Track::GetCrossingPoint(Int_t padrow,Float_t *xyz)
233 {
234   //Assumes the track is given in local coordinates
235   
236   if(!IsLocal())
237     {
238       cerr<<"GetCrossingPoint: Track is given on global coordinates"<<endl;
239       return false;
240     }
241   
242   Double_t xHit = AliL3Transform::Row2X(padrow);
243
244   xyz[0] = xHit;
245   Double_t aa = (xHit - GetCenterX())*(xHit - GetCenterX());
246   Double_t r2 = GetRadius()*GetRadius();
247   if(aa > r2)
248     return false;
249
250   Double_t aa2 = sqrt(r2 - aa);
251   Double_t y1 = GetCenterY() + aa2;
252   Double_t y2 = GetCenterY() - aa2;
253   xyz[1] = y1;
254   if(fabs(y2) < fabs(y1)) xyz[1] = y2;
255  
256   Double_t yHit = xyz[1];
257   Double_t angle1 = atan2((yHit - GetCenterY()),(xHit - GetCenterX()));
258   if(angle1 < 0) angle1 += 2.*AliL3Transform::Pi();
259   Double_t angle2 = atan2((GetFirstPointY() - GetCenterY()),(GetFirstPointX() - GetCenterX()));
260   if(angle2 < 0) angle2 += AliL3Transform::TwoPi();
261   Double_t diffangle = angle1 - angle2;
262   diffangle = fmod(diffangle,AliL3Transform::TwoPi());
263   if((GetCharge()*diffangle) > 0) diffangle = diffangle - GetCharge()*AliL3Transform::TwoPi();
264   Double_t stot = fabs(diffangle)*GetRadius();
265   Double_t zHit = GetFirstPointZ() + stot*GetTgl();
266   xyz[2] = zHit;
267  
268   return true;
269
270 }
271
272 Bool_t AliL3Track::CalculateReferencePoint(Double_t angle,Double_t radius)
273 {
274   // Global coordinate: crossing point with y = ax+ b; 
275   // a=tan(angle-AliL3Transform::PiHalf());
276   //
277   const Double_t krr=radius; //position of reference plane
278   const Double_t kxr = cos(angle) * krr;
279   const Double_t kyr = sin(angle) * krr;
280   
281   Double_t a = tan(angle-AliL3Transform::PiHalf());
282   Double_t b = kyr - a * kxr;
283
284   Double_t pp=(fCenterX+a*fCenterY-a*b)/(1+pow(a,2));
285   Double_t qq=(pow(fCenterX,2)+pow(fCenterY,2)-2*fCenterY*b+pow(b,2)-pow(fRadius,2))/(1+pow(a,2));
286
287   Double_t racine = pp*pp-qq;
288   if(racine<0) return IsPoint(kFALSE);      //no Point
289
290   Double_t rootRacine = sqrt(racine);
291   Double_t x0 = pp+rootRacine;
292   Double_t x1 = pp-rootRacine;
293   Double_t y0 = a*x0 + b;
294   Double_t y1 = a*x1 + b;
295
296   Double_t diff0 = sqrt(pow(x0-kxr,2)+pow(y0-kyr,2));
297   Double_t diff1 = sqrt(pow(x1-kxr,2)+pow(y1-kyr,2));
298  
299   if(diff0<diff1){
300     fPoint[0]=x0;
301     fPoint[1]=y0;
302   }
303   else{
304     fPoint[0]=x1;
305     fPoint[1]=y1;
306   }
307
308   Double_t pointPhi0  = atan2(fPoint[1]-fCenterY,fPoint[0]-fCenterX);
309   Double_t trackPhi0  = atan2(fFirstPoint[1]-fCenterY,fFirstPoint[0]-fCenterX);
310   if(fabs(trackPhi0-pointPhi0)>AliL3Transform::Pi()){
311     if(trackPhi0<pointPhi0) trackPhi0 += AliL3Transform::TwoPi();
312     else                    pointPhi0 += AliL3Transform::TwoPi();
313   }
314   Double_t stot = -fQ * (pointPhi0-trackPhi0) * fRadius ;
315   fPoint[2]   = fFirstPoint[2] + stot * fTanl;
316
317   fPointPsi = pointPhi0 - fQ * AliL3Transform::PiHalf();
318   if(fPointPsi<0.)  fPointPsi+= AliL3Transform::TwoPi();
319   fPointPsi = fmod(fPointPsi, AliL3Transform::TwoPi());
320
321   return IsPoint(kTRUE);
322 }
323
324 Bool_t AliL3Track::CalculateEdgePoint(Double_t angle)
325 {
326   // Global coordinate: crossing point with y = ax; a=tan(angle);
327   //
328   Double_t rmin=AliL3Transform::Row2X(AliL3Transform::GetFirstRow(-1));  //min Radius of TPC
329   Double_t rmax=AliL3Transform::Row2X(AliL3Transform::GetLastRow(-1)); //max Radius of TPC
330
331   Double_t a = tan(angle);
332   Double_t pp=(fCenterX+a*fCenterY)/(1+pow(a,2));
333   Double_t qq=(pow(fCenterX,2)+pow(fCenterY,2)-pow(fRadius,2))/(1+pow(a,2));
334   Double_t racine = pp*pp-qq;
335   if(racine<0) return IsPoint(kFALSE);     //no Point
336   Double_t rootRacine = sqrt(racine);
337   Double_t x0 = pp+rootRacine;
338   Double_t x1 = pp-rootRacine;
339   Double_t y0 = a*x0;
340   Double_t y1 = a*x1;
341
342   Double_t r0 = sqrt(pow(x0,2)+pow(y0,2));
343   Double_t r1 = sqrt(pow(x1,2)+pow(y1,2)); 
344   //find the right crossing point:
345   //inside the TPC modules
346   Bool_t ok0 = kFALSE;
347   Bool_t ok1 = kFALSE;
348
349   if(r0>rmin&&r0<rmax){
350     Double_t da=atan2(y0,x0);
351     if(da<0) da+=AliL3Transform::TwoPi();
352     if(fabs(da-angle)<0.5)
353       ok0 = kTRUE;
354   }
355   if(r1>rmin&&r1<rmax){
356     Double_t da=atan2(y1,x1);
357     if(da<0) da+=AliL3Transform::TwoPi();
358     if(fabs(da-angle)<0.5)
359       ok1 = kTRUE;
360   }
361   if(!(ok0||ok1)) return IsPoint(kFALSE);   //no Point
362   
363   if(ok0&&ok1){
364     Double_t diff0 = sqrt(pow(fFirstPoint[0]-x0,2)+pow(fFirstPoint[1]-y0,2));
365     Double_t diff1 = sqrt(pow(fFirstPoint[0]-x1,2)+pow(fFirstPoint[1]-y1,2));
366     if(diff0<diff1) ok1 = kFALSE; //use ok0
367     else ok0 = kFALSE;            //use ok1
368   }
369   if(ok0){fPoint[0]=x0; fPoint[1]=y0;}
370   else   {fPoint[0]=x1; fPoint[1]=y1;}
371
372   Double_t pointPhi0  = atan2(fPoint[1]-fCenterY,fPoint[0]-fCenterX);
373   Double_t trackPhi0  = atan2(fFirstPoint[1]-fCenterY,fFirstPoint[0]-fCenterX);
374   if(fabs(trackPhi0-pointPhi0)>AliL3Transform::Pi()){
375     if(trackPhi0<pointPhi0) trackPhi0 += AliL3Transform::TwoPi();
376     else                    pointPhi0 += AliL3Transform::TwoPi();
377   }
378   Double_t stot = -fQ * (pointPhi0-trackPhi0) * fRadius ;
379   fPoint[2]   = fFirstPoint[2] + stot * fTanl;
380
381   fPointPsi = pointPhi0 - fQ * AliL3Transform::PiHalf();
382   if(fPointPsi<0.)  fPointPsi+= AliL3Transform::TwoPi();
383   fPointPsi = fmod(fPointPsi, AliL3Transform::TwoPi());
384
385   return IsPoint(kTRUE);
386 }
387
388 Bool_t AliL3Track::CalculatePoint(Double_t xplane)
389 {
390   // Local coordinate: crossing point with x plane
391   //
392   Double_t racine = pow(fRadius,2)-pow(xplane-fCenterX,2);
393   if(racine<0) return IsPoint(kFALSE);
394   Double_t rootRacine = sqrt(racine);
395
396   Double_t y0 = fCenterY + rootRacine;
397   Double_t y1 = fCenterY - rootRacine;
398   //Double_t diff0 = sqrt(pow(fFirstPoint[0]-xplane)+pow(fFirstPoint[1]-y0));
399   //Double_t diff1 = sqrt(pow(fFirstPoint[0]-xplane)+pow(fFirstPoint[1]-y1));
400   Double_t diff0 = fabs(y0-fFirstPoint[1]);
401   Double_t diff1 = fabs(y1-fFirstPoint[1]);
402
403   fPoint[0]=xplane;
404   if(diff0<diff1) fPoint[1]=y0;
405   else            fPoint[1]=y1;
406
407   Double_t pointPhi0  = atan2(fPoint[1]-fCenterY,fPoint[0]-fCenterX);
408   Double_t trackPhi0  = atan2(fFirstPoint[1]-fCenterY,fFirstPoint[0]-fCenterX);
409   if(fabs(trackPhi0-pointPhi0)>AliL3Transform::Pi()){
410     if(trackPhi0<pointPhi0) trackPhi0 += AliL3Transform::TwoPi();
411     else                    pointPhi0 += AliL3Transform::TwoPi();
412   }
413   Double_t stot = -fQ * (pointPhi0-trackPhi0) * fRadius ;  
414   fPoint[2]   = fFirstPoint[2] + stot * fTanl;
415
416   fPointPsi = pointPhi0 - fQ * AliL3Transform::PiHalf();
417   if(fPointPsi<0.)  fPointPsi+= AliL3Transform::TwoPi();
418   fPointPsi = fmod(fPointPsi, AliL3Transform::TwoPi());
419
420   return IsPoint(kTRUE);
421 }
422
423 void AliL3Track::UpdateToFirstPoint()
424 {
425   //Update track parameters to the innermost point on the track.
426   //This means that the parameters of the track will be given in the point
427   //of closest approach to the first innermost point, i.e. the point 
428   //lying on the track fit (and not the coordinates of the innermost point itself).
429   //This function assumes that fFirstPoint is already set to the coordinates of the innermost
430   //assigned cluster.
431   //
432   //During the helix-fit, the first point on the track is set to the coordinates
433   //of the innermost assigned cluster. This may be ok, if you just want a fast
434   //estimate of the "global" track parameters; such as the momentum etc.
435   //However, if you later on want to do more precise local calculations, such
436   //as impact parameter, residuals etc, you need to give the track parameters
437   //according to the actual fit.
438
439   Double_t xc = GetCenterX() - GetFirstPointX();
440   Double_t yc = GetCenterY() - GetFirstPointY();
441   
442   Double_t distx1 = xc*(1 + GetRadius()/sqrt(xc*xc + yc*yc));
443   Double_t disty1 = yc*(1 + GetRadius()/sqrt(xc*xc + yc*yc));
444   Double_t distance1 = sqrt(distx1*distx1 + disty1*disty1);
445   
446   Double_t distx2 = xc*(1 - GetRadius()/sqrt(xc*xc + yc*yc));
447   Double_t disty2 = yc*(1 - GetRadius()/sqrt(xc*xc + yc*yc));
448   Double_t distance2 = sqrt(distx2*distx2 + disty2*disty2);
449   
450   //Choose the closest:
451   Double_t point[2];
452   if(distance1 < distance2)
453     {
454       point[0] = distx1 + GetFirstPointX();
455       point[1] = disty1 + GetFirstPointY();
456     }
457   else
458     {
459       point[0] = distx2 + GetFirstPointX();
460       point[1] = disty2 + GetFirstPointY();
461     }
462
463   Double_t pointpsi = atan2(point[1]-GetCenterY(),point[0]-GetCenterX());
464   pointpsi -= GetCharge()*AliL3Transform::PiHalf();
465   if(pointpsi < 0) pointpsi += AliL3Transform::TwoPi();
466   
467   //Update the track parameters
468   SetR0(sqrt(point[0]*point[0]+point[1]*point[1]));
469   SetPhi0(atan2(point[1],point[0]));
470   SetFirstPoint(point[0],point[1],GetZ0());
471   SetPsi(pointpsi);
472   
473 }
474
475 void AliL3Track::GetClosestPoint(AliL3Vertex *vertex,Double_t &closestx,Double_t &closesty,Double_t &closestz)
476 {
477   //Calculate the point of closest approach to the vertex
478   //This function calculates the minimum distance from the helix to the vertex, and choose 
479   //the corresponding point lying on the helix as the point of closest approach.
480   
481   Double_t xc = GetCenterX() - vertex->GetX();
482   Double_t yc = GetCenterY() - vertex->GetY();
483   
484   Double_t distx1 = xc*(1 + GetRadius()/sqrt(xc*xc + yc*yc));
485   Double_t disty1 = yc*(1 + GetRadius()/sqrt(xc*xc + yc*yc));
486   Double_t distance1 = sqrt(distx1*distx1 + disty1*disty1);
487   
488   Double_t distx2 = xc*(1 - GetRadius()/sqrt(xc*xc + yc*yc));
489   Double_t disty2 = yc*(1 - GetRadius()/sqrt(xc*xc + yc*yc));
490   Double_t distance2 = sqrt(distx2*distx2 + disty2*disty2);
491   
492   //Choose the closest:
493   if(distance1 < distance2)
494     {
495       closestx = distx1 + vertex->GetX();
496       closesty = disty1 + vertex->GetY();
497     }
498   else
499     {
500       closestx = distx2 + vertex->GetX();
501       closesty = disty2 + vertex->GetY();
502     }
503   
504   //Get the z coordinate:
505   Double_t angle1 = atan2((closesty-GetCenterY()),(closestx-GetCenterX()));
506   if(angle1 < 0) angle1 = angle1 + AliL3Transform::TwoPi();
507  
508   Double_t angle2 = atan2((GetFirstPointY()-GetCenterY()),(GetFirstPointX()-GetCenterX()));
509   if(angle2 < 0) angle2 = angle2 + AliL3Transform::TwoPi();
510   
511   Double_t diff_angle = angle1 - angle2;
512   diff_angle = fmod(diff_angle,AliL3Transform::TwoPi());
513   
514   if((GetCharge()*diff_angle) < 0) diff_angle = diff_angle + GetCharge()*AliL3Transform::TwoPi();
515   Double_t stot = fabs(diff_angle)*GetRadius();
516   closestz = GetFirstPointZ() - stot*GetTgl();
517 }
518
519 void AliL3Track::Print() const
520 {
521   LOG(AliL3Log::kInformational,"AliL3Track::Print","Print values")
522     <<fNHits<<" "<<fMCid<<" "<<fKappa<<" "<<fRadius<<" "<<fCenterX<<" "<<fCenterY<<" "<<fFromMainVertex<<" "<<fRowRange[0]<<" "<<fRowRange[1]<<" "<<fSector<<" "<<fQ<<" "<<fTanl<<" "<<fPsi<<" "<<fPt<<" "<<fLength<<" "<<fPterr<<" "<<fPsierr<<" "<<fZ0err<<" "<<fTanlerr<<" "<<fPhi0<<" "<<fR0<<" "<<fZ0<<" "<<fFirstPoint[0]<<" "<<fFirstPoint[1]<<" "<<fFirstPoint[2]<<" "<<fLastPoint[0]<<" "<<fLastPoint[1]<<" "<<fLastPoint[2]<<" "<<fPoint[0]<<" "<<fPoint[1]<<" "<<fPoint[2]<<" "<<fPointPsi<<" "<<fIsPoint<<" "<<fIsLocal<<" "<<fPID<<ENDLOG; 
523
524 }