Formatting changes.
[u/mrichter/AliRoot.git] / MUON / AliMUONSt12QuadrantSegmentation.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 // Class AliMUONSt12QuadrantSegmentation
20 // -------------------------------------
21 // Segmentation for MUON quadrants of stations 1 and 2 using 
22 // the mapping package
23 // Author: Ivana Hrivnacova, IPN Orsay
24  
25 #include <TError.h>
26 #include <TF1.h>
27 #include <TObjArray.h>
28 #include <TVector2.h>
29 #include <TSystem.h>
30
31 #include "AliLog.h"
32
33 #include "AliMpPad.h"
34 #include "AliMpArea.h"
35 #include "AliMpSectorReader.h"
36 #include "AliMpSector.h"
37 #include "AliMpVPadIterator.h"
38 #include "AliMpSectorSegmentation.h"
39 #include "AliMpFiles.h"
40 #include "AliMpNeighboursPadIterator.h"
41
42 #include "AliMUONSt12QuadrantSegmentation.h"
43 #include "AliMUONConstants.h"
44
45 /// \cond CLASSIMP
46 ClassImp(AliMUONSt12QuadrantSegmentation)
47 /// \endcond
48
49 //______________________________________________________________________________
50 AliMUONSt12QuadrantSegmentation::AliMUONSt12QuadrantSegmentation(
51                                        AliMpVSegmentation* segmentation,
52                                        AliMpStationType stationType,
53                                        AliMpPlaneType planeType) 
54 : AliMUONVGeometryDESegmentation(),
55   fStationType(stationType),
56   fPlaneType(planeType),
57   fSector(0),
58   fSectorSegmentation(0),
59   fSectorIterator(0),
60   fWireD(0),
61   fChamber(0),
62   fId(0),
63   fRmin(0.),
64   fRmax(0.),
65   fZ(0.),
66   fIx(0),
67   fIy(0),
68   fX(0.),
69   fY(0.),
70   fZone(0),
71   fXhit(0.),
72   fYhit(0.),
73   fIxt(0),
74   fIyt(0),
75   fIwt(0),
76   fXt(0.),
77   fYt(0.),
78   fCorrA(0)
79 {
80 /// Standard constructor
81
82   fSectorSegmentation = dynamic_cast<AliMpSectorSegmentation*>(segmentation);
83   if (fSectorSegmentation)
84     fSector = fSectorSegmentation->GetSector();
85   else 
86     AliFatal("Wrong mapping segmentation type");
87     
88   // Anod pitch
89   if ( stationType == kStation1 )  
90     fWireD = AliMUONConstants::PitchSt1();
91   else if ( stationType == kStation2 )   
92     fWireD = AliMUONConstants::Pitch();
93   else  
94     AliFatal("Wrong station type");
95
96   fCorrA = new TObjArray(3);
97   fCorrA->AddAt(0,0);
98   fCorrA->AddAt(0,1);
99   fCorrA->AddAt(0,2);
100
101   AliDebug(1, Form("ctor this = %p", this) ); 
102 }
103
104 //______________________________________________________________________________
105 AliMUONSt12QuadrantSegmentation::AliMUONSt12QuadrantSegmentation() 
106 : AliMUONVGeometryDESegmentation(),
107   fStationType(kStation1),
108   fPlaneType(kBendingPlane),
109   fSector(0),
110   fSectorSegmentation(0),
111   fSectorIterator(0),
112   fWireD(0),
113   fChamber(0),
114   fId(0),
115   fRmin(0.),
116   fRmax(0.),
117   fZ(0.),
118   fIx(0),
119   fIy(0),
120   fX(0.),
121   fY(0.),
122   fZone(0),
123   fXhit(0.),
124   fYhit(0.),
125   fIxt(0),
126   fIyt(0),
127   fIwt(0),
128   fXt(0.),
129   fYt(0.),
130   fCorrA(0) 
131 {
132 /// Default Constructor
133
134   AliDebug(1, Form("default (empty) ctor this = %p", this));
135 }
136
137 //______________________________________________________________________________
138 AliMUONSt12QuadrantSegmentation::~AliMUONSt12QuadrantSegmentation() 
139 {
140 /// Destructor
141
142   AliDebug(1, Form("dtor this = %p", this));
143
144   delete fSectorIterator;  
145
146
147 //
148 // private methods
149 //
150
151 //______________________________________________________________________________
152 void AliMUONSt12QuadrantSegmentation::UpdateCurrentPadValues(const AliMpPad& pad)
153 {
154 /// Updates current pad values.
155
156   fIx = pad.GetIndices().GetFirst();
157   fIy = pad.GetIndices().GetSecond();
158   fX = pad.Position().X();
159   fY = pad.Position().Y();
160   fZone = fSectorSegmentation->Zone(pad);
161 }  
162
163
164 //
165 // public methods
166 //
167
168 //______________________________________________________________________________
169 void AliMUONSt12QuadrantSegmentation::SetPadSize(Float_t /*p1*/, Float_t /*p2*/)
170 {
171 /// Set pad size Dx*Dy 
172
173   AliFatal("Not uniform pad size.");
174 }
175
176 //______________________________________________________________________________
177 void AliMUONSt12QuadrantSegmentation::SetDAnod(Float_t d)
178 {
179 /// Set anod pitch
180
181   fWireD = d;
182 }
183
184 #include "AliMpMotifMap.h"
185 //______________________________________________________________________________
186 Bool_t  AliMUONSt12QuadrantSegmentation::HasPad(Float_t x, Float_t y, Float_t /*z*/)
187
188 /// Returns true if a pad exists in the given position
189
190   // fSector->GetMotifMap()->Print();
191
192   AliMpPad pad = fSectorSegmentation
193                ->PadByPosition(TVector2(x,y), false);
194
195   return pad.IsValid();
196 }  
197
198
199 //______________________________________________________________________________
200 Bool_t  AliMUONSt12QuadrantSegmentation::HasPad(Int_t ix, Int_t iy)
201 {
202 /// Returns true if a pad with given indices exists
203
204   AliMpPad pad = fSectorSegmentation->PadByIndices(AliMpIntPair(ix,iy), false);
205
206   return pad.IsValid();
207 }  
208
209
210 //______________________________________________________________________________
211 AliMUONGeometryDirection  AliMUONSt12QuadrantSegmentation::GetDirection()
212 {
213 /// Returns the direction with a constant pad size  
214 /// (Direction or coordinate where the resolution is the best)
215
216   switch ( fSector->GetDirection() ) {
217     case kX: return kDirX;
218     case kY: return kDirY;
219     default: return kDirUndefined;
220   }  
221 }  
222
223 //______________________________________________________________________________
224 const AliMpVSegmentation*  
225 AliMUONSt12QuadrantSegmentation::GetMpSegmentation() const
226 {
227 /// Returns the mapping segmentation
228 /// (provides access to electronics info)
229
230   return fSectorSegmentation;
231 }  
232
233 //______________________________________________________________________________
234 Float_t AliMUONSt12QuadrantSegmentation::GetAnod(Float_t xhit) const
235 {
236 /// Anod wire coordinate closest to xhit
237 /// Returns for a hit position xhit the position of the nearest anode wire    
238 /// From AliMUONSegmentationV01.
239
240   Float_t wire= (xhit>0) ? Int_t(xhit/fWireD) + 0.5
241                          : Int_t(xhit/fWireD) - 0.5;
242   return fWireD*wire;
243
244 }
245
246 //______________________________________________________________________________
247 void  AliMUONSt12QuadrantSegmentation::GetPadI(Float_t x, Float_t y, Float_t /*z*/, 
248                                       Int_t& ix, Int_t& iy)
249 {                                       
250 ///  Returns pad coordinates (ix,iy) for given real coordinates (x,y)
251
252   GetPadI(x, y, ix, iy);
253 }
254                        
255 //______________________________________________________________________________
256 void  AliMUONSt12QuadrantSegmentation::GetPadI(Float_t x, Float_t y,
257                                       Int_t& ix, Int_t& iy)
258 {                                       
259 /// Returns pad coordinates (ix,iy) for given real coordinates (x,y)
260 /// If there is no pad, ix = 0, iy = 0 are returned.
261
262   AliMpPad pad = fSectorSegmentation->PadByPosition(TVector2(x,y), true);
263
264   ix = pad.GetIndices().GetFirst();
265   iy = pad.GetIndices().GetSecond();
266 }
267                        
268 //______________________________________________________________________________
269 void  AliMUONSt12QuadrantSegmentation::GetPadC(Int_t ix, Int_t iy, 
270                                       Float_t& x, Float_t& y, Float_t& z)
271 {                                       
272 /// Transform from pad to real coordinates
273
274   z = fZ;
275   GetPadC(ix, iy, x , y);
276 }
277
278 //______________________________________________________________________________
279 void  AliMUONSt12QuadrantSegmentation::GetPadC(Int_t ix, Int_t iy, 
280                                       Float_t& x, Float_t& y)
281 {                                       
282 /// Transform from pad to real coordinates
283 /// If there is no pad, x = 0., y = 0. are returned.
284
285   AliMpPad pad = fSectorSegmentation->PadByIndices(AliMpIntPair(ix,iy), true);
286
287   x = pad.Position().X();
288   y = pad.Position().Y();
289 }
290
291
292 //______________________________________________________________________________
293 void AliMUONSt12QuadrantSegmentation::Init(Int_t chamber)
294 {
295 /// Initialize segmentation
296
297  // find Npx, Npy and save this info
298   
299   // reference to chamber
300  fRmin=AliMUONConstants::Rmin(0);
301  fRmax=AliMUONConstants::Rmax(0);  
302  fZ = 0;
303  fId=chamber;
304 }
305  
306 //______________________________________________________________________________
307 Float_t AliMUONSt12QuadrantSegmentation::Dpx() const
308 {
309 /// Get pad size in x
310
311   AliFatal( "Not uniform pad size.");
312   return 0.;
313 }
314
315 //______________________________________________________________________________
316 Float_t AliMUONSt12QuadrantSegmentation::Dpy() const
317 {
318 /// Get pad size in y
319
320   AliFatal("Not uniform pad size.");
321   return 0.;
322 }
323  
324 //______________________________________________________________________________
325 Float_t AliMUONSt12QuadrantSegmentation::Dpx(Int_t isector) const
326 {
327 /// Pad size in x by sector
328
329   return fSectorSegmentation->PadDimensions(isector).X()*2.0;
330
331
332 //______________________________________________________________________________
333 Float_t AliMUONSt12QuadrantSegmentation::Dpy(Int_t isector) const
334 {
335 /// Pad size in x, y by Sector 
336
337   return fSectorSegmentation->PadDimensions(isector).Y()*2.0;
338 }
339
340 //______________________________________________________________________________
341 Int_t AliMUONSt12QuadrantSegmentation::Npx() const
342 {
343 /// Maximum number of Pads in x
344 /// hard coded for the time being
345
346   return fSectorSegmentation->MaxPadIndexX();
347 }
348
349 //______________________________________________________________________________
350 Int_t AliMUONSt12QuadrantSegmentation::Npy() const
351 {
352 /// Maximum number of Pads in y
353 /// hard coded for the time being
354
355   return fSectorSegmentation->MaxPadIndexY();
356 }
357
358 //______________________________________________________________________________
359 void  AliMUONSt12QuadrantSegmentation::SetPad(Int_t ix, Int_t iy)
360 {
361 /// Set pad position.
362 /// Sets virtual pad coordinates, needed for evaluating pad response 
363 /// outside the tracking program.
364 /// From AliMUONSegmentationV01.
365
366   GetPadC(ix, iy, fX, fY);
367   fZone = Sector(ix, iy);
368 }
369
370 //______________________________________________________________________________
371 void  AliMUONSt12QuadrantSegmentation::SetHit(Float_t xhit, Float_t yhit, Float_t /*zhit*/)
372 {
373 /// Set hit position
374 /// Sets virtual hit position, needed for evaluating pad response 
375 /// outside the tracking program 
376 /// From AliMUONSegmentationV01.
377
378   fXhit = xhit;
379   fYhit = yhit;
380 }
381     
382 //______________________________________________________________________________
383 void  AliMUONSt12QuadrantSegmentation::FirstPad(Float_t xhit, Float_t yhit, Float_t /*zhit*/, 
384                                        Float_t dx, Float_t dy) 
385 {                                        
386 /// Iterate over pads - initialiser
387
388   // Sets the current pad to that located in the hit position
389  
390   SetHit(GetAnod(xhit), yhit, 0.); 
391   
392   // Enable iterating in one dimension
393   if (dx == 0.)  dx = 0.01;
394   if (dy == 0.)  dy = 0.01;
395   
396   // Delete previous iterator
397   delete  fSectorIterator;
398   
399   fSectorIterator 
400     = fSectorSegmentation
401         ->CreateIterator(AliMpArea(TVector2(fXhit,fYhit),TVector2(dx,dy)));
402
403   AliDebug(1,Form("CreateIterator area=%e,%e +- %e,%e %s",
404                   fXhit,fYhit,dx,dy,PlaneTypeName(fPlaneType).Data()));
405   
406   fSectorIterator->First();             
407
408   if (! fSectorIterator->IsDone())
409     UpdateCurrentPadValues(fSectorIterator->CurrentItem());
410 }
411  
412 //______________________________________________________________________________
413 void  AliMUONSt12QuadrantSegmentation::NextPad()
414 {
415 /// Iterate over pads - stepper
416
417   fSectorIterator->Next();                              
418
419   if (! fSectorIterator->IsDone())
420     UpdateCurrentPadValues(fSectorIterator->CurrentItem());
421 }
422
423 //______________________________________________________________________________
424 Int_t AliMUONSt12QuadrantSegmentation::MorePads()
425 {
426 /// Iterate over pads - condition
427
428   if (fSectorIterator->IsDone())
429     return 0;
430   else
431     return 1;  
432 }
433
434 //______________________________________________________________________________
435 Float_t AliMUONSt12QuadrantSegmentation::Distance2AndOffset(Int_t iX, Int_t iY, 
436                                                    Float_t x, Float_t y, Int_t* /*dummy*/)
437 {                                          
438 /// Returns the square of the distance between 1 pad
439 /// labelled by its channel numbers and a coordinate
440
441   AliMpPad pad = fSectorSegmentation->PadByIndices(AliMpIntPair(iX, iY));
442   
443   if (!pad.IsValid())
444     AliFatal("Cannot locate pad.");
445
446   return (pad.Position() - TVector2(x, y)).Mod2();
447 }
448
449 //______________________________________________________________________________
450 void AliMUONSt12QuadrantSegmentation::GetNParallelAndOffset(Int_t /*iX*/, Int_t /*iY*/,
451                                                    Int_t* /*Nparallel*/, Int_t* /*Offset*/)
452 {                                          
453 /// Number of pads read in parallel and offset to add to x 
454 /// (specific to LYON, but mandatory for display)
455
456   AliFatal( "Not yet implemented.");
457 }
458
459
460 //______________________________________________________________________________
461 void AliMUONSt12QuadrantSegmentation::Neighbours(Int_t iX, Int_t iY, 
462                                         Int_t* Nlist, 
463                                         Int_t Xlist[10], Int_t Ylist[10])
464 {                                         
465 /// Get next neighbours 
466
467   AliMpPad pad = fSectorSegmentation->PadByIndices(AliMpIntPair(iX,iY));
468   Int_t &i = *Nlist;
469   i=0;
470   AliMpNeighboursPadIterator iter(fSectorSegmentation, pad, kFALSE);
471
472   for( iter.First(); !iter.IsDone() && i<10; iter.Next()) {
473     Xlist[i] = iter.CurrentItem().GetIndices().GetFirst();
474     Ylist[i] = iter.CurrentItem().GetIndices().GetSecond();
475     i++;
476   }
477 }
478  
479 //______________________________________________________________________________
480 Int_t  AliMUONSt12QuadrantSegmentation::Ix()
481 {
482 /// Current pad cursor during disintegration
483 /// x, y-coordinate
484
485   return fSectorIterator->CurrentItem().GetIndices().GetFirst();
486 }
487
488 //______________________________________________________________________________
489 Int_t  AliMUONSt12QuadrantSegmentation::Iy()
490 {
491 /// Current pad cursor during disintegration
492 /// x, y-coordinate
493
494   return fSectorIterator->CurrentItem().GetIndices().GetSecond();
495 }
496
497 //______________________________________________________________________________
498 Int_t  AliMUONSt12QuadrantSegmentation::ISector()
499 {
500 /// Current sector
501
502   return fZone;
503 }
504
505 //______________________________________________________________________________
506 Int_t AliMUONSt12QuadrantSegmentation::Sector(Int_t ix, Int_t iy)
507 {
508 /// Calculate sector from pad coordinates
509
510   return fSectorSegmentation
511            ->Zone(fSectorSegmentation->PadByIndices(AliMpIntPair(ix, iy)));
512 }
513
514 //______________________________________________________________________________
515 Int_t AliMUONSt12QuadrantSegmentation::Sector(Float_t x, Float_t y)
516 {
517 /// Calculate sector from pad coordinates
518
519   return fSectorSegmentation
520            ->Zone(fSectorSegmentation
521                     ->PadByPosition(TVector2(x,y)));
522 }
523
524 //______________________________________________________________________________
525 void  AliMUONSt12QuadrantSegmentation::IntegrationLimits(Float_t& x1, Float_t& x2,
526                                                 Float_t& y1, Float_t& y2)
527 {                                                 
528 /// Current integration limits 
529  
530   x1 = fXhit - fX - Dpx(fZone)/2.;
531   x2 = x1 + Dpx(fZone);
532
533   y1 = fYhit - fY - Dpy(fZone)/2.;
534   y2 = y1 + Dpy(fZone);    
535 }
536
537 //______________________________________________________________________________
538 Int_t AliMUONSt12QuadrantSegmentation::SigGenCond(Float_t x, Float_t y, Float_t /*z*/)
539 {
540 /// Signal Generation Condition during Stepping
541 /// -  0: don't generate signal
542 /// -  1: generate signal 
543 ///
544 ///  Comments:                                                                  \n 
545 ///
546 ///  Crossing of pad boundary and mid plane between neighbouring wires is checked.
547 ///  To correctly simulate the dependence of the spatial resolution on the angle 
548 ///  of incidence signal must be generated for constant steps on 
549 ///  the projection of the trajectory along the anode wire.
550 ///
551 ///  Signal will be generated if particle crosses pad boundary or
552 ///  boundary between two wires. 
553 ///
554 /// From AliMUONSegmentationV01
555
556   Int_t ixt, iyt;
557   GetPadI(x, y, ixt, iyt);
558   Int_t iwt=(x>0) ? Int_t(x/fWireD)+1 : Int_t(x/fWireD)-1;
559   
560   if ((ixt != fIxt) || (iyt !=fIyt) || (iwt != fIwt)) {
561     return 1;
562   } 
563   else {
564     return 0;
565   }
566 }
567
568 //______________________________________________________________________________
569 void  AliMUONSt12QuadrantSegmentation::SigGenInit(Float_t x, Float_t y, Float_t /*z*/)
570 {
571 /// Initialise signal generation at coord (x,y,z)
572 /// Initialises pad and wire position during stepping.
573 /// From AliMUONSegmentationV01
574
575   fXt = x;
576   fYt = y;
577   GetPadI(x, y, fIxt, fIyt);
578   fIwt = (x>0) ? Int_t(x/fWireD)+1 : Int_t(x/fWireD)-1 ;
579 }                   
580     
581 //______________________________________________________________________________
582 void AliMUONSt12QuadrantSegmentation::GiveTestPoints(Int_t& n, Float_t* x, Float_t* y) const
583 {                                             
584 /// Test points for auto calibration
585 /// Returns test point on the pad plane.
586 /// Used during determination of the segmoid correction of the COG-method
587 /// From AliMUONSegmentationV01
588
589   n=1;
590   x[0] = (fRmax+fRmin)/2/TMath::Sqrt(2.);
591   y[0] = x[0];
592 }
593
594 //______________________________________________________________________________
595 void AliMUONSt12QuadrantSegmentation::Draw(const char * /*opt*/)
596 {
597 /// Draw the segmentation zones.
598 /// (Called from AliMUON::BuildGeometry)
599
600   AliWarning("Not yet implemented.");
601 }
602
603 //______________________________________________________________________________
604 void AliMUONSt12QuadrantSegmentation::SetCorrFunc(Int_t isec, TF1* func)
605 {
606 /// Set the correction function.
607 /// From AliMUONSegmentationV01
608
609   fCorrA->AddAt(func, isec);
610 }
611
612 //______________________________________________________________________________
613 TF1* AliMUONSt12QuadrantSegmentation::CorrFunc(Int_t isec) const
614 {
615 /// Get the correction Function.
616 /// From AliMUONSegmentationV01
617
618   return (TF1*) fCorrA->At(isec);
619