]> git.uio.no Git - u/mrichter/AliRoot.git/blob - ITS/AliITSsimulationSPD.cxx
Adding MUON HLT code to the repository.
[u/mrichter/AliRoot.git] / ITS / AliITSsimulationSPD.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 #include <Riostream.h>
19 #include <TRandom.h>
20 #include <TH1.h>
21 #include <TMath.h>
22 #include <TString.h>
23 #include <TParticle.h>
24
25 #include "AliRun.h"
26 #include "AliITS.h"
27 #include "AliITShit.h"
28 #include "AliITSdigitSPD.h"
29 #include "AliITSmodule.h"
30 #include "AliITSMapA2.h"
31 #include "AliITSpList.h"
32 #include "AliITSsimulationSPD.h"
33 #include "AliITSsegmentation.h"
34 #include "AliITSresponse.h"
35 #include "AliITSsegmentationSPD.h"
36 #include "AliITSresponseSPD.h"
37
38 //#define DEBUG
39
40 ClassImp(AliITSsimulationSPD)
41 ////////////////////////////////////////////////////////////////////////
42 // Version: 0
43 // Written by Rocco Caliandro
44 // from a model developed with T. Virgili and R.A. Fini
45 // June 15 2000
46 //
47 // AliITSsimulationSPD is the simulation of SPDs
48 //
49 //______________________________________________________________________
50 AliITSsimulationSPD::AliITSsimulationSPD() : AliITSsimulation(),
51 fMapA2(0),
52 fHis(0){
53     // Default constructor
54     // Inputs: 
55     //    none.
56     // Outputs:
57     //    none.
58     // Return:
59     //    A default constructed AliITSsimulationSPD class.
60 }
61 //______________________________________________________________________
62 AliITSsimulationSPD::AliITSsimulationSPD(AliITSsegmentation *seg,
63                                          AliITSresponse *res):
64 AliITSsimulation(seg,res),
65 fMapA2(0),
66 fHis(0){
67     // Standard constructor
68     // Inputs: 
69     //    AliITSsegmentation *seg  Segmentation class to be used
70     //    AliITSresonse      *res  Response class to be used
71     // Outputs:
72     //    none.
73     // Return:
74     //    A standard constructed AliITSsimulationSPD class.
75
76     Init();
77 }
78 //______________________________________________________________________
79 void AliITSsimulationSPD::Init() {
80     // Initilizes the variables of AliITSsimulation SPD.
81     // Inputs:
82     //    none.
83     // Outputs:
84     //    none.
85     // Return:
86     //    none.
87
88     fHis = 0;
89     if(fMapA2) delete fMapA2;
90     fMapA2  = new AliITSMapA2(fSegmentation);
91     if(fpList) delete fpList;
92     fpList  = new AliITSpList(GetNPixelsZ()+1,GetNPixelsX()+1);
93 }
94 //______________________________________________________________________
95 void AliITSsimulationSPD::Init(AliITSsegmentationSPD *seg,
96                                AliITSresponseSPD *resp) {
97     // Initilizes the variables of AliITSsimulation SPD.
98     // Inputs:
99     //    AliITSsegmentationSPD   replacement segmentation class to be used
100     //    aliITSresponseSPD       replacement response class to be used
101     // Outputs:
102     //    none.
103     // Return:
104     //    none.
105
106     if(fHis){
107         fHis->Delete(); 
108         delete fHis;  
109     } // end if fHis
110     fHis = 0;
111     if(fResponse) delete fResponse;
112     fResponse     = resp;
113     if(fSegmentation) delete fSegmentation;
114     fSegmentation = seg;
115     if(fMapA2) delete fMapA2;
116     fMapA2  = new AliITSMapA2(fSegmentation);
117     if(fpList) delete fpList;
118     fpList  = new AliITSpList(GetNPixelsZ()+1,GetNPixelsX()+1);
119 }
120 //______________________________________________________________________
121 AliITSsimulationSPD::~AliITSsimulationSPD() { 
122     // destructor
123     // Inputs: 
124     //    none.
125     // Outputs:
126     //    none.
127     // Return:
128     //    none.
129
130     if(fMapA2) delete fMapA2;
131
132     if (fHis) {
133         fHis->Delete(); 
134         delete fHis;     
135     } // end if
136 }
137 //______________________________________________________________________
138 AliITSsimulationSPD::AliITSsimulationSPD(const AliITSsimulationSPD &source) :
139     AliITSsimulation(source){
140     // Copy Constructor
141     // Inputs: 
142     //    none.
143     // Outputs:
144     //    none.
145     // Return:
146     //    A new AliITSsimulationSPD class with the same parameters as source.
147
148     if(&source == this) return;
149
150     this->fMapA2    = source.fMapA2;
151     this->fHis      = source.fHis;
152     return;
153 }
154 //______________________________________________________________________
155 AliITSsimulationSPD& AliITSsimulationSPD::operator=(const AliITSsimulationSPD 
156                                                     &source) {
157     //    Assignment operator
158     // Inputs: 
159     //    none.
160     // Outputs:
161     //    none.
162     // Return:
163     //    A new AliITSsimulationSPD class with the same parameters as source.
164
165     if(&source == this) return *this;
166
167     this->fMapA2    = source.fMapA2;
168     this->fHis      = source.fHis;
169     return *this;
170
171 //______________________________________________________________________
172 AliITSsimulationSPD& AliITSsimulationSPD::operator=(const AliITSsimulation 
173                                                     &source) {
174     //    Assignment operator
175     // Inputs: 
176     //    none.
177     // Outputs:
178     //    none.
179     // Return:
180     //    A new AliITSsimulationSPD class with the same parameters as source.
181
182     if(&source == this) return *this;
183     Error("AliITSsimulationSPD","Not allowed to make a = with "
184           "AliITSsimulationSPD Using default creater instead");
185
186     return *this;
187
188
189 //______________________________________________________________________
190 void AliITSsimulationSPD::InitSimulationModule(Int_t module,Int_t event){
191     // Creates maps to build the list of tracks for each sumable digit
192     // Inputs:
193     //   Int_t module    // Module number to be simulated
194     //   Int_t event     // Event number to be simulated
195     // Outputs:
196     //   none.
197     // Return
198     //    none.
199  
200     fModule = module;
201     fEvent  = event;
202     fMapA2->ClearMap();
203     fpList->ClearMap();
204 }
205 //______________________________________________________________________
206 void AliITSsimulationSPD::FinishSDigitiseModule(){
207     // Does the Sdigits to Digits work
208     // Inputs:
209     //   none.
210     // Outputs:
211     //   none.
212     // Return:
213     //   none.
214
215     SDigitsToDigits(fModule,fpList);
216 }
217 //______________________________________________________________________
218 void AliITSsimulationSPD::SDigitiseModule(AliITSmodule *mod, Int_t dummy0,
219                                              Int_t dummy1) {
220     // Sum digitize module
221     // Inputs:
222     //   AliITSmodule  *mod    The module to be SDgitized
223     //   Int_t         dummy0  Not used kept for general compatibility
224     //   Int_t         dummy1  Not used kept for general compatibility
225     // Outputs:
226     //   none.
227     // Return:
228     //   none.
229     if (!(mod->GetNhits())) return; // if module has no hits then no Sdigits.
230     Int_t    number     = 10000;
231     Int_t    *frowpixel = new Int_t[number];
232     Int_t    *fcolpixel = new Int_t[number];
233     Double_t *fenepixel = new Double_t[number];
234
235     dummy0 = dummy1; // remove unsued variable warning.
236     fModule = mod->GetIndex();
237
238     // Array of pointers to store the track index of the digits
239     // leave +1, otherwise pList crashes when col=256, row=192
240
241     HitsToAnalogDigits(mod,frowpixel,fcolpixel,fenepixel,fpList);
242
243     WriteSDigits(fpList);
244
245     // clean memory
246     delete[] frowpixel;
247     delete[] fcolpixel;
248     delete[] fenepixel;
249     fMapA2->ClearMap();
250     fpList->ClearMap();
251 }
252 //______________________________________________________________________
253 void AliITSsimulationSPD::DigitiseModule(AliITSmodule *mod, Int_t,Int_t) {
254     // digitize module. Also need to digitize modules with only noise.
255     // Inputs:
256     //   AliITSmodule  *mod    The module to be SDgitized
257     // Outputs:
258     //   none.
259     // Return:
260     //   none.
261
262     Int_t    number     = 10000;
263     Int_t    *frowpixel = new Int_t[number];
264     Int_t    *fcolpixel = new Int_t[number];
265     Double_t *fenepixel = new Double_t[number];
266
267     // Array of pointers to store the track index of the digits
268     // leave +1, otherwise pList crashes when col=256, row=192
269     fModule = mod->GetIndex();
270     // noise setting
271     SetFluctuations(fpList,fModule);
272
273     HitsToAnalogDigits(mod,frowpixel,fcolpixel,fenepixel,fpList);
274
275     // apply mask to SPD module
276     SetMask();
277
278     CreateDigit(fModule,fpList);
279
280     // clean memory
281     delete[] frowpixel;
282     delete[] fcolpixel;
283     delete[] fenepixel;
284     fMapA2->ClearMap();
285     fpList->ClearMap();
286 }
287 //______________________________________________________________________
288 void AliITSsimulationSPD::SDigitsToDigits(Int_t module,AliITSpList *pList) {
289     // sum digits to Digits.
290     // Inputs:
291     //   AliITSmodule  *mod    The module to be SDgitized
292     //   AliITSpList   *pList  the array of SDigits
293     // Outputs:
294     //   AliITSpList   *pList  the array of SDigits
295     // Return:
296     //   none.
297
298     if(GetDebug()){
299         cout << "Entering AliITSsimulatinSPD::SDigitsToDigits for module=";
300         cout << module << endl;
301     } // end if GetDebug
302     fModule = module;
303
304     // noise setting
305     SetFluctuations(pList,module);
306
307     fMapA2->ClearMap(); // since noise is in pList aready. Zero Map so that
308     // noise is not doubled when calling FillMapFrompList.
309
310     FillMapFrompList(pList);
311
312     // apply mask to SPD module
313     SetMask();
314
315     CreateDigit(module,pList);
316
317     fMapA2->ClearMap();
318     pList->ClearMap();
319 }
320 //______________________________________________________________________
321 void AliITSsimulationSPD::UpdateMapSignal(Int_t row,Int_t col,Int_t trk,
322                                           Int_t hit,Int_t mod,Double_t ene,
323                                           AliITSpList *pList) {
324     // updates the Map of signal, adding the energy  (ene) released by
325     // the current track
326     // Inputs:
327     //   Int_t         row  pixel row number
328     //   Int_t         col  pixel column number
329     //   Int_t         trk  track number which contributed
330     //   Int_t         hit  hit number which contributed
331     //   Int_t         mod  module number
332     //   Double_t      ene  the energy associated with this contribution
333     //   AliITSpList   *pList  the array of SDigits
334     // Outputs:
335     //   AliITSpList   *pList  the array of SDigits
336     // Return:
337     //   none.
338
339     fMapA2->AddSignal(row,col,ene);
340     pList->AddSignal(row,col,trk,hit,mod,ene);
341 }
342 //______________________________________________________________________
343 void AliITSsimulationSPD::UpdateMapNoise(Int_t row,Int_t col,Int_t mod,
344                                          Double_t ene,AliITSpList *pList) {
345     // updates the Map of noise, adding the energy  (ene) give my noise
346     // Inputs:
347     //   Int_t         row  pixel row number
348     //   Int_t         col  pixel column number
349     //   Int_t         mod  module number
350     //   Double_t      ene  the energy associated with this contribution
351     //   AliITSpList   *pList  the array of SDigits
352     // Outputs:
353     //   AliITSpList   *pList  the array of SDigits
354     // Return:
355     //   none.
356
357     fMapA2->AddSignal(row,col,ene);
358     pList->AddNoise(row,col,mod,ene);
359 }
360 //______________________________________________________________________
361 void AliITSsimulationSPD::HitsToAnalogDigits(AliITSmodule *mod,
362                                              Int_t *frowpixel,Int_t *fcolpixel,
363                                              Double_t *fenepixel,
364                                              AliITSpList *pList) {
365     // Loops over all hits to produce Analog/floting point digits. This
366     // is also the first task in producing standard digits.
367     // Inputs:
368     //   AliITSmodule  *mod        module class
369     //   Int_t         *frowpixel  array of pixel rows
370     //   Int_t         *fcolpixel  array of pixel columns
371     //   Double_t      *fenepiexel array of pixel energies
372     //   AliITSpList   *pList  the array of SDigits
373     // Outputs:
374     //   AliITSpList   *pList  the array of SDigits
375     // Return:
376     //   none.
377     
378     // loop over hits in the module
379     Int_t hitpos,nhits = mod->GetNhits();
380     for (hitpos=0;hitpos<nhits;hitpos++) {
381         HitToDigit(mod,hitpos,frowpixel,fcolpixel,fenepixel,pList);
382     }// end loop over digits
383 }
384 //______________________________________________________________________
385 void AliITSsimulationSPD::HitToDigit(AliITSmodule *mod,Int_t hitpos,
386                                      Int_t *frowpixel,Int_t *fcolpixel,
387                                      Double_t *fenepixel,AliITSpList *pList) {
388     //  Steering function to determine the digits associated to a given
389     // hit (hitpos)
390     // The digits are created by charge sharing (ChargeSharing) and by
391     // capacitive coupling (SetCoupling). At all the created digits is
392     // associated the track number of the hit (ntrack)
393     // Inputs:
394     //   AliITSmodule  *mod        module class
395     //   Int_t         hitpos      hit index value
396     //   Int_t         *frowpixel  array of pixel rows
397     //   Int_t         *fcolpixel  array of pixel columns
398     //   Double_t      *fenepiexel array of pixel energies
399     //   AliITSpList   *pList  the array of SDigits
400     // Outputs:
401     //   AliITSpList   *pList  the array of SDigits
402     // Return:
403     //   none.
404     Double_t x1l=0.0,y1l=0.0,z1l=0.0,x2l=0.0,y2l=0.0,z2l=0.0;
405     Int_t r1,r2,c1,c2,row,col,npixel = 0;
406     Int_t ntrack;
407     Double_t ene=0.0,etot=0.0;
408     const Float_t kconv = 10000.;     // cm -> microns
409     const Float_t kconv1= 0.277e9;    // GeV -> electrons equivalent
410
411     if(!(mod->LineSegmentL(hitpos,x1l,x2l,y1l,y2l,z1l,z2l,etot,ntrack)))return;
412
413     x2l += x1l; y2l += y1l; z2l += z1l; // Convert to ending coordinate.
414     // positions shifted and converted in microns
415     x1l   = x1l*kconv + fSegmentation->Dx()/2.;
416     z1l   = z1l*kconv + fSegmentation->Dz()/2.;
417     // positions  shifted and converted in microns
418     x2l   = x2l*kconv + fSegmentation->Dx()/2.;
419     z2l   = z2l*kconv + fSegmentation->Dz()/2.;
420     etot *= kconv1; // convert from GeV to electrons equivalent.
421     Int_t module = mod->GetIndex();
422
423     // to account for the effective sensitive area
424     // introduced in geometry 
425     if (z1l<0 || z1l>fSegmentation->Dz()) return;
426     if (z2l<0 || z2l>fSegmentation->Dz()) return;
427     if (x1l<0 || x1l>fSegmentation->Dx()) return;
428     if (x2l<0 || x2l>fSegmentation->Dx()) return;
429
430     //Get the col and row number starting from 1
431     // the x direction is not inverted for the second layer!!!
432     fSegmentation->GetPadIxz(x1l, z1l, c1, r1); 
433     fSegmentation->GetPadIxz(x2l, z2l, c2, r2);
434
435     // to account for unexpected equal entrance and 
436     // exit coordinates
437     if (x1l==x2l) x2l=x2l+x2l*0.1;
438     if (z1l==z2l) z2l=z2l+z2l*0.1;
439
440     if ((r1==r2) && (c1==c2)){
441         // no charge sharing
442         npixel = 1;              
443         frowpixel[npixel-1] = r1;
444         fcolpixel[npixel-1] = c1;
445         fenepixel[npixel-1] = etot;
446     } else {
447         // charge sharing
448         ChargeSharing(x1l,z1l,x2l,z2l,c1,r1,c2,r2,etot,
449                       npixel,frowpixel,fcolpixel,fenepixel);
450     } // end if r1==r2 && c1==c2.
451
452     for (Int_t npix=0;npix<npixel;npix++){
453         row = frowpixel[npix];
454         col = fcolpixel[npix];
455         ene = fenepixel[npix];
456         UpdateMapSignal(row,col,ntrack,hitpos,module,ene,pList); 
457         // Starting capacitive coupling effect
458         SetCoupling(row,col,ntrack,hitpos,module,pList); 
459     } // end for npix
460 }
461 //______________________________________________________________________
462 void AliITSsimulationSPD::ChargeSharing(Float_t x1l,Float_t z1l,Float_t x2l,
463                                         Float_t z2l,Int_t c1,Int_t r1,Int_t c2,
464                                         Int_t r2,Float_t etot,
465                                         Int_t &npixel,Int_t *frowpixel,
466                                         Int_t *fcolpixel,Double_t *fenepixel){
467     //  Take into account the geometrical charge sharing when the track
468     //  crosses more than one pixel.
469     // Inputs:
470     //    Float_t  x1l
471     //    Float_t  z1l
472     //    Float_t  x2l
473     //    Float_t  z2l
474     //    Int_t    c1
475     //    Int_t    r1
476     //    Int_t    c2
477     //    Int_t    r2
478     //    Float_t  etot
479     //    Int_t    &npixel
480     //   Int_t     *frowpixel  array of pixel rows
481     //   Int_t     *fcolpixel  array of pixel columns
482     //   Double_t  *fenepiexel array of pixel energies
483     // Outputs:
484     //    Int_t    &npixel
485     // Return:
486     //   none.
487     //
488     //Begin_Html
489     /*
490       <img src="picts/ITS/barimodel_2.gif">
491       </pre>
492       <br clear=left>
493       <font size=+2 color=red>
494       <a href="mailto:Rocco.Caliandro@ba.infn.it"></a>.
495       </font>
496       <pre>
497     */
498     //End_Html
499     //Float_t dm;
500     Float_t xa,za,xb,zb,dx,dz,dtot,refr,refm,refc;
501     Float_t refn=0.;
502     Float_t arefm, arefr, arefn, arefc, azb, az2l, axb, ax2l;
503     Int_t   dirx,dirz,rb,cb;
504     Int_t flag,flagrow,flagcol;
505     Double_t epar;
506
507     npixel = 0;
508     xa     = x1l;
509     za     = z1l;
510 //    dx     = x1l-x2l;
511 //    dz     = z1l-z2l;
512     dx     = x2l-x1l;
513     dz     = z2l-z1l;
514     dtot   = TMath::Sqrt((dx*dx)+(dz*dz));   
515     if (dtot==0.0) dtot = 0.01;
516     dirx   = (Int_t) TMath::Sign((Float_t)1,dx);
517     dirz   = (Int_t) TMath::Sign((Float_t)1,dz);
518
519     // calculate the x coordinate of  the pixel in the next column    
520     // and the z coordinate of  the pixel in the next row
521     Float_t xpos, zpos;
522
523     fSegmentation->GetPadCxz(c1, r1-1, xpos, zpos); 
524
525     Float_t xsize = fSegmentation->Dpx(0);
526     Float_t zsize = fSegmentation->Dpz(r1-1);
527     
528     if (dirx == 1) refr = xpos+xsize/2.;
529     else refr = xpos-xsize/2.;
530
531     if (dirz == 1) refn = zpos+zsize/2.;
532     else refn = zpos-zsize/2.;
533
534     flag = 0;
535     flagrow = 0;
536     flagcol = 0;
537     do{
538         // calculate the x coordinate of the intersection with the pixel
539         // in the next cell in row  direction
540         if(dz!=0)
541             refm = dx*((refn - z1l)/dz) + x1l;
542         else
543             refm = refr+dirx*xsize;
544         
545         // calculate the z coordinate of the intersection with the pixel
546         // in the next cell in column direction
547         if (dx!=0)
548             refc = dz*((refr - x1l)/dx) + z1l;
549         else
550             refc = refn+dirz*zsize;
551         
552         arefm = refm * dirx;
553         arefr = refr * dirx;
554         arefn = refn * dirz;
555         arefc = refc * dirz;
556         
557         if ((arefm < arefr) && (arefn < arefc)){
558             // the track goes in the pixel in the next cell in row direction
559             xb = refm;
560             zb = refn;
561             cb = c1;
562             rb = r1 + dirz;
563             azb = zb * dirz;
564             az2l = z2l * dirz;
565             if (rb == r2) flagrow=1;
566             if (azb > az2l) {
567                 zb = z2l;
568                 xb = x2l;
569             } // end if
570             // shift to the pixel in the next cell in row direction
571             Float_t zsizeNext = fSegmentation->Dpz(rb-1);
572             //to account for cell at the borders of the detector
573             if(zsizeNext==0) zsizeNext = zsize;
574             refn += zsizeNext*dirz;
575         }else {
576             // the track goes in the pixel in the next cell in column direction
577             xb = refr;
578             zb = refc;
579             cb = c1 + dirx;
580             rb = r1;
581             axb = xb * dirx;
582             ax2l = x2l * dirx;
583             if (cb == c2) flagcol=1;
584             if (axb > ax2l) {
585                 zb = z2l;
586                 xb = x2l;
587             } // end ifaxb > ax2l
588             
589             // shift to the pixel in the next cell in column direction
590             Float_t xsizeNext = fSegmentation->Dpx(cb-1);
591             //to account for cell at the borders of the detector
592             if(xsizeNext==0) xsizeNext = xsize;
593             refr += xsizeNext*dirx;
594         } // end if (arefm < arefr) && (arefn < arefc)
595         
596         //calculate the energy lost in the crossed pixel      
597         epar = TMath::Sqrt((xb-xa)*(xb-xa)+(zb-za)*(zb-za)); 
598         epar = etot*(epar/dtot);
599         
600         //store row, column and energy lost in the crossed pixel
601         frowpixel[npixel] = r1;
602         fcolpixel[npixel] = c1;
603         fenepixel[npixel] = epar;
604         npixel++;
605         
606         // the exit point of the track is reached
607         if (epar == 0) flag = 1;
608         if ((r1 == r2) && (c1 == c2)) flag = 1;
609         if (flag!=1) {
610             r1 = rb;
611             c1 = cb;
612             xa = xb;
613             za = zb;
614         } // end if flag!=1
615     } while (flag==0);
616 }
617 //______________________________________________________________________
618 void AliITSsimulationSPD::SetCoupling(Int_t row, Int_t col, Int_t ntrack,
619                                       Int_t idhit,Int_t module,
620                                       AliITSpList *pList) {
621     //  Take into account the coupling between adiacent pixels.
622     //  The parameters probcol and probrow are the probability of the
623     //  signal in one pixel shared in the two adjacent pixels along
624     //  the column and row direction, respectively.
625     // Inputs:
626     //    Int_t      row    pixel row number
627     //    Int_t      col     pixel column number
628     //    Int_t      ntrack  track number of track contributing to this signal
629     //    Int_t      idhit   hit number of hit contributing to this signal
630     //    Int_t      module  module number
631     //   AliITSpList *pList  the array of SDigits
632     // Outputs:
633     //   AliITSpList *pList  the array of SDigits
634     // Return:
635     //   none.
636     //
637     //Begin_Html
638     /*
639       <img src="picts/ITS/barimodel_3.gif">
640       </pre>
641       <br clear=left>
642       <font size=+2 color=red>
643       <a href="mailto:tiziano.virgili@cern.ch"></a>.
644       </font>
645       <pre>
646     */
647     //End_Html
648     Int_t j1,j2,flag=0;
649     Double_t pulse1,pulse2;
650     Double_t couplR=0.0,couplC=0.0;
651     Double_t xr=0.;
652
653     GetCouplings(couplR,couplC);
654     j1 = row;
655     j2 = col;
656     pulse1 = fMapA2->GetSignal(row,col);
657     pulse2 = pulse1;
658     for (Int_t isign=-1;isign<=1;isign+=2){// loop in row direction
659         do{
660             j1 += isign;
661             //   pulse1 *= couplR; 
662             xr = gRandom->Rndm();
663             //if ((j1<0) || (j1>GetNPixelsZ()-1) || (pulse1<GetThreshold())){
664             if ((j1<0) || (j1>GetNPixelsZ()-1) || (xr>couplR)){
665                 j1 = row;
666                 flag = 1;
667             }else{
668                 UpdateMapSignal(j1,col,ntrack,idhit,module,pulse1,pList);
669                 //  flag = 0;
670                 flag = 1; // only first next!!
671             } // end if
672         } while(flag == 0);
673         // loop in column direction
674         do{
675             j2 += isign;
676             // pulse2 *= couplC; 
677             xr = gRandom->Rndm();
678             //if ((j2<0) || (j2>(GetNPixelsX()-1)) || (pulse2<GetThreshold())){
679             if ((j2<0) || (j2>GetNPixelsX()-1) || (xr>couplC)){
680                 j2 = col;
681                 flag = 1;
682             }else{
683                 UpdateMapSignal(row,j2,ntrack,idhit,module,pulse2,pList);
684                 //  flag = 0;
685                 flag = 1; // only first next!!
686             } // end if
687         } while(flag == 0);
688     } // for isign
689 }
690 //______________________________________________________________________
691 void AliITSsimulationSPD::SetCouplingOld(Int_t row, Int_t col, Int_t ntrack,
692                                          Int_t idhit,Int_t module,
693                                          AliITSpList *pList) {
694     //  Take into account the coupling between adiacent pixels.
695     //  The parameters probcol and probrow are the fractions of the
696     //  signal in one pixel shared in the two adjacent pixels along
697     //  the column and row direction, respectively.
698     // Inputs:
699     //    Int_t    row    pixel row number
700     //    Int_t    col    pixel column number
701     //    Int_t    ntrack track number of track contributing to this pixel
702     //    Int_t    idhit  hit index number of hit contributing to this pixel
703     //    Int_t    module module number
704     //   AliITSpList   *pList  the array of SDigits
705     // Outputs:
706     //   AliITSpList   *pList  the array of SDigits
707     // Return:
708     //   none.
709     //
710     //Begin_Html
711     /*
712       <img src="picts/ITS/barimodel_3.gif">
713       </pre>
714       <br clear=left>
715       <font size=+2 color=red>
716       <a href="mailto:Rocco.Caliandro@ba.infn.it"></a>.
717       </font>
718       <pre>
719     */
720     //End_Html
721     Int_t j1,j2,flag=0;
722     Double_t pulse1,pulse2;
723     Double_t couplR=0.0,couplC=0.0;
724
725     GetCouplings(couplR,couplC);
726     j1 = row;
727     j2 = col;
728     pulse1 = fMapA2->GetSignal(row,col);
729     pulse2 = pulse1;
730     for (Int_t isign=-1;isign<=1;isign+=2){// loop in row direction
731         do{
732             j1 += isign;
733             pulse1 *= couplR;
734             if ((j1<0) || (j1>GetNPixelsZ()-1) || (pulse1<GetThreshold())){
735                 pulse1 = fMapA2->GetSignal(row,col);
736                 j1 = row;
737                 flag = 1;
738             }else{
739                 UpdateMapSignal(j1,col,ntrack,idhit,module,pulse1,pList);
740                 flag = 0;
741             } // end if
742         } while(flag == 0);
743         // loop in column direction
744         do{
745             j2 += isign;
746             pulse2 *= couplC;
747             if ((j2<0) || (j2>(GetNPixelsX()-1)) || (pulse2<GetThreshold())){
748                 pulse2 = fMapA2->GetSignal(row,col);
749                 j2 = col;
750                 flag = 1;
751             }else{
752                 UpdateMapSignal(row,j2,ntrack,idhit,module,pulse2,pList);
753                 flag = 0;
754             } // end if
755         } while(flag == 0);
756     } // for isign
757 }
758 //______________________________________________________________________
759 void AliITSsimulationSPD::CreateDigit(Int_t module,AliITSpList *pList) {
760     // The pixels are fired if the energy deposited inside them is above
761     // the threshold parameter ethr. Fired pixed are interpreted as digits
762     // and stored in the file digitfilename. One also needs to write out
763     // cases when there is only noise (nhits==0).
764     // Inputs:
765     //    Int_t    module
766     //   AliITSpList   *pList  the array of SDigits
767     // Outputs:
768     //   AliITSpList   *pList  the array of SDigits
769     // Return:
770     //   none.
771
772     static AliITS *aliITS  = (AliITS*)gAlice->GetModule("ITS");
773
774     Int_t size = AliITSdigitSPD::GetNTracks();
775     Int_t * digits = new Int_t[size];
776     Int_t * tracks = new Int_t[size];
777     Int_t * hits = new Int_t[size];
778     Float_t * charges = new Float_t[size]; 
779     Int_t j1;
780
781     module=0; // remove unused variable warning.
782     for(j1=0;j1<size;j1++){tracks[j1]=-3;hits[j1]=-1;charges[j1]=0.0;}
783     for (Int_t r=1;r<=GetNPixelsZ();r++) {
784         for (Int_t c=1;c<=GetNPixelsX();c++) {
785             // check if the deposited energy in a pixel is above the
786             // threshold 
787             Float_t signal = (Float_t) fMapA2->GetSignal(r,c);
788             if ( signal > GetThreshold()) {
789                 digits[0] = r-1;  // digits starts from 0
790                 digits[1] = c-1;  // digits starts from 0
791                 //digits[2] = 1;  
792                 digits[2] =  (Int_t) signal;  // the signal is stored in
793                                               //  electrons
794                 for(j1=0;j1<size;j1++){
795                     if(j1<pList->GetNEnteries()){
796                         tracks[j1] = pList->GetTrack(r,c,j1);
797                         hits[j1]   = pList->GetHit(r,c,j1);
798                         //}else{
799                         //tracks[j1] = -3;
800                         //hits[j1]   = -1;
801                     } // end if
802                     //charges[j1] = 0;
803                 } // end for j1
804                 Float_t phys = 0;
805                 aliITS->AddSimDigit(0,phys,digits,tracks,hits,charges);
806                 if(GetDebug()){
807                     cout << " CreateSPDDigit mod=" << fModule << " r,c=" << r;
808                     cout <<","<<c<< " sig=" << fpList->GetSignalOnly(r,c);
809                     cout << " noise=" << fpList->GetNoise(r,c);
810                     cout << " Msig="<< signal << " Thres=" << GetThreshold();
811                     cout <<endl;
812                 }// end if GetDebug
813             } // end if of threshold condition
814         } // for c
815     }// end do on pixels
816     delete [] digits;
817     delete [] tracks;
818     delete [] hits;
819     delete [] charges;
820 }
821 //______________________________________________________________________
822 void AliITSsimulationSPD::SetFluctuations(AliITSpList *pList,Int_t module) {
823     //  Set the electronic noise and threshold non-uniformities to all the
824     //  pixels in a detector.
825     //  The parameter fSigma is the squared sum of the sigma due to noise
826     //  and the sigma of the threshold distribution among pixels.
827     // Inputs:
828     //    Int_t      module  modulel number
829     //   AliITSpList *pList  the array of SDigits
830     // Outputs:
831     //   AliITSpList *pList  the array of SDigits
832     // Return:
833     //   none.
834     //
835     //Begin_Html
836     /*
837       <img src="picts/ITS/barimodel_1.gif">
838       </pre>
839       <br clear=left>
840       <font size=+2 color=red>
841       <a href="mailto:Rocco.Caliandro@ba.infn.it"></a>.
842       </font>
843       <pre>
844     */
845     //End_Html
846     Double_t  thr=0.0,sigm=0.0;
847     Double_t signal,sigma;
848     Int_t iz,ix;
849
850     GetThresholds(thr,sigm);
851     sigma = (Double_t) sigm;
852     for(iz=1;iz<=GetNPixelsZ();iz++){
853         for(ix=1;ix<=GetNPixelsX();ix++){
854             signal = sigma*gRandom->Gaus(); 
855             fMapA2->SetHit(iz,ix,signal);
856             // insert in the label-signal-hit list the pixels fired
857             // only by noise
858             pList->AddNoise(iz,ix,module,signal);
859         } // end of loop on pixels
860     } // end of loop on pixels
861 }
862 //______________________________________________________________________
863 void AliITSsimulationSPD::SetMask() {
864     //  Apply a mask to the SPD module. 1% of the pixel channels are
865     //  masked. When the database will be ready, the masked pixels
866     //  should be read from it.
867     // Inputs:
868     //   none.
869     // Outputs:
870     //   none.
871     // Return:
872     //   none.
873     Double_t signal;
874     Int_t iz,ix,im;
875     Float_t totMask;
876     Float_t perc = ((AliITSresponseSPD*)fResponse)->GetFractionDead();
877     // in this way we get the same set of random numbers for all runs.
878     // This is a cluge for now.
879     static TRandom *rnd = new TRandom();
880
881     totMask= perc*GetNPixelsZ()*GetNPixelsX();
882     for(im=1;im<totMask;im++){
883         do{
884             ix=(Int_t)(rnd->Rndm()*(GetNPixelsX()-1.) + 1.);
885         } while(ix<=0 || ix>GetNPixelsX());
886         do{
887             iz=(Int_t)(rnd->Rndm()*(GetNPixelsZ()-1.) + 1.);
888         } while(iz<=0 || iz>GetNPixelsZ());
889         signal = -1.;
890         fMapA2->SetHit(iz,ix,signal);
891     } // end loop on masked pixels
892 }
893 //______________________________________________________________________
894 void AliITSsimulationSPD::CreateHistograms() {
895     // Create Histograms
896     // Inputs:
897     //   none.
898     // Outputs:
899     //   none.
900     // Return:
901     //   none.
902     Int_t i;
903
904     fHis=new TObjArray(GetNPixelsZ());
905     for(i=0;i<GetNPixelsZ();i++) {
906         TString spdname("spd_");
907         Char_t candnum[4];
908         sprintf(candnum,"%d",i+1);
909         spdname.Append(candnum);
910         (*fHis)[i] = new TH1F(spdname.Data(),"SPD maps",
911                               GetNPixelsX(),0.,(Float_t) GetNPixelsX());
912     } // end for i
913 }
914 //______________________________________________________________________
915 void AliITSsimulationSPD::ResetHistograms() {
916     // Reset histograms for this detector
917     // Inputs:
918     //   none.
919     // Outputs:
920     //   none.
921     // Return:
922     //   none.
923     Int_t i;
924
925     for(i=0;i<GetNPixelsZ();i++ ) {
926         if ((*fHis)[i])    ((TH1F*)(*fHis)[i])->Reset();
927     } // end for i
928 }
929 //______________________________________________________________________
930 void AliITSsimulationSPD::WriteSDigits(AliITSpList *pList){
931     // Fills the Summable digits Tree
932     // Inputs:
933     //   AliITSpList   *pList  the array of SDigits
934     // Outputs:
935     //   AliITSpList   *pList  the array of SDigits
936     // Return:
937     //   none.
938     Int_t i,ni,j,nj;
939     static AliITS *aliITS = (AliITS*)gAlice->GetModule("ITS");
940
941     pList->GetMaxMapIndex(ni,nj);
942     for(i=0;i<ni;i++)for(j=0;j<nj;j++){
943         if(pList->GetSignalOnly(i,j)>0.0){
944             aliITS->AddSumDigit(*(pList->GetpListItem(i,j)));
945             if(GetDebug()){
946                 cout << "pListSPD: " << *(pList->GetpListItem(i,j)) << endl;
947                 cout << " CreateSPDSDigit mod=" << fModule << " r,c=";
948                 cout << i  <<","<< j << " sig=" << fpList->GetSignalOnly(i,j);
949                 cout << " noise=" << fpList->GetNoise(i,j) <<endl;
950             } //  end if GetDebug
951         } // end if
952     } // end for i,j
953     return;
954 }
955 //______________________________________________________________________
956 void AliITSsimulationSPD::FillMapFrompList(AliITSpList *pList){
957     // Fills fMap2A from the pList of Summable digits
958     // Inputs:
959     //   AliITSpList   *pList  the array of SDigits
960     // Outputs:
961     //   AliITSpList   *pList  the array of SDigits
962     // Return:
963     //   none.
964     Int_t ix,iz;
965
966     for(iz=0;iz<GetNPixelsZ();iz++)for(ix=0;ix<GetNPixelsX();ix++) 
967         fMapA2->AddSignal(iz,ix,pList->GetSignal(iz,ix));
968     return;
969 }