1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
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 **************************************************************************/
19 #include "AliITSsegmentationSSD.h"
20 #include "AliITSgeom.h"
23 ClassImp(AliITSsegmentationSSD)
24 AliITSsegmentationSSD::AliITSsegmentationSSD(){
25 // default constructor
29 //------------------------------
30 AliITSsegmentationSSD::AliITSsegmentationSSD(AliITSgeom *geom){
35 cout<<"Dx="<<fDx<<endl;
41 //____________________________________________________________________________
42 AliITSsegmentationSSD& AliITSsegmentationSSD::operator=(AliITSsegmentationSSD &source){
44 if(this==&source) return *this;
45 this->fNstrips = source.fNstrips;
46 this->fStereoP = source.fStereoP;
47 this->fStereoN = source.fStereoN;
48 this->fPitch = source.fPitch;
49 this->fDz = source.fDz;
50 this->fDx = source.fDx;
51 this->fDy = source.fDy;
52 this->fGeom = source.fGeom; // copy only the pointer
53 this->fCorr = new TF1(*(source.fCorr)); // make a proper copy
57 //____________________________________________________________________________
58 AliITSsegmentationSSD::AliITSsegmentationSSD(AliITSsegmentationSSD &source){
62 //------------------------------
63 void AliITSsegmentationSSD::Init(){
64 // standard initalizer
66 //AliITSgeomSSD *gssd = (AliITSgeomSSD *) (fGeom->GetShape(5,1,1));
67 //const Float_t kconv=10000.;
69 fDx = 2.*kconv*gssd->GetDx();
70 fDz = 2.*kconv*gssd->GetDz();
71 fDy = 2.*kconv*gssd->GetDy();
78 //-------------------------------------------------------
79 void AliITSsegmentationSSD::GetPadTxz(Float_t &x,Float_t &z){
80 // returns P and N sided strip numbers for a given location.
81 // Transformation from microns detector center local coordinates
82 // to detector P and N side strip numbers..
85 fNstrips v | N-Side ...0
86 \-------/------------|-----------\--------\
87 |\\\\\\/////////////.|\\\\\\\\\\\\\\\\\\\\|
88 |0\\\\/////////////..|.\\\\\\\\\\\\\\\\\\\|
89 |00\\/////////////...|..\\\\\\\\\\\\\\\\\\|
90 X <--|000/////////////... |...\\\\\\\\\\\\\\\\\|
91 |00/////////////... | ...\\\\\\\\\\\\\\\\|
92 |0/////////////... | ...\\\\\\\\\\\\\\\|
93 |//////////////... | ...\\\\\\\\\\\\\\\|
94 /-----\--------------|--------------------/
95 fNstrips-1 P-Side ...0
101 // expects x, z in microns
103 Float_t tanP=TMath::Tan(fStereoP);
104 Float_t tanN=TMath::Tan(-fStereoN);
109 x = (x1 - z1*tanP)/fPitch;
110 z = (x1 - tanN*(z1 - fDz))/fPitch;
112 //-------------------------------------------------------
113 void AliITSsegmentationSSD::GetPadIxz(Float_t x,Float_t z,Int_t &iP,Int_t &iN)
115 // returns P and N sided strip numbers for a given location.
118 fNstrips v | N-Side ...0
119 \-------/------------|-----------\--------\
120 |\\\\\\/////////////.|\\\\\\\\\\\\\\\\\\\\|
121 |0\\\\/////////////..|.\\\\\\\\\\\\\\\\\\\|
122 |00\\/////////////...|..\\\\\\\\\\\\\\\\\\|
123 X <--|000/////////////... |...\\\\\\\\\\\\\\\\\|
124 |00/////////////... | ...\\\\\\\\\\\\\\\\|
125 |0/////////////... | ...\\\\\\\\\\\\\\\|
126 |//////////////... | ...\\\\\\\\\\\\\\\|
127 /-----\--------------|--------------------/
128 fNstrips-1 P-Side ...0
135 // expects x, z in microns
137 Float_t tanP=TMath::Tan(fStereoP);
138 Float_t tanN=TMath::Tan(fStereoN);
139 //cout<<"1 segment::GetPad: xL,zL,fDx,fDz ="<<x<<","<<z<<","<<fDx<<","<<fDz<<endl;
140 //cout<<"2 segment: ? tanP,tanN ="<<tanP<<","<<tanN<<endl;
144 // cout << "GetPadIxz::Tan(" << fStereoP << ")=" << tanP << endl;
145 // cout << "GetPadIxz::Tan(" << fStereoN << ")=" << tanN << endl;
148 Float_t ldX = x1 - z1*tanP; // distance from left-down edge
150 this->GetPadTxz(x,z); // use existing routine.
151 iP = (Int_t) x; //(Int_t)(ldX/fPitch);
153 iP = (iP>fNstrips)? -1: iP;
155 //cout<<"3 segment::GetPad: x1,tanP,ix1 ="<<ldX<<","<<tanP<<","<<iP<<endl;
157 ldX = x1 - tanN*(fDz - z1);
159 iN = (Int_t) z; //(Int_t)(ldX/fPitch);
161 iN = (iN>fNstrips)? -1: iN;
163 //cout<<"4 segment::GetPad: x2,tanN,ix2 ="<<ldX<<","<<tanN<<","<<iN<<endl;
166 //-------------------------------------------------------
167 void AliITSsegmentationSSD::GetPadCxz(Int_t iP,Int_t iN,Float_t &x,Float_t &z)
169 // actually this is the GetCrossing(Float_t &,Float_t &)
171 // returns x, z in microns !
175 Float_t tanP=TMath::Tan(fStereoP);
176 Float_t tanN=TMath::Tan(fStereoN);
179 // cout << "GetPadCxz::Tan(" << fStereoP << ")=" << tanP << endl;
180 // cout << "GetPadCxz::Tan(" << fStereoN << ")=" << tanN << endl;
181 // cout << "GetPadCxz::dx=" << dx << endl;
185 if(tanP + tanN == 0) {x=z=flag; return ;}
187 z = (z - x + tanN * fDz) / (tanP + tanN);
193 if ( ( z < -(fDz/2+dx) ) || ( z > (fDz/2+dx) ) ) {x=z=flag; return ;}
194 if ( ( x < -(fDx/2+dx) ) || ( x > (fDx/2+dx) ) ) {x=z=flag; return ;}
198 //______________________________________________________________________
199 void AliITSsegmentationSSD::LocalToDet(Float_t x,Float_t z,
200 Int_t &iP,Int_t &iN){
201 // Transformation from Geant cm detector center local coordinates
202 // to detector P and N side strip numbers..
205 fNstrips v | N-Side ...0
206 \-------/------------|-----------\--------\
207 |\\\\\\/////////////.|\\\\\\\\\\\\\\\\\\\\|
208 |0\\\\/////////////..|.\\\\\\\\\\\\\\\\\\\|
209 |00\\/////////////...|..\\\\\\\\\\\\\\\\\\|
210 X <--|000/////////////... |...\\\\\\\\\\\\\\\\\|
211 |00/////////////... | ...\\\\\\\\\\\\\\\\|
212 |0/////////////... | ...\\\\\\\\\\\\\\\|
213 |//////////////... | ...\\\\\\\\\\\\\\\|
214 /-----\--------------|--------------------/
215 fNstrips-1 P-Side ...0
222 const Double_t kconst = 1.0E-04; // convert microns to cm.
224 x /= kconst; // convert to microns
225 z /= kconst; // convert to microns
226 this->GetPadTxz(x,z);
230 if(iP<0 || iP>=fNstrips) iP=-1; // strip number must be in range.
233 if(iN<0 || iN>=fNstrips) iN=-1; // strip number must be in range.
236 //----------------------------------------------------------------------
237 void AliITSsegmentationSSD::DetToLocal(Int_t ix,Int_t iPN,
238 Float_t &x,Float_t &z){
239 // Transformation from detector segmentation/cell coordiantes starting
240 // from 0. iPN=0 for P side and 1 for N side strip. Returned is z=0.0
241 // and the corresponding x value..
244 fNstrips v | N-Side ...0
245 \-------/------------|-----------\--------\
246 |\\\\\\/////////////.|\\\\\\\\\\\\\\\\\\\\|
247 |0\\\\/////////////..|.\\\\\\\\\\\\\\\\\\\|
248 |00\\/////////////...|..\\\\\\\\\\\\\\\\\\|
249 X <--|000/////////////... |...\\\\\\\\\\\\\\\\\|
250 |00/////////////... | ...\\\\\\\\\\\\\\\\|
251 |0/////////////... | ...\\\\\\\\\\\\\\\|
252 |//////////////... | ...\\\\\\\\\\\\\\\|
253 /-----\--------------|--------------------/
254 fNstrips-1 P-Side ...0
262 // x = a + b + z*tan(fStereoP); a = Dpx(iP)*(iP+0.5)-dx; b = dz*th;
264 // x = a + b + z*tan(fStereoP); a = Dpx(iN)*(iN+0.5)-dx; b = -dz*th;
265 const Double_t kconst = 1.0E-04; // convert microns to cm.
266 Float_t flag=kconst*Dx(); // error value
267 Double_t th=0.0,dx,dz,i,a,b=0.0,xb[4],zb[4];
269 z = 0.0; // Strip center in z.
270 if(iPN<0 || iPN>1){// if error return full detector size in x.
271 x = z = flag; return;
273 if(ix<0 || ix>=fNstrips) {x = z = flag; return;} // if error return full
274 // detector size in x.
275 i = (Double_t) ix; // convert to double
276 dx = 0.5*kconst*Dx(); // half distance in x in cm
277 dz = 0.5*kconst*Dz(); // half distance in z in cm
278 a = kconst*Dpx(ix)*(i+0.5)-dx; // Min x value.
279 if(iPN==0){ //P-side angle defined backwards.
280 th = TMath::Tan(fStereoP);
282 }else if(iPN==1){ // N-side
283 th = TMath::Tan(-fStereoN);
286 // compute average/center position of the strip.
287 xb[0] = +dx; if(th!=0.0) zb[0] = (+dx-a-b)/th; else zb[0] = 0.0;
288 xb[1] = -dx; if(th!=0.0) zb[1] = (-dx-a-b)/th; else zb[1] = 0.0;
289 xb[2] = a+b+dz*th; zb[2] = +dz;
290 xb[3] = a+b-dz*th; zb[3] = -dz;
292 for(Int_t j=0;j<4;j++){
293 // cout << "xb["<<j<<"]="<<xb[j]<<" zb["<<j<<"[="<<zb[j]<<endl;
294 if(xb[j]>=-dx && xb[j]<=dx && zb[j]>=-dz && zb[j]<=dz){
303 //----------------------------------------------------------------------
304 Bool_t AliITSsegmentationSSD::GetCrossing(Int_t iP,Int_t iN,
305 Float_t &x,Float_t &z,
307 // Given one P side strip and one N side strip, Returns kTRUE if they
308 // cross each other and the location of the two crossing strips and
309 // their correxlation matrix c[2][2].
312 fNstrips v | N-Side ...0
313 \-------/------------|-----------\--------\
314 |\\\\\\/////////////.|\\\\\\\\\\\\\\\\\\\\|
315 |0\\\\/////////////..|.\\\\\\\\\\\\\\\\\\\|
316 |00\\/////////////...|..\\\\\\\\\\\\\\\\\\|
317 X <--|000/////////////... |...\\\\\\\\\\\\\\\\\|
318 |00/////////////... | ...\\\\\\\\\\\\\\\\|
319 |0/////////////... | ...\\\\\\\\\\\\\\\|
320 |//////////////... | ...\\\\\\\\\\\\\\\|
321 /-----\--------------|--------------------/
322 fNstrips-1 P-Side ...0
328 c[2][2] is defined as follows
329 /c[0][0] c[0][1]\ /delta iP\ = /delta x\
330 \c[1][0] c[1][1]/ \delta iN/ = \delta z/
332 const Double_t kconst = 1.0E-04; // convert microns to cm.
333 Double_t thp,thn,th,dx,dz,p,ip,in;
336 thp = TMath::Tan(fStereoP);
337 thn = TMath::Tan(-fStereoN);
339 if(th==0.0) { // parall strips then never cross.
342 c[0][0] = c[1][0] = c[0][1] = c[1][1] = 0.0;
345 // The strips must cross some place in space.
346 ip = (Double_t) iP; // convert to double now for speed
347 in = (Double_t) iN; // convert to double now for speed
348 dx = 0.5*kconst*Dx(); // half distance in x in cm
349 dz = 0.5*kconst*Dz(); // half distance in z in cm
350 p = kconst*Dpx(iP); // Get strip spacing/pitch now
351 x = 0.5*p+dx + (p*(in*thp-ip*thn)-2.0*dz*thp*thn)/th;
352 z =(p*(in-ip)-dz*(thp+thn))/th;
353 // compute correlations.
354 c[0][0] = -thn*p/th; // dx/diP
355 c[1][1] = p/th; // dz/diN
356 c[0][1] = p*thp/th; // dx/diN
357 c[1][0] = -p/th; // dz/diP
358 if(x<-dx || x>dx || z<-dz || z>dz) return kFALSE; // crossing is outside
359 // of the detector so
360 // these strips don't