AliMUONTriggerConstants added
[u/mrichter/AliRoot.git] / MUON / AliMUON.cxx
CommitLineData
4c039060 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 **************************************************************************/
4c039060 15/*
16$Log$
9ae15266 17Revision 1.18 2000/06/15 07:58:48 morsch
18Code from MUON-dev joined
19
a9e2aefa 20Revision 1.14.4.17 2000/06/14 14:36:46 morsch
21- add TriggerCircuit (PC)
22- add GlobalTrigger and LocalTrigger and specific methods (PC)
23
24Revision 1.14.4.16 2000/06/09 21:20:28 morsch
25Most coding rule violations corrected
26
27Revision 1.14.4.15 2000/05/02 09:54:32 morsch
28RULE RN17 violations corrected
29
30Revision 1.14.4.12 2000/04/26 12:25:02 morsch
31Code revised by P. Crochet:
32- Z position of TriggerChamber changed according to A.Tournaire Priv.Comm.
33- ToF included in the method MakePadHits
34- inner radius of flange between beam shielding and trigger corrected
35- Trigger global volume updated (according to the new geometry)
36
37Revision 1.14.4.11 2000/04/19 19:42:08 morsch
38Some changes of variable names curing viols and methods concerning
39correlated clusters removed.
40
41Revision 1.14.4.10 2000/03/22 16:44:07 gosset
42Memory leak suppressed in function Digitise:
43p_adr->Delete() instead of Clear (I.Chevrot and A.Baldisseri)
44
45Revision 1.14.4.9 2000/03/20 18:15:25 morsch
46Positions of trigger chambers corrected (P.C.)
dbe37a89 47
a9e2aefa 48Revision 1.14.4.8 2000/02/21 15:38:01 morsch
49Call to AddHitList introduced to make this version compatible with head.
dffd31ef 50
a9e2aefa 51Revision 1.14.4.7 2000/02/20 07:45:53 morsch
52Bugs in Trigger part of BuildGeomemetry corrected (P.C)
1cedd08a 53
a9e2aefa 54Revision 1.14.4.6 2000/02/17 14:28:54 morsch
55Trigger included into initialization and digitization
6a935c13 56
a9e2aefa 57Revision 1.14.4.5 2000/02/15 10:02:58 morsch
58Log messages of previous revisions added
5d84196c 59
a9e2aefa 60Revision 1.14.4.2 2000/02/04 10:57:34 gosset
61Z position of the chambers:
62it was the Z position of the stations;
63it is now really the Z position of the chambers.
64 !!!! WARNING: THE CALLS TO "AliMUONChamber::SetZPOS"
65 !!!! AND "AliMUONChamber::ZPosition"
66 !!!! HAVE TO BE CHANGED TO "AliMUONChamber::"SetZ"
67 !!!! AND "AliMUONChamber::Z"
50f986db 68
a9e2aefa 69Revision 1.14.4.3 2000/02/04 16:19:04 gosset
70Correction for mis-spelling of NCH
0b34885d 71
a9e2aefa 72Revision 1.14.4.4 2000/02/15 09:43:38 morsch
73Log message added
2b86633d 74
4c039060 75*/
76
a9e2aefa 77
78///////////////////////////////////////////////
fe4da5cc 79// Manager and hits classes for set:MUON //
80////////////////////////////////////////////////
81
82#include <TTUBE.h>
a897a37a 83#include <TBRIK.h>
84#include <TRotMatrix.h>
fe4da5cc 85#include <TNode.h>
a897a37a 86#include <TTree.h>
fe4da5cc 87#include <TRandom.h>
88#include <TObject.h>
89#include <TVector.h>
90#include <TObjArray.h>
a897a37a 91#include <TMinuit.h>
92#include <TParticle.h>
93#include <TROOT.h>
94#include <TFile.h>
95#include <TNtuple.h>
96#include <TCanvas.h>
97#include <TPad.h>
98#include <TDirectory.h>
99#include <TObjectTable.h>
100#include <AliPDG.h>
a9e2aefa 101#include <TTUBE.h>
fe4da5cc 102
103#include "AliMUON.h"
a9e2aefa 104#include "AliMUONHit.h"
105#include "AliMUONPadHit.h"
106#include "AliMUONDigit.h"
107#include "AliMUONTransientDigit.h"
108#include "AliMUONRawCluster.h"
109#include "AliMUONLocalTrigger.h"
110#include "AliMUONGlobalTrigger.h"
111#include "AliMUONHitMap.h"
112#include "AliMUONHitMapA1.h"
113#include "AliMUONChamberTrigger.h"
114
a897a37a 115#include "AliMUONClusterFinder.h"
a9e2aefa 116#include "AliMUONTriggerDecision.h"
fe4da5cc 117#include "AliRun.h"
118#include "AliMC.h"
119#include "iostream.h"
120#include "AliCallf77.h"
a9e2aefa 121#include "AliConst.h"
122
123// Defaults parameters for Z positions of chambers
124// taken from values for "stations" in AliMUON::AliMUON
125// const Float_t zch[7]={528, 690., 975., 1249., 1449., 1610, 1710.};
126// and from array "dstation" in AliMUONv1::CreateGeometry
127// Float_t dstation[5]={20., 20., 20, 20., 20.};
128// for tracking chambers,
129// according to (Z1 = zch - dstation) and (Z2 = zch + dstation)
130// for the first and second chambers in the station, respectively,
131// and from "DTPLANES" in AliMUONv1::CreateGeometry
132// const Float_t DTPLANES = 15.;
133// for trigger chambers,
134// according to (Z1 = zch) and (Z2 = zch + DTPLANES)
135// for the first and second chambers in the station, respectively
136static const Float_t kDefaultChambersZ[kNCH] =
137{518., 538., 680., 700., 965., 985., 1239., 1259., 1439., 1459.,
138 1603.5, 1618.5, 1703.5, 1718.5};
fe4da5cc 139
fe4da5cc 140ClassImp(AliMUON)
fe4da5cc 141//___________________________________________
142AliMUON::AliMUON()
143{
a9e2aefa 144 fIshunt = 0;
145 fHits = 0;
146 fPadHits = 0;
147 fNPadHits = 0;
148 fDchambers = 0;
149 fTriggerCircuits = 0; // cp new design of AliMUONTriggerDecision
150 fNdch = 0;
151 fRawClusters = 0;
152 fNrawch = 0;
153 fGlobalTrigger = 0;
154 fNLocalTrigger = 0;
155 fLocalTrigger = 0;
156 fNLocalTrigger = 0;
fe4da5cc 157}
158
159//___________________________________________
160AliMUON::AliMUON(const char *name, const char *title)
161 : AliDetector(name,title)
162{
163//Begin_Html
164/*
a897a37a 165<img src="gif/alimuon.gif">
fe4da5cc 166*/
167//End_Html
168
a9e2aefa 169 fHits = new TClonesArray("AliMUONHit",1000);
1cedd08a 170 gAlice->AddHitList(fHits);
a9e2aefa 171 fPadHits = new TClonesArray("AliMUONPadHit",10000);
172 fNPadHits = 0;
fe4da5cc 173 fIshunt = 0;
174
a9e2aefa 175 fNdch = new Int_t[kNCH];
fe4da5cc 176
a9e2aefa 177 fDchambers = new TObjArray(kNCH);
fe4da5cc 178
179 Int_t i;
180
a9e2aefa 181 for (i=0; i<kNCH ;i++) {
182 (*fDchambers)[i] = new TClonesArray("AliMUONDigit",10000);
fe4da5cc 183 fNdch[i]=0;
184 }
185
a9e2aefa 186 fNrawch = new Int_t[kNTrackingCh];
a897a37a 187
a9e2aefa 188 fRawClusters = new TObjArray(kNTrackingCh);
a897a37a 189
a9e2aefa 190 for (i=0; i<kNTrackingCh;i++) {
a897a37a 191 (*fRawClusters)[i] = new TClonesArray("AliMUONRawCluster",10000);
192 fNrawch[i]=0;
193 }
a9e2aefa 194 cout << " here " << "\n";
a897a37a 195
a9e2aefa 196 fGlobalTrigger = new TClonesArray("AliMUONGlobalTrigger",1);
197 fNGlobalTrigger = 0;
198 fLocalTrigger = new TClonesArray("AliMUONLocalTrigger",234);
199 fNLocalTrigger = 0;
fe4da5cc 200
201//
202// Transport angular cut
203 fAccCut=0;
204 fAccMin=2;
205 fAccMax=9;
206
207 SetMarkerColor(kRed);
a9e2aefa 208//
209//
210//
211//
212// inner diameter
213 const Float_t kDmin[7]={ 35., 47., 66., 80., 80., 100., 100.};
214//
215// outer diameter
216 const Float_t kDmax[7]={183., 245., 316.6, 520., 520., 830., 880.};
217//
218 Int_t ch;
219
220 fChambers = new TObjArray(kNCH);
221
222 // Loop over stations
223 for (Int_t st = 0; st < kNCH / 2; st++) {
224 // Loop over 2 chambers in the station
225 for (Int_t stCH = 0; stCH < 2; stCH++) {
226//
227//
228// Default Parameters for Muon Tracking Stations
229
230
231 ch = 2 * st + stCH;
232//
233 if (ch < kNTrackingCh) {
234 (*fChambers)[ch] = new AliMUONChamber();
235 } else {
236 (*fChambers)[ch] = new AliMUONChamberTrigger();
237 }
238
239 AliMUONChamber* chamber = (AliMUONChamber*) (*fChambers)[ch];
240
241 chamber->SetGid(0);
242 // Default values for Z of chambers
243 chamber->SetZ(kDefaultChambersZ[ch]);
244//
245 chamber->InitGeo(kDefaultChambersZ[ch]);
246 chamber->SetRInner(kDmin[st]/2);
247 chamber->SetROuter(kDmax[st]/2);
248//
249 } // Chamber stCH (0, 1) in
250 } // Station st (0...)
251 fMaxStepGas=0.01;
252 fMaxStepAlu=0.1;
253 fMaxDestepGas=-1;
254 fMaxDestepAlu=-1;
255//
256 fMaxIterPad = 0;
257 fCurIterPad = 0;
258
259 // cp new design of AliMUONTriggerDecision
260 fTriggerCircuits = new TObjArray(kNTriggerCircuit);
261 for (Int_t circ=0; circ<kNTriggerCircuit; circ++) {
262 (*fTriggerCircuits)[circ] = new AliMUONTriggerCircuit();
263 }
264 // cp new design of AliMUONTriggerDecision
265
fe4da5cc 266}
267
268//___________________________________________
a9e2aefa 269AliMUON::AliMUON(const AliMUON& rMUON)
270{
271// Dummy copy constructor
272 ;
273
274}
275
fe4da5cc 276AliMUON::~AliMUON()
277{
a897a37a 278
279 printf("Calling AliMUON destructor !!!\n");
280
a6f39961 281 Int_t i;
fe4da5cc 282 fIshunt = 0;
283 delete fHits;
a9e2aefa 284 delete fPadHits;
fe4da5cc 285
a9e2aefa 286 delete fGlobalTrigger;
287 fNGlobalTrigger = 0;
288
289 delete fLocalTrigger;
290 fNLocalTrigger = 0;
291
292 for (i=0;i<kNCH;i++) {
a897a37a 293 delete (*fDchambers)[i];
294 fNdch[i]=0;
295 }
296 delete fDchambers;
297
a9e2aefa 298 for (i=0;i<kNTrackingCh;i++) {
a897a37a 299 delete (*fRawClusters)[i];
300 fNrawch[i]=0;
301 }
302 delete fRawClusters;
303
a9e2aefa 304 for (Int_t circ=0; circ<kNTriggerCircuit; circ++) {
305 delete (*fTriggerCircuits)[circ];
a897a37a 306 }
a9e2aefa 307 delete fTriggerCircuits;
fe4da5cc 308}
309
310//___________________________________________
311void AliMUON::AddHit(Int_t track, Int_t *vol, Float_t *hits)
312{
313 TClonesArray &lhits = *fHits;
a9e2aefa 314 new(lhits[fNhits++]) AliMUONHit(fIshunt,track,vol,hits);
fe4da5cc 315}
316//___________________________________________
a9e2aefa 317void AliMUON::AddPadHit(Int_t *clhits)
fe4da5cc 318{
a9e2aefa 319 TClonesArray &lclusters = *fPadHits;
320 new(lclusters[fNPadHits++]) AliMUONPadHit(clhits);
fe4da5cc 321}
322//_____________________________________________________________________________
323void AliMUON::AddDigits(Int_t id, Int_t *tracks, Int_t *charges, Int_t *digits)
324{
325 //
326 // Add a MUON digit to the list
327 //
328
329 TClonesArray &ldigits = *((TClonesArray*)(*fDchambers)[id]);
a9e2aefa 330 new(ldigits[fNdch[id]++]) AliMUONDigit(tracks,charges,digits);
fe4da5cc 331}
332
a897a37a 333//_____________________________________________________________________________
334void AliMUON::AddRawCluster(Int_t id, const AliMUONRawCluster& c)
335{
336 //
337 // Add a MUON digit to the list
338 //
339
340 TClonesArray &lrawcl = *((TClonesArray*)(*fRawClusters)[id]);
341 new(lrawcl[fNrawch[id]++]) AliMUONRawCluster(c);
342}
a897a37a 343
a9e2aefa 344//___________________________________________
345void AliMUON::AddGlobalTrigger(Int_t *singlePlus, Int_t *singleMinus,
346 Int_t *singleUndef,
347 Int_t *pairUnlike, Int_t *pairLike)
348{
349// add a MUON Global Trigger to the list (only one GlobalTrigger per event !)
350 TClonesArray &globalTrigger = *fGlobalTrigger;
351 new(globalTrigger[fNGlobalTrigger++])
352 AliMUONGlobalTrigger(singlePlus, singleMinus, singleUndef, pairUnlike,
353 pairLike);
354}
355//___________________________________________
356void AliMUON::AddLocalTrigger(Int_t *localtr)
357{
358// add a MUON Local Trigger to the list
359 TClonesArray &localTrigger = *fLocalTrigger;
360 new(localTrigger[fNLocalTrigger++]) AliMUONLocalTrigger(localtr);
a897a37a 361}
362
fe4da5cc 363//___________________________________________
364void AliMUON::BuildGeometry()
365{
a9e2aefa 366 TNode *node, *nodeF, *top, *nodeS;
367 const int kColorMUON = kBlue;
368 const int kColorMUON2 = kGreen;
a897a37a 369 //
a9e2aefa 370 top=gAlice->GetGeometry()->GetNode("alice");
a897a37a 371// MUON
372//
373// z-Positions of Chambers
a9e2aefa 374 const Float_t kCz[7]={511., 686., 971., 1245., 1445., 1600, 1700.};
375// inner diameter (Xlenght for trigger chamber -> active area)
376 const Float_t kDmin[7]={ 35., 47., 67., 86., 100., 544., 544.};
377// outer diameter (Ylenght for trigger chamber -> active area)
378 const Float_t kDmax[7]={183., 245., 346., 520., 520., 612., 612.};
a897a37a 379
380 TRotMatrix* rot000 = new TRotMatrix("Rot000"," ", 90, 0, 90, 90, 0, 0);
381 TRotMatrix* rot090 = new TRotMatrix("Rot090"," ", 90, 90, 90,180, 0, 0);
382 TRotMatrix* rot180 = new TRotMatrix("Rot180"," ", 90,180, 90,270, 0, 0);
383 TRotMatrix* rot270 = new TRotMatrix("Rot270"," ", 90,270, 90, 0, 0, 0);
384
a9e2aefa 385 Float_t rmin, rmax, dx, dy, dz, dr, xpos, ypos, zpos;
386 Float_t dzc1=4.; // tracking chambers
387 Float_t dzc2=15.; // trigger chambers
388 Float_t hole=102.; // x-y hole around beam pipe for trig. chambers
389 Float_t zscale; // scaling parameter trigger chambers
390 Float_t halfx, halfy;
391 char nameChamber[9], nameSense[9], nameFrame[9], nameNode[8];
392 char nameSense1[9], nameSense2[9];
393 for (Int_t i=0; i<7; i++) {
a897a37a 394 for (Int_t j=0; j<2; j++) {
395 Int_t id=2*i+j+1;
a9e2aefa 396 if (i<5) { // tracking chambers
397 if (j==0) {
398 zpos=kCz[i]-dzc1;
399 } else {
400 zpos=kCz[i]+dzc1;
401 }
a897a37a 402 } else {
a9e2aefa 403 if (j==0) {
404 zpos=kCz[i];
405 } else {
406 zpos=kCz[i]+dzc2;
407 }
a897a37a 408 }
a9e2aefa 409 sprintf(nameChamber,"C_MUON%d",id);
410 sprintf(nameSense,"S_MUON%d",id);
411 sprintf(nameSense1,"S1_MUON%d",id);
412 sprintf(nameSense2,"S2_MUON%d",id);
413 sprintf(nameFrame,"F_MUON%d",id);
414 if (i<5) { // tracking chambers
415 rmin = kDmin[i]/2.-3;
416 rmax = kDmax[i]/2.+3;
417 new TTUBE(nameChamber,"Mother","void",rmin,rmax,0.25,1.);
418 rmin = kDmin[i]/2.;
419 rmax = kDmax[i]/2.;
420 new TTUBE(nameSense,"Sens. region","void",rmin,rmax,0.25, 1.);
421 dx=(rmax-rmin)/2;
422 dy=3.;
423 dz=0.25;
424 TBRIK* frMUON = new TBRIK(nameFrame,"Frame","void",dx,dy,dz);
425 top->cd();
426 sprintf(nameNode,"MUON%d",100+id);
427 node = new TNode(nameNode,"ChamberNode",nameChamber,0,0,zpos,"");
428 node->SetLineColor(kColorMUON);
429 fNodes->Add(node);
430 node->cd();
431 sprintf(nameNode,"MUON%d",200+id);
432 node = new TNode(nameNode,"Sens. Region Node",nameSense,0,0,0,"");
433 node->SetLineColor(kColorMUON);
434 node->cd();
435 dr=dx+rmin;
436 sprintf(nameNode,"MUON%d",300+id);
437 nodeF = new TNode(nameNode,"Frame0",frMUON,dr, 0, 0,rot000,"");
438 nodeF->SetLineColor(kColorMUON);
439 node->cd();
440 sprintf(nameNode,"MUON%d",400+id);
441 nodeF = new TNode(nameNode,"Frame1",frMUON,0 ,dr,0,rot090,"");
442 nodeF->SetLineColor(kColorMUON);
443 node->cd();
444 sprintf(nameNode,"MUON%d",500+id);
445 nodeF = new TNode(nameNode,"Frame2",frMUON,-dr,0,0,rot180,"");
446 nodeF->SetLineColor(kColorMUON);
447 node ->cd();
448 sprintf(nameNode,"MUON%d",600+id);
449 nodeF = new TNode(nameNode,"Frame3",frMUON,0,-dr,0,rot270,"");
450 nodeF->SetLineColor(kColorMUON);
451 } else {
452 zscale=zpos/kCz[5];
453 Float_t xsize=kDmin[i]*zscale;
454 Float_t ysize=kDmax[i]*zscale;
455 Float_t holeScaled=hole*zscale;
456
457 halfx=xsize/2.+3.;
458 halfy=ysize/2.+3.;
459 new TBRIK(nameChamber,"Mother","void",halfx,halfy,0.25);
460 top->cd();
461 sprintf(nameNode,"MUON%d",100+id);
462 node = new TNode(nameNode,"Chambernode",nameChamber,0,0,zpos,"");
463 node->SetLineColor(kColorMUON2);
464 fNodes->Add(node);
465
466// up/down of beam pipe
467 halfx=xsize/2.;
468 halfy=(ysize/2.-holeScaled/2.)/2.;
469 new TBRIK(nameSense,"Sens. region","void",halfx,halfy,0.25);
470
471 node->cd();
472 ypos=holeScaled/2.+((ysize/2.-holeScaled/2.)/2.);
473 sprintf(nameNode,"MUON%d",200+id);
474 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense,0,ypos,0,"");
475 nodeS->SetLineColor(kColorMUON2);
476
477 node->cd();
478 ypos=-1.*ypos;
479 sprintf(nameNode,"MUON%d",300+id);
480 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense,0,ypos,0,"");
481 nodeS->SetLineColor(kColorMUON2);
482
483// left/right of beam pipe
484 halfx=(xsize/2.-holeScaled/2.)/2.;
485 halfy=holeScaled/2.;
486 new TBRIK(nameSense1,"Sens. region","void",halfx,halfy,0.25);
487
488 node->cd();
489 xpos=holeScaled/2.+((xsize/2.-holeScaled/2.)/2.);
490 sprintf(nameNode,"MUON%d",400+id);
491 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense1,xpos,0,0,"");
492 nodeS->SetLineColor(kColorMUON2);
493
494 node->cd();
495 xpos=-1.*xpos;
496 sprintf(nameNode,"MUON%d",500+id);
497 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense1,xpos,0,0,"");
498 nodeS->SetLineColor(kColorMUON2);
499
500// missing corners
501 halfx=17.*zscale/2.;
502 halfy=halfx;
503 new TBRIK(nameSense2,"Sens. region","void",halfx,halfy,0.25);
504
505 node->cd();
506 xpos=holeScaled/2.-halfx;
507 ypos=xpos;
508 sprintf(nameNode,"MUON%d",600+id);
509 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
510 nodeS->SetLineColor(kColorMUON2);
511
512 node->cd();
513 ypos=-1.*xpos;
514 sprintf(nameNode,"MUON%d",700+id);
515 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
516 nodeS->SetLineColor(kColorMUON2);
517
518 node->cd();
519 xpos=-1.*xpos;
520 sprintf(nameNode,"MUON%d",800+id);
521 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
522 nodeS->SetLineColor(kColorMUON2);
523
524 node->cd();
525 ypos=-1.*xpos;
526 sprintf(nameNode,"MUON%d",900+id);
527 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
528 nodeS->SetLineColor(kColorMUON2);
529 }
a897a37a 530 }
531 }
fe4da5cc 532}
533
a897a37a 534
fe4da5cc 535//___________________________________________
536Int_t AliMUON::DistancetoPrimitive(Int_t , Int_t )
537{
538 return 9999;
539}
540
541//___________________________________________
542void AliMUON::MakeBranch(Option_t* option)
543{
544 // Create Tree branches for the MUON.
545
a9e2aefa 546 const Int_t kBufferSize = 4000;
a897a37a 547 char branchname[30];
fe4da5cc 548 sprintf(branchname,"%sCluster",GetName());
549
550 AliDetector::MakeBranch(option);
551
a9e2aefa 552 if (fPadHits && gAlice->TreeH()) {
553 gAlice->TreeH()->Branch(branchname,&fPadHits, kBufferSize);
fe4da5cc 554 printf("Making Branch %s for clusters\n",branchname);
555 }
556
557// one branch for digits per chamber
558 Int_t i;
559
a9e2aefa 560 for (i=0; i<kNCH ;i++) {
fe4da5cc 561 sprintf(branchname,"%sDigits%d",GetName(),i+1);
562
563 if (fDchambers && gAlice->TreeD()) {
a9e2aefa 564 gAlice->TreeD()->Branch(branchname,&((*fDchambers)[i]), kBufferSize);
fe4da5cc 565 printf("Making Branch %s for digits in chamber %d\n",branchname,i+1);
566 }
567 }
a897a37a 568
a9e2aefa 569 printf("Make Branch - TreeR address %p\n",gAlice->TreeR());
a897a37a 570
571// one branch for raw clusters per chamber
a9e2aefa 572 for (i=0; i<kNTrackingCh ;i++) {
a897a37a 573 sprintf(branchname,"%sRawClusters%d",GetName(),i+1);
574
575 if (fRawClusters && gAlice->TreeR()) {
a9e2aefa 576 gAlice->TreeR()->Branch(branchname,&((*fRawClusters)[i]), kBufferSize);
a897a37a 577 printf("Making Branch %s for raw clusters in chamber %d\n",branchname,i+1);
578 }
579 }
580
a9e2aefa 581// one branch for global trigger
582 sprintf(branchname,"%sGlobalTrigger",GetName());
583 if (fGlobalTrigger && gAlice->TreeR()) {
584 gAlice->TreeR()->Branch(branchname,&fGlobalTrigger,kBufferSize);
585 printf("Making Branch %s for Global Trigger\n",branchname);
586 }
587// one branch for local trigger
588 sprintf(branchname,"%sLocalTrigger",GetName());
589 if (fLocalTrigger && gAlice->TreeR()) {
590 gAlice->TreeR()->Branch(branchname,&fLocalTrigger,kBufferSize);
591 printf("Making Branch %s for Local Trigger\n",branchname);
592 }
593
fe4da5cc 594}
595
596//___________________________________________
597void AliMUON::SetTreeAddress()
598{
599 // Set branch address for the Hits and Digits Tree.
a897a37a 600 char branchname[30];
fe4da5cc 601 AliDetector::SetTreeAddress();
602
603 TBranch *branch;
604 TTree *treeH = gAlice->TreeH();
605 TTree *treeD = gAlice->TreeD();
a897a37a 606 TTree *treeR = gAlice->TreeR();
fe4da5cc 607
608 if (treeH) {
a9e2aefa 609 if (fPadHits) {
fe4da5cc 610 branch = treeH->GetBranch("MUONCluster");
a9e2aefa 611 if (branch) branch->SetAddress(&fPadHits);
fe4da5cc 612 }
613 }
614
615 if (treeD) {
a9e2aefa 616 for (int i=0; i<kNCH; i++) {
fe4da5cc 617 sprintf(branchname,"%sDigits%d",GetName(),i+1);
618 if (fDchambers) {
619 branch = treeD->GetBranch(branchname);
620 if (branch) branch->SetAddress(&((*fDchambers)[i]));
621 }
622 }
623 }
a897a37a 624
625 // printf("SetTreeAddress --- treeR address %p \n",treeR);
626
627 if (treeR) {
a9e2aefa 628 for (int i=0; i<kNTrackingCh; i++) {
a897a37a 629 sprintf(branchname,"%sRawClusters%d",GetName(),i+1);
630 if (fRawClusters) {
631 branch = treeR->GetBranch(branchname);
632 if (branch) branch->SetAddress(&((*fRawClusters)[i]));
633 }
634 }
a897a37a 635
a9e2aefa 636 if (fLocalTrigger) {
637 branch = treeR->GetBranch("MUONLocalTrigger");
638 if (branch) branch->SetAddress(&fLocalTrigger);
639 }
640 if (fGlobalTrigger) {
641 branch = treeR->GetBranch("MUONGlobalTrigger");
642 if (branch) branch->SetAddress(&fGlobalTrigger);
643 }
644 }
fe4da5cc 645}
646//___________________________________________
647void AliMUON::ResetHits()
648{
649 // Reset number of clusters and the cluster array for this detector
650 AliDetector::ResetHits();
a9e2aefa 651 fNPadHits = 0;
652 if (fPadHits) fPadHits->Clear();
fe4da5cc 653}
654
655//____________________________________________
656void AliMUON::ResetDigits()
657{
658 //
659 // Reset number of digits and the digits array for this detector
660 //
a9e2aefa 661 for ( int i=0;i<kNCH;i++ ) {
a897a37a 662 if ((*fDchambers)[i]) ((TClonesArray*)(*fDchambers)[i])->Clear();
fe4da5cc 663 if (fNdch) fNdch[i]=0;
664 }
665}
a897a37a 666//____________________________________________
667void AliMUON::ResetRawClusters()
668{
669 //
670 // Reset number of raw clusters and the raw clust array for this detector
671 //
a9e2aefa 672 for ( int i=0;i<kNTrackingCh;i++ ) {
a897a37a 673 if ((*fRawClusters)[i]) ((TClonesArray*)(*fRawClusters)[i])->Clear();
674 if (fNrawch) fNrawch[i]=0;
675 }
676}
a9e2aefa 677
a897a37a 678//____________________________________________
a9e2aefa 679void AliMUON::ResetTrigger()
a897a37a 680{
a9e2aefa 681 // Reset Local and Global Trigger
682 fNGlobalTrigger = 0;
683 if (fGlobalTrigger) fGlobalTrigger->Clear();
684 fNLocalTrigger = 0;
685 if (fLocalTrigger) fLocalTrigger->Clear();
686}
687
688//____________________________________________
689void AliMUON::SetPadSize(Int_t id, Int_t isec, Float_t p1, Float_t p2)
690{
691 Int_t i=2*(id-1);
692 ((AliMUONChamber*) (*fChambers)[i]) ->SetPadSize(isec,p1,p2);
693 ((AliMUONChamber*) (*fChambers)[i+1])->SetPadSize(isec,p1,p2);
a897a37a 694}
695
fe4da5cc 696//___________________________________________
a9e2aefa 697void AliMUON::SetChambersZ(const Float_t *Z)
698{
699 // Set Z values for all chambers (tracking and trigger)
700 // from the array pointed to by "Z"
701 for (Int_t ch = 0; ch < kNCH; ch++)
702 ((AliMUONChamber*) ((*fChambers)[ch]))->SetZ(Z[ch]);
703 return;
704}
fe4da5cc 705
a9e2aefa 706//___________________________________________
707void AliMUON::SetChambersZToDefault()
fe4da5cc 708{
a9e2aefa 709 // Set Z values for all chambers (tracking and trigger)
710 // to default values
711 SetChambersZ(kDefaultChambersZ);
712 return;
fe4da5cc 713}
714
715//___________________________________________
a897a37a 716void AliMUON::SetChargeSlope(Int_t id, Float_t p1)
fe4da5cc 717{
718 Int_t i=2*(id-1);
a9e2aefa 719 ((AliMUONChamber*) (*fChambers)[i])->SetChargeSlope(p1);
720 ((AliMUONChamber*) (*fChambers)[i+1])->SetChargeSlope(p1);
fe4da5cc 721}
722
723//___________________________________________
a897a37a 724void AliMUON::SetChargeSpread(Int_t id, Float_t p1, Float_t p2)
fe4da5cc 725{
726 Int_t i=2*(id-1);
a9e2aefa 727 ((AliMUONChamber*) (*fChambers)[i])->SetChargeSpread(p1,p2);
728 ((AliMUONChamber*) (*fChambers)[i+1])->SetChargeSpread(p1,p2);
fe4da5cc 729}
730
731//___________________________________________
a897a37a 732void AliMUON::SetSigmaIntegration(Int_t id, Float_t p1)
fe4da5cc 733{
734 Int_t i=2*(id-1);
a9e2aefa 735 ((AliMUONChamber*) (*fChambers)[i])->SetSigmaIntegration(p1);
736 ((AliMUONChamber*) (*fChambers)[i+1])->SetSigmaIntegration(p1);
fe4da5cc 737}
738
739//___________________________________________
a897a37a 740void AliMUON::SetMaxAdc(Int_t id, Float_t p1)
fe4da5cc 741{
742 Int_t i=2*(id-1);
a9e2aefa 743 ((AliMUONChamber*) (*fChambers)[i])->SetMaxAdc(p1);
744 ((AliMUONChamber*) (*fChambers)[i+1])->SetMaxAdc(p1);
fe4da5cc 745}
746
747//___________________________________________
a897a37a 748void AliMUON::SetMaxStepGas(Float_t p1)
fe4da5cc 749{
750 fMaxStepGas=p1;
751}
752
753//___________________________________________
a897a37a 754void AliMUON::SetMaxStepAlu(Float_t p1)
fe4da5cc 755{
756 fMaxStepAlu=p1;
757}
758
759//___________________________________________
a897a37a 760void AliMUON::SetMaxDestepGas(Float_t p1)
fe4da5cc 761{
762 fMaxDestepGas=p1;
763}
764
765//___________________________________________
a897a37a 766void AliMUON::SetMaxDestepAlu(Float_t p1)
fe4da5cc 767{
768 fMaxDestepAlu=p1;
769}
770//___________________________________________
a897a37a 771void AliMUON::SetMuonAcc(Bool_t acc, Float_t angmin, Float_t angmax)
fe4da5cc 772{
773 fAccCut=acc;
774 fAccMin=angmin;
775 fAccMax=angmax;
776}
777//___________________________________________
a9e2aefa 778void AliMUON::SetSegmentationModel(Int_t id, Int_t isec, AliMUONSegmentation *segmentation)
fe4da5cc 779{
a9e2aefa 780 ((AliMUONChamber*) (*fChambers)[id])->SetSegmentationModel(isec, segmentation);
fe4da5cc 781
782}
783//___________________________________________
a9e2aefa 784void AliMUON::SetResponseModel(Int_t id, AliMUONResponse *response)
fe4da5cc 785{
a9e2aefa 786 ((AliMUONChamber*) (*fChambers)[id])->SetResponseModel(response);
fe4da5cc 787}
788
a897a37a 789void AliMUON::SetReconstructionModel(Int_t id, AliMUONClusterFinder *reconst)
790{
a9e2aefa 791 ((AliMUONChamber*) (*fChambers)[id])->SetReconstructionModel(reconst);
a897a37a 792}
793
fe4da5cc 794void AliMUON::SetNsec(Int_t id, Int_t nsec)
795{
a9e2aefa 796 ((AliMUONChamber*) (*fChambers)[id])->SetNsec(nsec);
fe4da5cc 797}
798
799
800//___________________________________________
801
a897a37a 802
a9e2aefa 803
804void AliMUON::MakePadHits(Float_t xhit,Float_t yhit,
805 Float_t eloss, Float_t tof, Int_t idvol)
fe4da5cc 806{
807//
a897a37a 808// Calls the charge disintegration method of the current chamber and adds
809// the simulated cluster to the root treee
fe4da5cc 810//
a897a37a 811 Int_t clhits[7];
812 Float_t newclust[6][500];
813 Int_t nnew;
814
815
fe4da5cc 816//
a897a37a 817// Integrated pulse height on chamber
818
819
820 clhits[0]=fNhits+1;
fe4da5cc 821//
a897a37a 822//
a9e2aefa 823 ((AliMUONChamber*) (*fChambers)[idvol])
824 ->DisIntegration(eloss, tof, xhit, yhit, nnew, newclust);
a897a37a 825 Int_t ic=0;
826
827//
828// Add new clusters
829 for (Int_t i=0; i<nnew; i++) {
830 if (Int_t(newclust[3][i]) > 0) {
831 ic++;
832// Cathode plane
833 clhits[1] = Int_t(newclust[5][i]);
834// Cluster Charge
835 clhits[2] = Int_t(newclust[0][i]);
836// Pad: ix
837 clhits[3] = Int_t(newclust[1][i]);
838// Pad: iy
839 clhits[4] = Int_t(newclust[2][i]);
840// Pad: charge
841 clhits[5] = Int_t(newclust[3][i]);
842// Pad: chamber sector
843 clhits[6] = Int_t(newclust[4][i]);
844
a9e2aefa 845 AddPadHit(clhits);
a897a37a 846 }
847 }
a897a37a 848}
849
a9e2aefa 850//----------------------------------------------------------------------
851
852void AliMUON::Digitise(Int_t nev,Int_t bgrEvent,Option_t *option,Option_t *opt,Text_t *filename)
a897a37a 853{
854 // keep galice.root for signal and name differently the file for
855 // background when add! otherwise the track info for signal will be lost !
856
a6f39961 857 static Bool_t first=kTRUE;
a9e2aefa 858 static TFile *file;
859 char *addBackground = strstr(option,"Add");
a897a37a 860
a9e2aefa 861 AliMUONChamber* iChamber;
862 AliMUONSegmentation* segmentation;
a897a37a 863
864
865 Int_t trk[50];
866 Int_t chtrk[50];
867 TObjArray *list=new TObjArray;
a9e2aefa 868 static TClonesArray *pAddress=0;
869 if(!pAddress) pAddress=new TClonesArray("TVector",1000);
a897a37a 870 Int_t digits[5];
871
a9e2aefa 872 AliMUON *pMUON = (AliMUON *) gAlice->GetModule("MUON");
873 AliMUONHitMap * hitMap[kNCH];
874 for (Int_t i=0; i<kNCH; i++) {hitMap[i]=0;}
875 if (addBackground ) {
a897a37a 876 if(first) {
877 fFileName=filename;
878 cout<<"filename"<<fFileName<<endl;
a9e2aefa 879 file=new TFile(fFileName);
a897a37a 880 cout<<"I have opened "<<fFileName<<" file "<<endl;
a9e2aefa 881 fHits2 = new TClonesArray("AliMUONHit",1000 );
882 fPadHits2 = new TClonesArray("AliMUONPadHit",10000);
a897a37a 883 }
a6f39961 884 first=kFALSE;
a9e2aefa 885 file->cd();
886 //file->ls();
a897a37a 887 // Get Hits Tree header from file
888 if(fHits2) fHits2->Clear();
a9e2aefa 889 if(fPadHits2) fPadHits2->Clear();
890 if(fTrH1) delete fTrH1;
891 fTrH1=0;
a897a37a 892
893 char treeName[20];
a9e2aefa 894 sprintf(treeName,"TreeH%d",bgrEvent);
895 fTrH1 = (TTree*)gDirectory->Get(treeName);
896 //printf("fTrH1 %p of treename %s for event %d \n",fTrH1,treeName,bgrEvent);
a897a37a 897
a9e2aefa 898 if (!fTrH1) {
899 printf("ERROR: cannot find Hits Tree for event:%d\n",bgrEvent);
a897a37a 900 }
901 // Set branch addresses
902 TBranch *branch;
903 char branchname[20];
904 sprintf(branchname,"%s",GetName());
a9e2aefa 905 if (fTrH1 && fHits2) {
906 branch = fTrH1->GetBranch(branchname);
a897a37a 907 if (branch) branch->SetAddress(&fHits2);
908 }
a9e2aefa 909 if (fTrH1 && fPadHits2) {
910 branch = fTrH1->GetBranch("MUONCluster");
911 if (branch) branch->SetAddress(&fPadHits2);
a897a37a 912 }
913// test
a9e2aefa 914 //Int_t ntracks1 =(Int_t)fTrH1->GetEntries();
a897a37a 915 //printf("background - ntracks1 - %d\n",ntracks1);
916 }
917 //
918 // loop over cathodes
919 //
920 AliMUONHitMap* hm;
921 Int_t countadr=0;
922 for (int icat=0; icat<2; icat++) {
a897a37a 923 Int_t counter=0;
a9e2aefa 924 for (Int_t i =0; i<kNCH; i++) {
925 iChamber=(AliMUONChamber*) (*fChambers)[i];
a897a37a 926 if (iChamber->Nsec()==1 && icat==1) {
fe4da5cc 927 continue;
a897a37a 928 } else {
a9e2aefa 929 segmentation=iChamber->SegmentationModel(icat+1);
fe4da5cc 930 }
a9e2aefa 931 hitMap[i] = new AliMUONHitMapA1(segmentation, list);
a897a37a 932 }
933 //printf("Start loop over tracks \n");
934//
935// Loop over tracks
936//
937
a9e2aefa 938 TTree *treeH = gAlice->TreeH();
939 Int_t ntracks =(Int_t) treeH->GetEntries();
940 Int_t nmuon[kNCH]={0,0,0,0,0,0,0,0,0,0,0,0,0,0};
941 Float_t xhit[kNCH][2];
942 Float_t yhit[kNCH][2];
a897a37a 943
944 for (Int_t track=0; track<ntracks; track++) {
945 gAlice->ResetHits();
a9e2aefa 946 treeH->GetEvent(track);
a897a37a 947
948//
949// Loop over hits
a9e2aefa 950 for(AliMUONHit* mHit=(AliMUONHit*)pMUON->FirstHit(-1);
a897a37a 951 mHit;
a9e2aefa 952 mHit=(AliMUONHit*)pMUON->NextHit())
a897a37a 953 {
954 Int_t nch = mHit->fChamber-1; // chamber number
a9e2aefa 955 if (nch > kNCH-1) continue;
956 iChamber = &(pMUON->Chamber(nch));
a897a37a 957 // new 17.07.99
a9e2aefa 958 if (addBackground) {
959
960 if (mHit->fParticle == kMuonPlus
961 || mHit->fParticle == kMuonMinus) {
962 xhit[nch][nmuon[nch]]=mHit->fX;
963 yhit[nch][nmuon[nch]]=mHit->fY;
964 nmuon[nch]++;
965 if (nmuon[nch] >2) printf("nmuon %d\n",nmuon[nch]);
966 }
fe4da5cc 967 }
a9e2aefa 968
a897a37a 969
970
971
972//
973// Loop over pad hits
a9e2aefa 974 for (AliMUONPadHit* mPad=
975 (AliMUONPadHit*)pMUON->FirstPad(mHit,fPadHits);
a897a37a 976 mPad;
a9e2aefa 977 mPad=(AliMUONPadHit*)pMUON->NextPad(fPadHits))
a897a37a 978 {
979 Int_t cathode = mPad->fCathode; // cathode number
980 Int_t ipx = mPad->fPadX; // pad number on X
981 Int_t ipy = mPad->fPadY; // pad number on Y
a9e2aefa 982 Int_t iqpad = Int_t(mPad->fQpad);// charge per pad
a897a37a 983//
984//
985
986 if (cathode != (icat+1)) continue;
987 // fill the info array
988 Float_t thex, they;
a9e2aefa 989 segmentation=iChamber->SegmentationModel(cathode);
a897a37a 990 segmentation->GetPadCxy(ipx,ipy,thex,they);
a9e2aefa 991// Float_t rpad=TMath::Sqrt(thex*thex+they*they);
992// if (rpad < rmin || iqpad ==0 || rpad > rmax) continue;
a897a37a 993
a9e2aefa 994 new((*pAddress)[countadr++]) TVector(2);
995 TVector &trinfo=*((TVector*) (*pAddress)[countadr-1]);
a897a37a 996 trinfo(0)=(Float_t)track;
997 trinfo(1)=(Float_t)iqpad;
998
999 digits[0]=ipx;
1000 digits[1]=ipy;
1001 digits[2]=iqpad;
1002 digits[3]=iqpad;
a9e2aefa 1003 if (mHit->fParticle == kMuonPlus ||
1004 mHit->fParticle == kMuonMinus) {
1005 digits[4]=mPad->fHitNumber;
a897a37a 1006 } else digits[4]=-1;
1007
a9e2aefa 1008 AliMUONTransientDigit* pdigit;
a897a37a 1009 // build the list of fired pads and update the info
a9e2aefa 1010 if (!hitMap[nch]->TestHit(ipx, ipy)) {
a897a37a 1011
1012 list->AddAtAndExpand(
a9e2aefa 1013 new AliMUONTransientDigit(nch,digits),counter);
a897a37a 1014
a9e2aefa 1015 hitMap[nch]->SetHit(ipx, ipy, counter);
a897a37a 1016 counter++;
a9e2aefa 1017 pdigit=(AliMUONTransientDigit*)list->At(list->GetLast());
a897a37a 1018 // list of tracks
1019 TObjArray *trlist=(TObjArray*)pdigit->TrackList();
1020 trlist->Add(&trinfo);
1021 } else {
a9e2aefa 1022 pdigit=(AliMUONTransientDigit*) hitMap[nch]->GetHit(ipx, ipy);
a897a37a 1023 // update charge
1024 (*pdigit).fSignal+=iqpad;
1025 (*pdigit).fPhysics+=iqpad;
1026 // update list of tracks
1027 TObjArray* trlist=(TObjArray*)pdigit->TrackList();
a9e2aefa 1028 Int_t lastEntry=trlist->GetLast();
1029 TVector *pTrack=(TVector*)trlist->At(lastEntry);
1030 TVector &ptrk=*pTrack;
1031 Int_t lastTrack=Int_t(ptrk(0));
1032 Int_t lastCharge=Int_t(ptrk(1));
1033 if (lastTrack==track) {
1034 lastCharge+=iqpad;
1035 trlist->RemoveAt(lastEntry);
1036 trinfo(0)=lastTrack;
1037 trinfo(1)=lastCharge;
1038 trlist->AddAt(&trinfo,lastEntry);
a897a37a 1039 } else {
1040 trlist->Add(&trinfo);
1041 }
1042 // check the track list
1043 Int_t nptracks=trlist->GetEntriesFast();
1044 if (nptracks > 2) {
1045 for (Int_t tr=0;tr<nptracks;tr++) {
a9e2aefa 1046 TVector *ppTrack=(TVector*)trlist->At(tr);
1047 TVector &pptrk=*ppTrack;
a897a37a 1048 trk[tr]=Int_t(pptrk(0));
1049 chtrk[tr]=Int_t(pptrk(1));
1050 }
1051 } // end if nptracks
1052 } // end if pdigit
1053 } //end loop over clusters
1054 } // hit loop
1055 } // track loop
a897a37a 1056
1057 // open the file with background
1058
a9e2aefa 1059 if (addBackground) {
1060 ntracks =(Int_t)fTrH1->GetEntries();
a897a37a 1061//
1062// Loop over tracks
1063//
1064 for (Int_t track=0; track<ntracks; track++) {
1065
1066 if (fHits2) fHits2->Clear();
a9e2aefa 1067 if (fPadHits2) fPadHits2->Clear();
a897a37a 1068
a9e2aefa 1069 fTrH1->GetEvent(track);
a897a37a 1070//
1071// Loop over hits
a9e2aefa 1072 AliMUONHit* mHit;
a897a37a 1073 for(int i=0;i<fHits2->GetEntriesFast();++i)
a9e2aefa 1074 {
1075 mHit=(AliMUONHit*) (*fHits2)[i];
a897a37a 1076 Int_t nch = mHit->fChamber-1; // chamber number
1077 if (nch >9) continue;
a9e2aefa 1078 iChamber = &(pMUON->Chamber(nch));
a897a37a 1079 Int_t rmin = (Int_t)iChamber->RInner();
1080 Int_t rmax = (Int_t)iChamber->ROuter();
1081 Float_t xbgr=mHit->fX;
1082 Float_t ybgr=mHit->fY;
a6f39961 1083 Bool_t cond=kFALSE;
a897a37a 1084
1085 for (Int_t imuon =0; imuon < nmuon[nch]; imuon++) {
1086 Float_t dist= (xbgr-xhit[nch][imuon])*(xbgr-xhit[nch][imuon])
1087 +(ybgr-yhit[nch][imuon])*(ybgr-yhit[nch][imuon]);
a6f39961 1088 if (dist<100) cond=kTRUE;
a897a37a 1089 }
1090 if (!cond) continue;
1091
1092//
1093// Loop over pad hits
a9e2aefa 1094 for (AliMUONPadHit* mPad=
1095 (AliMUONPadHit*)pMUON->FirstPad(mHit,fPadHits2);
a897a37a 1096 mPad;
a9e2aefa 1097 mPad=(AliMUONPadHit*)pMUON->NextPad(fPadHits2))
a897a37a 1098 {
a9e2aefa 1099 // mPad = (AliMUONPadHit*) (*fPadHits2)[j];
a897a37a 1100 Int_t cathode = mPad->fCathode; // cathode number
1101 Int_t ipx = mPad->fPadX; // pad number on X
1102 Int_t ipy = mPad->fPadY; // pad number on Y
a9e2aefa 1103 Int_t iqpad = Int_t(mPad->fQpad);// charge per pad
a897a37a 1104
1105 if (cathode != (icat+1)) continue;
a897a37a 1106 Float_t thex, they;
a9e2aefa 1107 segmentation=iChamber->SegmentationModel(cathode);
a897a37a 1108 segmentation->GetPadCxy(ipx,ipy,thex,they);
1109 Float_t rpad=TMath::Sqrt(thex*thex+they*they);
1110 if (rpad < rmin || iqpad ==0 || rpad > rmax) continue;
a9e2aefa 1111 new((*pAddress)[countadr++]) TVector(2);
1112 TVector &trinfo=*((TVector*) (*pAddress)[countadr-1]);
1113 trinfo(0)=-1; // tag background
1114 trinfo(1)=-1;
1115
a897a37a 1116 digits[0]=ipx;
1117 digits[1]=ipy;
1118 digits[2]=iqpad;
1119 digits[3]=0;
1120 digits[4]=-1;
a897a37a 1121
a9e2aefa 1122 AliMUONTransientDigit* pdigit;
1123 // build the list of fired pads and update the info
1124 if (!hitMap[nch]->TestHit(ipx, ipy)) {
1125 list->AddAtAndExpand(new AliMUONTransientDigit(nch,digits),counter);
1126
1127 hitMap[nch]->SetHit(ipx, ipy, counter);
a897a37a 1128 counter++;
1129
a9e2aefa 1130 pdigit=(AliMUONTransientDigit*)list->At(list->GetLast());
a897a37a 1131 // list of tracks
a9e2aefa 1132 TObjArray *trlist=(TObjArray*)pdigit->
1133 TrackList();
1134 trlist->Add(&trinfo);
a897a37a 1135 } else {
a9e2aefa 1136 pdigit=(AliMUONTransientDigit*) hitMap[nch]->GetHit(ipx, ipy);
a897a37a 1137 // update charge
1138 (*pdigit).fSignal+=iqpad;
a9e2aefa 1139
a897a37a 1140 // update list of tracks
a9e2aefa 1141 TObjArray* trlist=(TObjArray*)pdigit->
1142 TrackList();
1143 Int_t lastEntry=trlist->GetLast();
1144 TVector *pTrack=(TVector*)trlist->
1145 At(lastEntry);
1146 TVector &ptrk=*pTrack;
1147 Int_t lastTrack=Int_t(ptrk(0));
1148 if (lastTrack==-1) {
1149 continue;
1150 } else {
1151 trlist->Add(&trinfo);
1152 }
a897a37a 1153 // check the track list
a9e2aefa 1154 Int_t nptracks=trlist->GetEntriesFast();
1155 if (nptracks > 0) {
1156 for (Int_t tr=0;tr<nptracks;tr++) {
1157 TVector *ppTrack=(TVector*)trlist->At(tr);
1158 TVector &pptrk=*ppTrack;
1159 trk[tr]=Int_t(pptrk(0));
1160 chtrk[tr]=Int_t(pptrk(1));
1161 }
1162 } // end if nptracks
a897a37a 1163 } // end if pdigit
1164 } //end loop over clusters
1165 } // hit loop
1166 } // track loop
1167 //Int_t nentr2=list->GetEntriesFast();
1168 //printf(" \n counter2, nentr2 %d %d \n",counter,nentr2);
1169 TTree *fAli=gAlice->TreeK();
a9e2aefa 1170 TFile *file=NULL;
a897a37a 1171
1172 if (fAli) file =fAli->GetCurrentFile();
1173 file->cd();
a9e2aefa 1174 } // if addBackground
1175
a897a37a 1176 Int_t tracks[10];
1177 Int_t charges[10];
a897a37a 1178 Int_t nentries=list->GetEntriesFast();
a897a37a 1179
1180 for (Int_t nent=0;nent<nentries;nent++) {
a9e2aefa 1181 AliMUONTransientDigit *address=(AliMUONTransientDigit*)list->At(nent);
a897a37a 1182 if (address==0) continue;
1183 Int_t ich=address->fChamber;
1184 Int_t q=address->fSignal;
a9e2aefa 1185 iChamber=(AliMUONChamber*) (*fChambers)[ich];
1186//
1187// Digit Response (noise, threshold, saturation, ...)
1188// if (address->fPhysics !=0 ) address->fPhysics+=(Int_t)Noise;
1189 AliMUONResponse * response=iChamber->ResponseModel();
1190 q=response->DigitResponse(q);
1191
1192 if (!q) continue;
1193
a897a37a 1194 digits[0]=address->fPadX;
1195 digits[1]=address->fPadY;
1196 digits[2]=q;
1197 digits[3]=address->fPhysics;
1198 digits[4]=address->fHit;
a897a37a 1199
1200 TObjArray* trlist=(TObjArray*)address->TrackList();
1201 Int_t nptracks=trlist->GetEntriesFast();
1202 //printf("nptracks, trlist %d %p\n",nptracks,trlist);
1203
a9e2aefa 1204 // this was changed to accomodate the real number of tracks
1205 if (nptracks > 10) {
1206 cout<<"Attention - nptracks > 10 "<<nptracks<<endl;
1207 nptracks=10;
1208 }
1209 if (nptracks > 2) {
1210 printf("Attention - nptracks > 2 %d \n",nptracks);
1211 printf("cat,ich,ix,iy,q %d %d %d %d %d \n",icat,ich,digits[0],digits[1],q);
1212 }
1213 for (Int_t tr=0;tr<nptracks;tr++) {
1214 TVector *ppP=(TVector*)trlist->At(tr);
1215 if(!ppP ) printf("ppP - %p\n",ppP);
1216 TVector &pp =*ppP;
1217 tracks[tr]=Int_t(pp(0));
1218 charges[tr]=Int_t(pp(1));
a897a37a 1219 //printf("tracks, charges - %d %d\n",tracks[tr],charges[tr]);
a9e2aefa 1220 } //end loop over list of tracks for one pad
a897a37a 1221 // Sort list of tracks according to charge
a9e2aefa 1222 if (nptracks > 1) {
1223 SortTracks(tracks,charges,nptracks);
1224 }
1225 if (nptracks < 10 ) {
1226 for (Int_t i=nptracks; i<10; i++) {
1227 tracks[i]=0;
1228 charges[i]=0;
a897a37a 1229 }
a9e2aefa 1230 }
1231
a897a37a 1232 // fill digits
a9e2aefa 1233 pMUON->AddDigits(ich,tracks,charges,digits);
1234 // delete trlist;
a897a37a 1235 }
1236 //cout<<"I'm out of the loops for digitisation"<<endl;
a9e2aefa 1237 // gAlice->GetEvent(nev);
a897a37a 1238 gAlice->TreeD()->Fill();
a9e2aefa 1239 pMUON->ResetDigits();
a897a37a 1240 list->Delete();
a9e2aefa 1241
1242 for(Int_t ii=0;ii<kNCH;++ii) {
1243 if (hitMap[ii]) {
1244 hm=hitMap[ii];
a897a37a 1245 delete hm;
a9e2aefa 1246 hitMap[ii]=0;
fe4da5cc 1247 }
a897a37a 1248 }
a897a37a 1249 } //end loop over cathodes
a9e2aefa 1250
1251 char hname[30];
1252 sprintf(hname,"TreeD%d",nev);
1253 gAlice->TreeD()->Write(hname);
1254 // reset tree
1255 gAlice->TreeD()->Reset();
1256 delete list;
1257
1258 pAddress->Delete();
1259 // gObjectTable->Print();
a897a37a 1260}
1261
1262void AliMUON::SortTracks(Int_t *tracks,Int_t *charges,Int_t ntr)
1263{
1264 //
1265 // Sort the list of tracks contributing to a given digit
1266 // Only the 3 most significant tracks are acctually sorted
1267 //
1268
1269 //
1270 // Loop over signals, only 3 times
1271 //
1272
1273 Int_t qmax;
1274 Int_t jmax;
1275 Int_t idx[3] = {-2,-2,-2};
1276 Int_t jch[3] = {-2,-2,-2};
1277 Int_t jtr[3] = {-2,-2,-2};
1278 Int_t i,j,imax;
1279
1280 if (ntr<3) imax=ntr;
1281 else imax=3;
1282 for(i=0;i<imax;i++){
1283 qmax=0;
1284 jmax=0;
1285
1286 for(j=0;j<ntr;j++){
1287
1288 if((i == 1 && j == idx[i-1])
1289 ||(i == 2 && (j == idx[i-1] || j == idx[i-2]))) continue;
1290
1291 if(charges[j] > qmax) {
1292 qmax = charges[j];
1293 jmax=j;
1294 }
1295 }
1296
1297 if(qmax > 0) {
1298 idx[i]=jmax;
1299 jch[i]=charges[jmax];
1300 jtr[i]=tracks[jmax];
1301 }
1302
1303 }
1304
1305 for(i=0;i<3;i++){
1306 if (jtr[i] == -2) {
1307 charges[i]=0;
1308 tracks[i]=0;
1309 } else {
1310 charges[i]=jch[i];
1311 tracks[i]=jtr[i];
1312 }
1313 }
1314
fe4da5cc 1315}
1316
a9e2aefa 1317//___________________________________________
1318void AliMUON::Trigger(Int_t nev){
1319// call the Trigger Algorithm and fill TreeR
1320
1321 Int_t singlePlus[3] = {0,0,0};
1322 Int_t singleMinus[3] = {0,0,0};
1323 Int_t singleUndef[3] = {0,0,0};
1324 Int_t pairUnlike[3] = {0,0,0};
1325 Int_t pairLike[3] = {0,0,0};
1326
1327 ResetTrigger();
1328
1329 AliMUONTriggerDecision* decision= new AliMUONTriggerDecision(1);
1330 decision->Trigger();
1331 decision->GetGlobalTrigger(singlePlus, singleMinus, singleUndef,
1332 pairUnlike, pairLike);
1333// add a local trigger in the list
1334 AddGlobalTrigger(singlePlus, singleMinus, singleUndef, pairUnlike, pairLike);
9ae15266 1335 Int_t i;
a9e2aefa 1336
1337 for (Int_t icirc=0; icirc<kNTriggerCircuit; icirc++) {
9ae15266 1338 if(decision->GetITrigger(icirc)==1) {
1339 Int_t localtr[7]={0,0,0,0,0,0,0};
1340 Int_t loLpt[2]={0,0}; Int_t loHpt[2]={0,0}; Int_t loApt[2]={0,0};
1341 decision->GetLutOutput(icirc, loLpt, loHpt, loApt);
1342 localtr[0] = icirc;
1343 localtr[1] = decision->GetStripX11(icirc);
1344 localtr[2] = decision->GetDev(icirc);
1345 localtr[3] = decision->GetStripY11(icirc);
1346 for (i=0; i<2; i++) { // convert the Lut output in 1 digit
1347 localtr[4] = localtr[4]+Int_t(loLpt[i]*TMath::Power(2,i));
1348 localtr[5] = localtr[5]+Int_t(loHpt[i]*TMath::Power(2,i));
1349 localtr[6] = localtr[6]+Int_t(loApt[i]*TMath::Power(2,i));
1350 }
1351 AddLocalTrigger(localtr); // add a local trigger in the list
a897a37a 1352 }
a9e2aefa 1353 }
1354 delete decision;
a897a37a 1355
a9e2aefa 1356 gAlice->TreeR()->Fill();
1357 ResetTrigger();
a897a37a 1358 char hname[30];
1359 sprintf(hname,"TreeR%d",nev);
1360 gAlice->TreeR()->Write(hname);
1361 gAlice->TreeR()->Reset();
a9e2aefa 1362 printf("\n End of trigger for event %d", nev);
a897a37a 1363}
a897a37a 1364
a897a37a 1365
a9e2aefa 1366//____________________________________________
1367void AliMUON::FindClusters(Int_t nev,Int_t lastEntry)
1368{
1369 TClonesArray *dig1, *dig2;
1370 Int_t ndig, k;
1371 dig1 = new TClonesArray("AliMUONDigit",1000);
1372 dig2 = new TClonesArray("AliMUONDigit",1000);
1373 AliMUONDigit *digit;
a897a37a 1374//
a9e2aefa 1375// Loop on chambers and on cathode planes
a897a37a 1376//
a897a37a 1377
a9e2aefa 1378 for (Int_t ich=0;ich<10;ich++) {
1379 AliMUONChamber* iChamber=(AliMUONChamber*) (*fChambers)[ich];
1380 AliMUONClusterFinder* rec = iChamber->ReconstructionModel();
1381 gAlice->ResetDigits();
1382 gAlice->TreeD()->GetEvent(lastEntry);
1383 TClonesArray *muonDigits = this->DigitsAddress(ich);
1384 ndig=muonDigits->GetEntriesFast();
1385 printf("\n 1 Found %d digits in %p %d", ndig, muonDigits,ich);
1386 TClonesArray &lhits1 = *dig1;
1387 Int_t n=0;
1388 for (k=0; k<ndig; k++) {
1389 digit=(AliMUONDigit*) muonDigits->UncheckedAt(k);
1390 if (rec->TestTrack(digit->fTracks[0]))
1391 new(lhits1[n++]) AliMUONDigit(*digit);
1392 }
1393 gAlice->ResetDigits();
1394 gAlice->TreeD()->GetEvent(lastEntry+1);
1395 muonDigits = this->DigitsAddress(ich);
1396 ndig=muonDigits->GetEntriesFast();
1397 printf("\n 2 Found %d digits in %p %d", ndig, muonDigits, ich);
1398 TClonesArray &lhits2 = *dig2;
1399 n=0;
1400
1401 for (k=0; k<ndig; k++) {
1402 digit= (AliMUONDigit*) muonDigits->UncheckedAt(k);
1403 if (rec->TestTrack(digit->fTracks[0]))
1404 new(lhits2[n++]) AliMUONDigit(*digit);
a897a37a 1405 }
a897a37a 1406
a9e2aefa 1407 if (rec) {
1408 rec->SetDigits(dig1, dig2);
1409 rec->SetChamber(ich);
1410 rec->FindRawClusters();
1411 }
1412 dig1->Delete();
1413 dig2->Delete();
1414 } // for ich
1415 gAlice->TreeR()->Fill();
1416 ResetRawClusters();
1417 char hname[30];
1418 sprintf(hname,"TreeR%d",nev);
1419 gAlice->TreeR()->Write(hname);
1420 gAlice->TreeR()->Reset();
1421 printf("\n End of cluster finding for event %d", nev);
1422
1423 delete dig1;
1424 delete dig2;
1425 //gObjectTable->Print();
a897a37a 1426}
a9e2aefa 1427
a897a37a 1428
fe4da5cc 1429void AliMUON::Streamer(TBuffer &R__b)
1430{
1431 // Stream an object of class AliMUON.
a9e2aefa 1432 AliMUONChamber *iChamber;
1433 AliMUONTriggerCircuit *iTriggerCircuit;
1434 AliMUONSegmentation *segmentation;
1435 AliMUONResponse *response;
fe4da5cc 1436 TClonesArray *digitsaddress;
a897a37a 1437 TClonesArray *rawcladdress;
9ae15266 1438 Int_t i;
fe4da5cc 1439
9ae15266 1440 if (R__b.IsReading()) {
1441 Version_t R__v = R__b.ReadVersion(); if (R__v) { }
1442 AliDetector::Streamer(R__b);
1443 R__b >> fNPadHits;
1444 R__b >> fPadHits; // diff
1445 R__b >> fNLocalTrigger;
1446 R__b >> fLocalTrigger;
1447 R__b >> fNGlobalTrigger;
1448 R__b >> fGlobalTrigger;
1449 R__b >> fDchambers;
1450 R__b >> fRawClusters;
1451 R__b.ReadArray(fNdch);
1452 R__b.ReadArray(fNrawch);
1453 R__b >> fAccCut;
1454 R__b >> fAccMin;
1455 R__b >> fAccMax;
1456 R__b >> fChambers;
1457 R__b >> fTriggerCircuits;
1458 for (i =0; i<kNTriggerCircuit; i++) {
1459 iTriggerCircuit=(AliMUONTriggerCircuit*) (*fTriggerCircuits)[i];
1460 iTriggerCircuit->Streamer(R__b);
fe4da5cc 1461 }
9ae15266 1462// Stream chamber related information
1463 for (i =0; i<kNCH; i++) {
1464 iChamber=(AliMUONChamber*) (*fChambers)[i];
1465 iChamber->Streamer(R__b);
1466 if (iChamber->Nsec()==1) {
1467 segmentation=iChamber->SegmentationModel(1);
1468 if (segmentation)
1469 segmentation->Streamer(R__b);
1470 } else {
1471 segmentation=iChamber->SegmentationModel(1);
1472 if (segmentation)
1473 segmentation->Streamer(R__b);
1474 if (segmentation)
1475 segmentation=iChamber->SegmentationModel(2);
1476 segmentation->Streamer(R__b);
1477 }
1478 response=iChamber->ResponseModel();
1479 if (response)
1480 response->Streamer(R__b);
1481 digitsaddress=(TClonesArray*) (*fDchambers)[i];
1482 digitsaddress->Streamer(R__b);
1483 if (i < kNTrackingCh) {
1484 rawcladdress=(TClonesArray*) (*fRawClusters)[i];
1485 rawcladdress->Streamer(R__b);
1486 }
a9e2aefa 1487 }
9ae15266 1488
1489 } else {
1490 R__b.WriteVersion(AliMUON::IsA());
1491 AliDetector::Streamer(R__b);
1492 R__b << fNPadHits;
1493 R__b << fPadHits; // diff
1494 R__b << fNLocalTrigger;
1495 R__b << fLocalTrigger;
1496 R__b << fNGlobalTrigger;
1497 R__b << fGlobalTrigger;
1498 R__b << fDchambers;
1499 R__b << fRawClusters;
1500 R__b.WriteArray(fNdch, kNCH);
1501 R__b.WriteArray(fNrawch, kNTrackingCh);
1502
1503 R__b << fAccCut;
1504 R__b << fAccMin;
1505 R__b << fAccMax;
1506
1507 R__b << fChambers;
1508 R__b << fTriggerCircuits;
1509 for (i =0; i<kNTriggerCircuit; i++) {
1510 iTriggerCircuit=(AliMUONTriggerCircuit*) (*fTriggerCircuits)[i];
1511 iTriggerCircuit->Streamer(R__b);
fe4da5cc 1512 }
9ae15266 1513 for (i =0; i<kNCH; i++) {
1514 iChamber=(AliMUONChamber*) (*fChambers)[i];
1515 iChamber->Streamer(R__b);
1516 if (iChamber->Nsec()==1) {
1517 segmentation=iChamber->SegmentationModel(1);
1518 if (segmentation)
1519 segmentation->Streamer(R__b);
1520 } else {
1521 segmentation=iChamber->SegmentationModel(1);
1522 if (segmentation)
1523 segmentation->Streamer(R__b);
1524 segmentation=iChamber->SegmentationModel(2);
1525 if (segmentation)
1526 segmentation->Streamer(R__b);
1527 }
1528 response=iChamber->ResponseModel();
1529 if (response)
1530 response->Streamer(R__b);
1531 digitsaddress=(TClonesArray*) (*fDchambers)[i];
1532 digitsaddress->Streamer(R__b);
1533 if (i < kNTrackingCh) {
1534 rawcladdress=(TClonesArray*) (*fRawClusters)[i];
1535 rawcladdress->Streamer(R__b);
1536 }
a9e2aefa 1537 }
fe4da5cc 1538 }
fe4da5cc 1539}
a9e2aefa 1540AliMUONPadHit* AliMUON::FirstPad(AliMUONHit* hit, TClonesArray *clusters)
fe4da5cc 1541{
1542//
1543 // Initialise the pad iterator
1544 // Return the address of the first padhit for hit
a897a37a 1545 TClonesArray *theClusters = clusters;
fe4da5cc 1546 Int_t nclust = theClusters->GetEntriesFast();
1547 if (nclust && hit->fPHlast > 0) {
a9e2aefa 1548 AliMUON::fMaxIterPad=hit->fPHlast;
1549 AliMUON::fCurIterPad=hit->fPHfirst;
1550 return (AliMUONPadHit*) clusters->UncheckedAt(AliMUON::fCurIterPad-1);
fe4da5cc 1551 } else {
1552 return 0;
1553 }
1554}
1555
a9e2aefa 1556AliMUONPadHit* AliMUON::NextPad(TClonesArray *clusters)
fe4da5cc 1557{
a9e2aefa 1558 AliMUON::fCurIterPad++;
1559 if (AliMUON::fCurIterPad <= AliMUON::fMaxIterPad) {
1560 return (AliMUONPadHit*) clusters->UncheckedAt(AliMUON::fCurIterPad-1);
fe4da5cc 1561 } else {
1562 return 0;
1563 }
1564}
1565
a897a37a 1566
1567AliMUONRawCluster *AliMUON::RawCluster(Int_t ichamber, Int_t icathod, Int_t icluster)
1568{
a9e2aefa 1569 TClonesArray *muonRawCluster = RawClustAddress(ichamber);
a897a37a 1570 ResetRawClusters();
a9e2aefa 1571 TTree *treeR = gAlice->TreeR();
1572 Int_t nent=(Int_t)treeR->GetEntries();
1573 treeR->GetEvent(nent-2+icathod-1);
1574 //treeR->GetEvent(icathod);
1575 //Int_t nrawcl = (Int_t)muonRawCluster->GetEntriesFast();
a897a37a 1576
a9e2aefa 1577 AliMUONRawCluster * mRaw = (AliMUONRawCluster*)muonRawCluster->UncheckedAt(icluster);
a897a37a 1578 //printf("RawCluster _ nent nrawcl icluster mRaw %d %d %d%p\n",nent,nrawcl,icluster,mRaw);
1579
1580 return mRaw;
1581}
1582
a9e2aefa 1583AliMUON& AliMUON::operator = (const AliMUON& rhs)
a897a37a 1584{
a9e2aefa 1585// copy operator
1586// dummy version
1587 return *this;
a897a37a 1588}
1589
1590
1591
a897a37a 1592
1593
fe4da5cc 1594
fe4da5cc 1595
fe4da5cc 1596
fe4da5cc 1597
1598
1599
1600
1601
1602
1603
1604
1605
1606
1607