Commenting out the infamous speed eater = StdoutToAliDebug until a better solution...
[u/mrichter/AliRoot.git] / MUON / mapping / AliMpRow.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 // $MpId: AliMpRow.cxx,v 1.9 2006/05/24 13:58:46 ivana Exp $
18 // Category: sector
19 //
20 // Class AliMpRow
21 // --------------
22 // Class describing a row composed of the row segments.
23 // Included in AliRoot: 2003/05/02
24 // Authors: David Guez, Ivana Hrivnacova; IPN Orsay
25
26 #include "AliMpRow.h"
27 #include "AliMpVRowSegment.h"
28 #include "AliMpVRowSegmentSpecial.h"
29 #include "AliMpRowSegmentRSpecial.h"
30 #include "AliMpVMotif.h"
31 #include "AliMpMotifType.h"
32 #include "AliMpMotifPosition.h"
33 #include "AliMpMotifMap.h"
34 #include "AliMpConstants.h"
35
36 #include "AliLog.h"
37
38 #include <TMath.h>
39 #include <Riostream.h>
40
41 /// \cond CLASSIMP
42 ClassImp(AliMpRow)
43 /// \endcond
44
45 //_____________________________________________________________________________
46 AliMpRow::AliMpRow(Int_t id, AliMpMotifMap* motifMap) 
47   : AliMpVIndexed(),
48     fID(id),
49     fOffsetY(0.),
50     fSegments(),
51     fMotifMap(motifMap)
52 {
53 /// Standard constructor
54 }
55
56 //_____________________________________________________________________________
57 AliMpRow::AliMpRow() 
58   : AliMpVIndexed(),
59     fID(0),
60     fOffsetY(0.),
61     fSegments(),
62     fMotifMap(0)
63 {
64 /// Default constructor
65 }
66
67 //_____________________________________________________________________________
68 AliMpRow::~AliMpRow() 
69 {
70 /// Destructor 
71
72 #ifdef WITH_STL
73   for (Int_t i=0; i<GetNofRowSegments(); i++)
74     delete fSegments[i]; 
75 #endif
76
77 #ifdef WITH_ROOT
78   fSegments.Delete();
79 #endif
80 }
81
82 //
83 // private methods
84 //
85
86 //_____________________________________________________________________________
87 AliMpVRowSegment*  AliMpRow::FindRowSegment(Int_t ix) const
88 {    
89 /// Find first normal row segment with low indices limit >= ix.
90
91   for (Int_t i=0; i<GetNofRowSegments(); i++) {
92     AliMpVRowSegment* segment = GetRowSegment(i);
93
94     if (!dynamic_cast<AliMpVRowSegmentSpecial*>(segment) &&
95          segment->GetHighIndicesLimit().GetFirst() >= ix)
96          
97      return segment;     
98   }   
99
100   return 0;      
101 }
102
103 //_____________________________________________________________________________
104 AliMpMotifPosition*  
105 AliMpRow::FindMotifPosition(AliMpVRowSegment* segment, Int_t ix) const
106 {
107 /// Find first motif position in the specified row segment 
108 /// with high indices limit >= ix.
109
110   if (!segment) return 0;
111
112   for (Int_t i=0; i<segment->GetNofMotifs(); i++){
113      AliMpMotifPosition* motifPosition 
114        = GetMotifMap()->FindMotifPosition(segment->GetMotifPositionId(i));
115        
116      if(!motifPosition) {
117        Fatal("FindMotifPosition", "Not found.");
118        return 0;
119      }  
120      
121      if (motifPosition->GetHighIndicesLimit().GetFirst()>=ix) 
122        return motifPosition;
123   }
124   
125   return 0;     
126 }
127
128
129 //_____________________________________________________________________________
130 void AliMpRow::SetHighIndicesLimits(Int_t iy)
131 {
132 /// Set the global indices high limit to its row segments,
133 /// motif positions with a given value.
134 /// Keep ix unmodified.
135
136   for (Int_t j=0; j<GetNofRowSegments(); j++) {
137      AliMpVRowSegment* rowSegment = GetRowSegment(j);       
138      rowSegment
139        ->SetHighIndicesLimit(
140             AliMpIntPair(rowSegment->GetHighIndicesLimit().GetFirst(),iy));
141
142     for (Int_t k=0; k<rowSegment->GetNofMotifs(); k++) {
143
144       Int_t motifPositionId = rowSegment->GetMotifPositionId(k);
145       AliMpMotifPosition* motifPosition 
146         = GetMotifMap()->FindMotifPosition(motifPositionId);
147
148       motifPosition
149         ->SetHighIndicesLimit(
150              AliMpIntPair(motifPosition->GetHighIndicesLimit().GetFirst(), iy));
151      
152     }
153   }  
154 }
155
156 //_____________________________________________________________________________
157 void  AliMpRow::CheckEmpty() const
158 {
159 /// Give a fatal if the row is empty.
160
161   if (GetNofRowSegments() == 0) 
162     Fatal("CheckEmpty", "Empty row");
163 }
164
165 //
166 // public methods
167 //
168
169 //_____________________________________________________________________________
170 void AliMpRow::AddRowSegment(AliMpVRowSegment* rowSegment)
171 {
172 /// Add row segment at the end.
173
174 #ifdef WITH_STL
175   fSegments.push_back(rowSegment);
176 #endif
177
178 #ifdef WITH_ROOT
179   fSegments.Add(rowSegment);
180 #endif
181 }  
182   
183 //_____________________________________________________________________________
184 void AliMpRow::AddRowSegmentInFront(AliMpVRowSegment* rowSegment)
185 {
186 /// Insert row segment in the first vector position.
187
188 #ifdef WITH_STL
189   fSegments.insert(fSegments.begin(), rowSegment);
190 #endif
191
192 #ifdef WITH_ROOT
193   fSegments.AddFirst(rowSegment);
194 #endif
195 }  
196   
197 //_____________________________________________________________________________
198 AliMpVRowSegment* AliMpRow::FindRowSegment(Double_t x) const
199 {
200 /// Find the row segment for the specified x position;
201 /// return 0 if no row segment is found.
202
203   for (Int_t i=0; i<GetNofRowSegments(); i++) {
204
205 #ifdef WITH_STL
206     AliMpVRowSegment* rs = fSegments[i];
207 #endif
208 #ifdef WITH_ROOT
209     AliMpVRowSegment* rs = (AliMpVRowSegment*)fSegments.At(i);
210 #endif
211
212     if (x >= rs->LeftBorderX() && x <= rs->RightBorderX())
213       return rs;
214   }
215   
216   return 0;    
217 }    
218
219 //_____________________________________________________________________________
220 Double_t AliMpRow::LowBorderY() const
221 {
222 /// Return the lowest row offset (the Y coordinate of the position of the
223 /// low border of motif).
224
225   CheckEmpty();
226
227   return fOffsetY - GetRowSegment(0)->HalfSizeY();
228 }  
229
230 //_____________________________________________________________________________
231 Double_t AliMpRow::UpperBorderY() const
232 {
233 /// Return the uppermost row offset (the Y coordinate of the position of the
234 /// upper border of motif).
235 \
236   CheckEmpty();
237
238   return fOffsetY + GetRowSegment(0)->HalfSizeY();
239 }  
240
241 //_____________________________________________________________________________
242 AliMpVPadIterator* AliMpRow::CreateIterator() const
243 {
244 /// Iterator is not implemented.
245
246   Fatal("CreateIterator", "Iterator is not implemented.");
247   
248   return 0;
249 }  
250
251 //_____________________________________________________________________________
252 void AliMpRow::SetMotifPositions()
253 {
254 /// Create motif positions objects and fills them in the motif map.
255
256   CheckEmpty();
257
258   for (Int_t j=0; j<GetNofRowSegments(); j++) {
259      AliMpVRowSegment* rowSegment = GetRowSegment(j);
260
261      for (Int_t k=0; k<rowSegment->GetNofMotifs(); k++) {
262         // Get values 
263         Int_t motifPositionId = rowSegment->GetMotifPositionId(k);
264         AliMpVMotif* motif = rowSegment->GetMotif(k);
265         TVector2 position = rowSegment->MotifCenter(motifPositionId);
266        
267         AliMpMotifPosition* motifPosition 
268           = new AliMpMotifPosition(motifPositionId, motif, position);
269         // set the initial value to of HighIndicesLimit() Invalid()
270         // (this is used for calculation of indices in case of
271         // special row segments)
272         motifPosition->SetHighIndicesLimit(AliMpIntPair::Invalid());
273
274         //Bool_t warn = (rowSegment->GetNofMotifs()==1); 
275         Bool_t warn = true;
276         if (dynamic_cast<AliMpVRowSegmentSpecial*>(rowSegment)) warn = false; 
277                // supress warnings for special row segments
278                // which motifs can overlap the row borders
279                
280         Bool_t added = GetMotifMap()->AddMotifPosition(motifPosition, warn);
281         
282         if (!added) delete motifPosition;       
283      }  
284   }
285 }    
286
287 //_____________________________________________________________________________
288 void AliMpRow::SetGlobalIndices(AliMp::Direction constPadSizeDirection, 
289                                 AliMpRow* rowBefore)
290 {
291 /// Set the global indices limits to its row segments, motif positions
292 /// and itself.
293
294   Int_t ix = AliMpConstants::StartPadIndex();
295   Int_t iy = AliMpConstants::StartPadIndex();
296
297   for (Int_t j=0; j<GetNofRowSegments(); j++) {
298      AliMpVRowSegment* rowSegment = GetRowSegment(j);
299      
300      ix += rowSegment->GetLowIndicesLimit().GetFirst();
301
302      for (Int_t k=0; k<rowSegment->GetNofMotifs(); k++) {
303      
304        // Find the y index value of the low edge
305        if (rowBefore) {
306          if (constPadSizeDirection == AliMp::kY) {
307            iy = rowBefore->GetHighIndicesLimit().GetSecond()+1;
308          } 
309          else {
310            AliMpVRowSegment* seg = rowBefore->FindRowSegment(ix);       
311            AliMpMotifPosition* motPos =  FindMotifPosition(seg, ix);
312            if (!dynamic_cast<AliMpRowSegmentRSpecial*>(rowSegment)) {
313              if (!motPos) 
314                Fatal("SetGlobalIndices", "Motif position in rowBefore not found.");
315            
316              iy = motPos->GetHighIndicesLimit().GetSecond()+1;
317            }  
318          }
319        } 
320
321        // Set (ix, iy) to k-th motif position and update ix
322        ix = rowSegment->SetIndicesToMotifPosition(k, AliMpIntPair(ix, iy));
323     }
324     rowSegment->SetGlobalIndices(rowBefore);    
325   }
326
327   // The low/high indices limits has to be taken as the highest/lowest from all 
328   // row segments
329   Int_t ixl = 9999;
330   Int_t iyl = 9999;
331   Int_t ixh = AliMpConstants::StartPadIndex();
332   Int_t iyh = AliMpConstants::StartPadIndex();
333
334   for (Int_t i=0; i<GetNofRowSegments(); i++) {
335     
336     AliMpVRowSegment* rowSegment = GetRowSegment(i);
337     
338     if ( rowSegment->GetLowIndicesLimit().GetFirst() < ixl ) 
339        ixl = rowSegment->GetLowIndicesLimit().GetFirst();
340        
341     if ( rowSegment->GetLowIndicesLimit().GetSecond() < iyl ) 
342        iyl = rowSegment->GetLowIndicesLimit().GetSecond();
343
344     if ( rowSegment->GetHighIndicesLimit().GetFirst() > ixh ) 
345        ixh = rowSegment->GetHighIndicesLimit().GetFirst();
346        
347     if ( rowSegment->GetHighIndicesLimit().GetSecond() > iyh ) 
348        iyh = rowSegment->GetHighIndicesLimit().GetSecond();
349   }     
350
351   SetLowIndicesLimit(AliMpIntPair(ixl, iyl));
352   SetHighIndicesLimit(AliMpIntPair(ixh, iyh));
353 }
354
355 //_____________________________________________________________________________
356 TVector2  AliMpRow::Position() const
357 {
358 /// Return the position of the row centre.
359
360   Double_t x = (GetRowSegment(0)->LeftBorderX() +
361                 GetRowSegment(GetNofRowSegments()-1)->RightBorderX())/2.;
362                     
363   Double_t y = fOffsetY;  
364     
365   return TVector2(x, y);   
366 }
367
368 //_____________________________________________________________________________
369 TVector2  AliMpRow::Dimensions() const
370 {
371 /// Return the maximum halflengths of the row in x, y.
372
373   Double_t x = (GetRowSegment(GetNofRowSegments()-1)->RightBorderX() -
374                 GetRowSegment(0)->LeftBorderX())/2.;
375                   
376   Double_t y = GetRowSegment(0)->HalfSizeY();  
377     
378   return TVector2(x, y);   
379 }
380
381 //_____________________________________________________________________________
382 void AliMpRow::SetRowSegmentOffsets(const TVector2& offset)
383 {
384 /// Set the row segments offsets in X .
385
386   CheckEmpty();
387   
388   AliMpVRowSegment* previous = 0;
389
390   for (Int_t j=0; j<GetNofRowSegments(); j++) {
391      AliMpVRowSegment* rowSegment = GetRowSegment(j);
392
393      Double_t offsetX;
394      if (previous) 
395       offsetX = previous->RightBorderX();
396     else
397       offsetX = offset.X();  
398   
399     rowSegment->SetOffset(TVector2(offsetX, 0.));
400     previous = rowSegment;  
401   }
402 }
403
404
405 //_____________________________________________________________________________
406 Double_t AliMpRow::SetOffsetY(Double_t offsetY)
407 {
408 /// Set the row offset (the Y coordinate of the position of the
409 /// center of motif) and returns the offset of the top border.
410
411   CheckEmpty();
412
413   AliMpVRowSegment* first = GetRowSegment(0);
414   Double_t rowSizeY = first->HalfSizeY();
415   
416   // Check if all next row segments have motif of
417   // the same size in y
418   for (Int_t i=1; i<GetNofRowSegments(); i++) {
419      Double_t sizeY = GetRowSegment(i)->HalfSizeY();
420      
421      if (TMath::Abs(sizeY - rowSizeY) >= AliMpConstants::LengthTolerance()) {
422        Fatal("SetOffsetY", "Motif with different Y size in one row");
423        return 0.;
424      }  
425   }
426
427   offsetY += rowSizeY ;
428     
429   fOffsetY = offsetY;
430     
431   return offsetY += rowSizeY;
432 }  
433
434 //_____________________________________________________________________________
435 Int_t AliMpRow::GetNofRowSegments() const 
436 {
437 /// Return number of row segments.
438
439 #ifdef WITH_STL
440   return fSegments.size();
441 #endif
442
443 #ifdef WITH_ROOT
444   return fSegments.GetSize();
445 #endif
446 }  
447
448 //_____________________________________________________________________________
449 AliMpVRowSegment* AliMpRow::GetRowSegment(Int_t i) const 
450 {
451 /// Return i-th row segment.
452
453   if (i<0 || i>=GetNofRowSegments()) {
454     AliWarningStream() << "Index outside range" << endl;
455     return 0;
456   }
457   
458 #ifdef WITH_STL
459   return fSegments[i];  
460 #endif
461
462 #ifdef WITH_ROOT
463   return (AliMpVRowSegment*)fSegments.At(i);  
464 #endif
465 }
466