1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
17 Revision 1.29 2000/07/28 13:49:38 morsch
18 SetAcceptance defines inner and outer chamber radii according to angular acceptance.
19 Can be used for simple acceptance studies.
21 Revision 1.28 2000/07/22 16:43:15 morsch
22 Same comment as before, but now done correctly I hope (sorry it's Saturday evening)
24 Revision 1.27 2000/07/22 16:36:50 morsch
25 Change order of indices in creation (new) of xhit and yhit
27 Revision 1.26 2000/07/03 11:54:57 morsch
28 AliMUONSegmentation and AliMUONHitMap have been replaced by AliSegmentation and AliHitMap in STEER
29 The methods GetPadIxy and GetPadXxy of AliMUONSegmentation have changed name to GetPadI and GetPadC.
31 Revision 1.25 2000/06/29 12:34:09 morsch
32 AliMUONSegmentation class has been made independent of AliMUONChamber. This makes
33 it usable with any other geometry class. The link to the object to which it belongs is
34 established via an index. This assumes that there exists a global geometry manager
35 from which the pointer to the parent object can be obtained (in our case gAlice).
37 Revision 1.24 2000/06/28 15:16:35 morsch
38 (1) Client code adapted to new method signatures in AliMUONSegmentation (see comments there)
39 to allow development of slat-muon chamber simulation and reconstruction code in the MUON
40 framework. The changes should have no side effects (mostly dummy arguments).
41 (2) Hit disintegration uses 3-dim hit coordinates to allow simulation
42 of chambers with overlapping modules (MakePadHits, Disintegration).
44 Revision 1.23 2000/06/28 12:19:17 morsch
45 More consequent seperation of global input data services (AliMUONClusterInput singleton) and the
46 cluster and hit reconstruction algorithms in AliMUONClusterFinderVS.
47 AliMUONClusterFinderVS becomes the base class for clustering and hit reconstruction.
48 It requires two cathode planes. Small modifications in the code will make it usable for
49 one cathode plane and, hence, more general (for test beam data).
50 AliMUONClusterFinder is now obsolete.
52 Revision 1.22 2000/06/28 08:06:10 morsch
53 Avoid global variables in AliMUONClusterFinderVS by seperating the input data for the fit from the
54 algorithmic part of the class. Input data resides inside the AliMUONClusterInput singleton.
55 It also naturally takes care of the TMinuit instance.
57 Revision 1.21 2000/06/27 08:54:41 morsch
58 Problems with on constant array sizes (in hitMap, nmuon, xhit, yhit) corrected.
60 Revision 1.20 2000/06/26 14:02:38 morsch
61 Add class AliMUONConstants with MUON specific constants using static memeber data and access methods.
63 Revision 1.19 2000/06/22 13:40:51 morsch
64 scope problem on HP, "i" declared once
65 pow changed to TMath::Power (PH, AM)
67 Revision 1.18 2000/06/15 07:58:48 morsch
68 Code from MUON-dev joined
70 Revision 1.14.4.17 2000/06/14 14:36:46 morsch
71 - add TriggerCircuit (PC)
72 - add GlobalTrigger and LocalTrigger and specific methods (PC)
74 Revision 1.14.4.16 2000/06/09 21:20:28 morsch
75 Most coding rule violations corrected
77 Revision 1.14.4.15 2000/05/02 09:54:32 morsch
78 RULE RN17 violations corrected
80 Revision 1.14.4.12 2000/04/26 12:25:02 morsch
81 Code revised by P. Crochet:
82 - Z position of TriggerChamber changed according to A.Tournaire Priv.Comm.
83 - ToF included in the method MakePadHits
84 - inner radius of flange between beam shielding and trigger corrected
85 - Trigger global volume updated (according to the new geometry)
87 Revision 1.14.4.11 2000/04/19 19:42:08 morsch
88 Some changes of variable names curing viols and methods concerning
89 correlated clusters removed.
91 Revision 1.14.4.10 2000/03/22 16:44:07 gosset
92 Memory leak suppressed in function Digitise:
93 p_adr->Delete() instead of Clear (I.Chevrot and A.Baldisseri)
95 Revision 1.14.4.9 2000/03/20 18:15:25 morsch
96 Positions of trigger chambers corrected (P.C.)
98 Revision 1.14.4.8 2000/02/21 15:38:01 morsch
99 Call to AddHitList introduced to make this version compatible with head.
101 Revision 1.14.4.7 2000/02/20 07:45:53 morsch
102 Bugs in Trigger part of BuildGeomemetry corrected (P.C)
104 Revision 1.14.4.6 2000/02/17 14:28:54 morsch
105 Trigger included into initialization and digitization
107 Revision 1.14.4.5 2000/02/15 10:02:58 morsch
108 Log messages of previous revisions added
110 Revision 1.14.4.2 2000/02/04 10:57:34 gosset
111 Z position of the chambers:
112 it was the Z position of the stations;
113 it is now really the Z position of the chambers.
114 !!!! WARNING: THE CALLS TO "AliMUONChamber::SetZPOS"
115 !!!! AND "AliMUONChamber::ZPosition"
116 !!!! HAVE TO BE CHANGED TO "AliMUONChamber::"SetZ"
117 !!!! AND "AliMUONChamber::Z"
119 Revision 1.14.4.3 2000/02/04 16:19:04 gosset
120 Correction for mis-spelling of NCH
122 Revision 1.14.4.4 2000/02/15 09:43:38 morsch
128 ///////////////////////////////////////////////
129 // Manager and hits classes for set:MUON //
130 ////////////////////////////////////////////////
134 #include <TRotMatrix.h>
140 #include <TObjArray.h>
142 #include <TParticle.h>
148 #include <TDirectory.h>
149 #include <TObjectTable.h>
154 #include "AliMUONHit.h"
155 #include "AliMUONPadHit.h"
156 #include "AliMUONDigit.h"
157 #include "AliMUONTransientDigit.h"
158 #include "AliMUONRawCluster.h"
159 #include "AliMUONLocalTrigger.h"
160 #include "AliMUONGlobalTrigger.h"
161 #include "AliMUONTriggerCircuit.h"
162 #include "AliHitMap.h"
163 #include "AliMUONHitMapA1.h"
164 #include "AliMUONChamberTrigger.h"
165 #include "AliMUONConstants.h"
166 #include "AliMUONClusterFinderVS.h"
167 #include "AliMUONTriggerDecision.h"
170 #include "AliMUONClusterInput.h"
171 #include "iostream.h"
172 #include "AliCallf77.h"
173 #include "AliConst.h"
175 // Defaults parameters for Z positions of chambers
176 // taken from values for "stations" in AliMUON::AliMUON
177 // const Float_t zch[7]={528, 690., 975., 1249., 1449., 1610, 1710.};
178 // and from array "dstation" in AliMUONv1::CreateGeometry
179 // Float_t dstation[5]={20., 20., 20, 20., 20.};
180 // for tracking chambers,
181 // according to (Z1 = zch - dstation) and (Z2 = zch + dstation)
182 // for the first and second chambers in the station, respectively,
183 // and from "DTPLANES" in AliMUONv1::CreateGeometry
184 // const Float_t DTPLANES = 15.;
185 // for trigger chambers,
186 // according to (Z1 = zch) and (Z2 = zch + DTPLANES)
187 // for the first and second chambers in the station, respectively
190 //___________________________________________
198 fTriggerCircuits = 0; // cp new design of AliMUONTriggerDecision
211 //___________________________________________
212 AliMUON::AliMUON(const char *name, const char *title)
213 : AliDetector(name,title)
217 <img src="gif/alimuon.gif">
221 fHits = new TClonesArray("AliMUONHit",1000);
222 gAlice->AddHitList(fHits);
223 fPadHits = new TClonesArray("AliMUONPadHit",10000);
227 fNdch = new Int_t[AliMUONConstants::NCh()];
229 fDchambers = new TObjArray(AliMUONConstants::NCh());
233 for (i=0; i<AliMUONConstants::NCh() ;i++) {
234 (*fDchambers)[i] = new TClonesArray("AliMUONDigit",10000);
238 fNrawch = new Int_t[AliMUONConstants::NTrackingCh()];
240 fRawClusters = new TObjArray(AliMUONConstants::NTrackingCh());
242 for (i=0; i<AliMUONConstants::NTrackingCh();i++) {
243 (*fRawClusters)[i] = new TClonesArray("AliMUONRawCluster",10000);
247 fGlobalTrigger = new TClonesArray("AliMUONGlobalTrigger",1);
249 fLocalTrigger = new TClonesArray("AliMUONLocalTrigger",234);
252 SetMarkerColor(kRed);
260 fChambers = new TObjArray(AliMUONConstants::NCh());
262 // Loop over stations
263 for (Int_t st = 0; st < AliMUONConstants::NCh() / 2; st++) {
264 // Loop over 2 chambers in the station
265 for (Int_t stCH = 0; stCH < 2; stCH++) {
268 // Default Parameters for Muon Tracking Stations
273 if (ch < AliMUONConstants::NTrackingCh()) {
274 (*fChambers)[ch] = new AliMUONChamber(ch);
276 (*fChambers)[ch] = new AliMUONChamberTrigger(ch);
279 AliMUONChamber* chamber = (AliMUONChamber*) (*fChambers)[ch];
282 // Default values for Z of chambers
283 chamber->SetZ(AliMUONConstants::DefaultChamberZ(ch));
285 chamber->InitGeo(AliMUONConstants::DefaultChamberZ(ch));
286 // Set chamber inner and outer radius to default
287 chamber->SetRInner(AliMUONConstants::Dmin(st)/2);
288 chamber->SetROuter(AliMUONConstants::Dmax(st)/2);
290 } // Chamber stCH (0, 1) in
291 } // Station st (0...)
304 // cp new design of AliMUONTriggerDecision
305 fTriggerCircuits = new TObjArray(AliMUONConstants::NTriggerCircuit());
306 for (Int_t circ=0; circ<AliMUONConstants::NTriggerCircuit(); circ++) {
307 (*fTriggerCircuits)[circ] = new AliMUONTriggerCircuit();
309 // cp new design of AliMUONTriggerDecision
313 //___________________________________________
314 AliMUON::AliMUON(const AliMUON& rMUON)
316 // Dummy copy constructor
323 printf("Calling AliMUON destructor !!!\n");
330 delete fGlobalTrigger;
333 delete fLocalTrigger;
336 for (i=0;i<AliMUONConstants::NCh();i++) {
337 delete (*fDchambers)[i];
342 for (i=0;i<AliMUONConstants::NTrackingCh();i++) {
343 delete (*fRawClusters)[i];
348 for (Int_t circ=0; circ<AliMUONConstants::NTriggerCircuit(); circ++) {
349 delete (*fTriggerCircuits)[circ];
351 delete fTriggerCircuits;
354 //___________________________________________
355 void AliMUON::AddHit(Int_t track, Int_t *vol, Float_t *hits)
357 TClonesArray &lhits = *fHits;
358 new(lhits[fNhits++]) AliMUONHit(fIshunt,track,vol,hits);
360 //___________________________________________
361 void AliMUON::AddPadHit(Int_t *clhits)
363 TClonesArray &lclusters = *fPadHits;
364 new(lclusters[fNPadHits++]) AliMUONPadHit(clhits);
366 //_____________________________________________________________________________
367 void AliMUON::AddDigits(Int_t id, Int_t *tracks, Int_t *charges, Int_t *digits)
370 // Add a MUON digit to the list
373 TClonesArray &ldigits = *((TClonesArray*)(*fDchambers)[id]);
374 new(ldigits[fNdch[id]++]) AliMUONDigit(tracks,charges,digits);
377 //_____________________________________________________________________________
378 void AliMUON::AddRawCluster(Int_t id, const AliMUONRawCluster& c)
381 // Add a MUON digit to the list
384 TClonesArray &lrawcl = *((TClonesArray*)(*fRawClusters)[id]);
385 new(lrawcl[fNrawch[id]++]) AliMUONRawCluster(c);
388 //___________________________________________
389 void AliMUON::AddGlobalTrigger(Int_t *singlePlus, Int_t *singleMinus,
391 Int_t *pairUnlike, Int_t *pairLike)
393 // add a MUON Global Trigger to the list (only one GlobalTrigger per event !)
394 TClonesArray &globalTrigger = *fGlobalTrigger;
395 new(globalTrigger[fNGlobalTrigger++])
396 AliMUONGlobalTrigger(singlePlus, singleMinus, singleUndef, pairUnlike,
399 //___________________________________________
400 void AliMUON::AddLocalTrigger(Int_t *localtr)
402 // add a MUON Local Trigger to the list
403 TClonesArray &localTrigger = *fLocalTrigger;
404 new(localTrigger[fNLocalTrigger++]) AliMUONLocalTrigger(localtr);
407 //___________________________________________
408 void AliMUON::BuildGeometry()
410 TNode *node, *nodeF, *top, *nodeS;
411 const int kColorMUON = kBlue;
412 const int kColorMUON2 = kGreen;
414 top=gAlice->GetGeometry()->GetNode("alice");
417 // z-Positions of Chambers
418 const Float_t kCz[7]={511., 686., 971., 1245., 1445., 1600, 1700.};
419 // inner diameter (Xlenght for trigger chamber -> active area)
420 const Float_t kDmin[7]={ 35., 47., 67., 86., 100., 544., 544.};
421 // outer diameter (Ylenght for trigger chamber -> active area)
422 const Float_t kDmax[7]={183., 245., 346., 520., 520., 612., 612.};
424 TRotMatrix* rot000 = new TRotMatrix("Rot000"," ", 90, 0, 90, 90, 0, 0);
425 TRotMatrix* rot090 = new TRotMatrix("Rot090"," ", 90, 90, 90,180, 0, 0);
426 TRotMatrix* rot180 = new TRotMatrix("Rot180"," ", 90,180, 90,270, 0, 0);
427 TRotMatrix* rot270 = new TRotMatrix("Rot270"," ", 90,270, 90, 0, 0, 0);
429 Float_t rmin, rmax, dx, dy, dz, dr, xpos, ypos, zpos;
430 Float_t dzc1=4.; // tracking chambers
431 Float_t dzc2=15.; // trigger chambers
432 Float_t hole=102.; // x-y hole around beam pipe for trig. chambers
433 Float_t zscale; // scaling parameter trigger chambers
434 Float_t halfx, halfy;
435 char nameChamber[9], nameSense[9], nameFrame[9], nameNode[8];
436 char nameSense1[9], nameSense2[9];
437 for (Int_t i=0; i<7; i++) {
438 for (Int_t j=0; j<2; j++) {
440 if (i<5) { // tracking chambers
453 sprintf(nameChamber,"C_MUON%d",id);
454 sprintf(nameSense,"S_MUON%d",id);
455 sprintf(nameSense1,"S1_MUON%d",id);
456 sprintf(nameSense2,"S2_MUON%d",id);
457 sprintf(nameFrame,"F_MUON%d",id);
458 if (i<5) { // tracking chambers
459 rmin = kDmin[i]/2.-3;
460 rmax = kDmax[i]/2.+3;
461 new TTUBE(nameChamber,"Mother","void",rmin,rmax,0.25,1.);
464 new TTUBE(nameSense,"Sens. region","void",rmin,rmax,0.25, 1.);
468 TBRIK* frMUON = new TBRIK(nameFrame,"Frame","void",dx,dy,dz);
470 sprintf(nameNode,"MUON%d",100+id);
471 node = new TNode(nameNode,"ChamberNode",nameChamber,0,0,zpos,"");
472 node->SetLineColor(kColorMUON);
475 sprintf(nameNode,"MUON%d",200+id);
476 node = new TNode(nameNode,"Sens. Region Node",nameSense,0,0,0,"");
477 node->SetLineColor(kColorMUON);
480 sprintf(nameNode,"MUON%d",300+id);
481 nodeF = new TNode(nameNode,"Frame0",frMUON,dr, 0, 0,rot000,"");
482 nodeF->SetLineColor(kColorMUON);
484 sprintf(nameNode,"MUON%d",400+id);
485 nodeF = new TNode(nameNode,"Frame1",frMUON,0 ,dr,0,rot090,"");
486 nodeF->SetLineColor(kColorMUON);
488 sprintf(nameNode,"MUON%d",500+id);
489 nodeF = new TNode(nameNode,"Frame2",frMUON,-dr,0,0,rot180,"");
490 nodeF->SetLineColor(kColorMUON);
492 sprintf(nameNode,"MUON%d",600+id);
493 nodeF = new TNode(nameNode,"Frame3",frMUON,0,-dr,0,rot270,"");
494 nodeF->SetLineColor(kColorMUON);
497 Float_t xsize=kDmin[i]*zscale;
498 Float_t ysize=kDmax[i]*zscale;
499 Float_t holeScaled=hole*zscale;
503 new TBRIK(nameChamber,"Mother","void",halfx,halfy,0.25);
505 sprintf(nameNode,"MUON%d",100+id);
506 node = new TNode(nameNode,"Chambernode",nameChamber,0,0,zpos,"");
507 node->SetLineColor(kColorMUON2);
510 // up/down of beam pipe
512 halfy=(ysize/2.-holeScaled/2.)/2.;
513 new TBRIK(nameSense,"Sens. region","void",halfx,halfy,0.25);
516 ypos=holeScaled/2.+((ysize/2.-holeScaled/2.)/2.);
517 sprintf(nameNode,"MUON%d",200+id);
518 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense,0,ypos,0,"");
519 nodeS->SetLineColor(kColorMUON2);
523 sprintf(nameNode,"MUON%d",300+id);
524 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense,0,ypos,0,"");
525 nodeS->SetLineColor(kColorMUON2);
527 // left/right of beam pipe
528 halfx=(xsize/2.-holeScaled/2.)/2.;
530 new TBRIK(nameSense1,"Sens. region","void",halfx,halfy,0.25);
533 xpos=holeScaled/2.+((xsize/2.-holeScaled/2.)/2.);
534 sprintf(nameNode,"MUON%d",400+id);
535 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense1,xpos,0,0,"");
536 nodeS->SetLineColor(kColorMUON2);
540 sprintf(nameNode,"MUON%d",500+id);
541 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense1,xpos,0,0,"");
542 nodeS->SetLineColor(kColorMUON2);
547 new TBRIK(nameSense2,"Sens. region","void",halfx,halfy,0.25);
550 xpos=holeScaled/2.-halfx;
552 sprintf(nameNode,"MUON%d",600+id);
553 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
554 nodeS->SetLineColor(kColorMUON2);
558 sprintf(nameNode,"MUON%d",700+id);
559 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
560 nodeS->SetLineColor(kColorMUON2);
564 sprintf(nameNode,"MUON%d",800+id);
565 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
566 nodeS->SetLineColor(kColorMUON2);
570 sprintf(nameNode,"MUON%d",900+id);
571 nodeS = new TNode(nameNode,"Sens. Region Node",nameSense2,xpos,ypos,0,"");
572 nodeS->SetLineColor(kColorMUON2);
579 //___________________________________________
580 Int_t AliMUON::DistancetoPrimitive(Int_t , Int_t )
585 //___________________________________________
586 void AliMUON::MakeBranch(Option_t* option)
588 // Create Tree branches for the MUON.
589 const Int_t kBufferSize = 4000;
591 sprintf(branchname,"%sCluster",GetName());
593 AliDetector::MakeBranch(option);
595 if (fPadHits && gAlice->TreeH()) {
596 gAlice->TreeH()->Branch(branchname,&fPadHits, kBufferSize);
597 printf("Making Branch %s for clusters\n",branchname);
600 // one branch for digits per chamber
603 for (i=0; i<AliMUONConstants::NCh() ;i++) {
604 sprintf(branchname,"%sDigits%d",GetName(),i+1);
606 if (fDchambers && gAlice->TreeD()) {
607 gAlice->TreeD()->Branch(branchname,&((*fDchambers)[i]), kBufferSize);
608 printf("Making Branch %s for digits in chamber %d\n",branchname,i+1);
612 printf("Make Branch - TreeR address %p\n",gAlice->TreeR());
614 // one branch for raw clusters per chamber
615 for (i=0; i<AliMUONConstants::NTrackingCh() ;i++) {
616 sprintf(branchname,"%sRawClusters%d",GetName(),i+1);
618 if (fRawClusters && gAlice->TreeR()) {
619 gAlice->TreeR()->Branch(branchname,&((*fRawClusters)[i]), kBufferSize);
620 printf("Making Branch %s for raw clusters in chamber %d\n",branchname,i+1);
624 // one branch for global trigger
625 sprintf(branchname,"%sGlobalTrigger",GetName());
626 if (fGlobalTrigger && gAlice->TreeR()) {
627 gAlice->TreeR()->Branch(branchname,&fGlobalTrigger,kBufferSize);
628 printf("Making Branch %s for Global Trigger\n",branchname);
630 // one branch for local trigger
631 sprintf(branchname,"%sLocalTrigger",GetName());
632 if (fLocalTrigger && gAlice->TreeR()) {
633 gAlice->TreeR()->Branch(branchname,&fLocalTrigger,kBufferSize);
634 printf("Making Branch %s for Local Trigger\n",branchname);
639 //___________________________________________
640 void AliMUON::SetTreeAddress()
642 // Set branch address for the Hits and Digits Tree.
644 AliDetector::SetTreeAddress();
647 TTree *treeH = gAlice->TreeH();
648 TTree *treeD = gAlice->TreeD();
649 TTree *treeR = gAlice->TreeR();
653 branch = treeH->GetBranch("MUONCluster");
654 if (branch) branch->SetAddress(&fPadHits);
659 for (int i=0; i<AliMUONConstants::NCh(); i++) {
660 sprintf(branchname,"%sDigits%d",GetName(),i+1);
662 branch = treeD->GetBranch(branchname);
663 if (branch) branch->SetAddress(&((*fDchambers)[i]));
668 // printf("SetTreeAddress --- treeR address %p \n",treeR);
671 for (int i=0; i<AliMUONConstants::NTrackingCh(); i++) {
672 sprintf(branchname,"%sRawClusters%d",GetName(),i+1);
674 branch = treeR->GetBranch(branchname);
675 if (branch) branch->SetAddress(&((*fRawClusters)[i]));
680 branch = treeR->GetBranch("MUONLocalTrigger");
681 if (branch) branch->SetAddress(&fLocalTrigger);
683 if (fGlobalTrigger) {
684 branch = treeR->GetBranch("MUONGlobalTrigger");
685 if (branch) branch->SetAddress(&fGlobalTrigger);
689 //___________________________________________
690 void AliMUON::ResetHits()
692 // Reset number of clusters and the cluster array for this detector
693 AliDetector::ResetHits();
695 if (fPadHits) fPadHits->Clear();
698 //____________________________________________
699 void AliMUON::ResetDigits()
702 // Reset number of digits and the digits array for this detector
704 for ( int i=0;i<AliMUONConstants::NCh();i++ ) {
705 if ((*fDchambers)[i]) ((TClonesArray*)(*fDchambers)[i])->Clear();
706 if (fNdch) fNdch[i]=0;
709 //____________________________________________
710 void AliMUON::ResetRawClusters()
713 // Reset number of raw clusters and the raw clust array for this detector
715 for ( int i=0;i<AliMUONConstants::NTrackingCh();i++ ) {
716 if ((*fRawClusters)[i]) ((TClonesArray*)(*fRawClusters)[i])->Clear();
717 if (fNrawch) fNrawch[i]=0;
721 //____________________________________________
722 void AliMUON::ResetTrigger()
724 // Reset Local and Global Trigger
726 if (fGlobalTrigger) fGlobalTrigger->Clear();
728 if (fLocalTrigger) fLocalTrigger->Clear();
731 //____________________________________________
732 void AliMUON::SetPadSize(Int_t id, Int_t isec, Float_t p1, Float_t p2)
735 ((AliMUONChamber*) (*fChambers)[i]) ->SetPadSize(isec,p1,p2);
736 ((AliMUONChamber*) (*fChambers)[i+1])->SetPadSize(isec,p1,p2);
739 //___________________________________________
740 void AliMUON::SetChambersZ(const Float_t *Z)
742 // Set Z values for all chambers (tracking and trigger)
743 // from the array pointed to by "Z"
744 for (Int_t ch = 0; ch < AliMUONConstants::NCh(); ch++)
745 ((AliMUONChamber*) ((*fChambers)[ch]))->SetZ(Z[ch]);
749 //___________________________________________
750 void AliMUON::SetChambersZToDefault()
752 // Set Z values for all chambers (tracking and trigger)
754 SetChambersZ(AliMUONConstants::DefaultChamberZ());
758 //___________________________________________
759 void AliMUON::SetChargeSlope(Int_t id, Float_t p1)
762 ((AliMUONChamber*) (*fChambers)[i])->SetChargeSlope(p1);
763 ((AliMUONChamber*) (*fChambers)[i+1])->SetChargeSlope(p1);
766 //___________________________________________
767 void AliMUON::SetChargeSpread(Int_t id, Float_t p1, Float_t p2)
770 ((AliMUONChamber*) (*fChambers)[i])->SetChargeSpread(p1,p2);
771 ((AliMUONChamber*) (*fChambers)[i+1])->SetChargeSpread(p1,p2);
774 //___________________________________________
775 void AliMUON::SetSigmaIntegration(Int_t id, Float_t p1)
778 ((AliMUONChamber*) (*fChambers)[i])->SetSigmaIntegration(p1);
779 ((AliMUONChamber*) (*fChambers)[i+1])->SetSigmaIntegration(p1);
782 //___________________________________________
783 void AliMUON::SetMaxAdc(Int_t id, Int_t p1)
786 ((AliMUONChamber*) (*fChambers)[i])->SetMaxAdc(p1);
787 ((AliMUONChamber*) (*fChambers)[i+1])->SetMaxAdc(p1);
790 //___________________________________________
791 void AliMUON::SetMaxStepGas(Float_t p1)
796 //___________________________________________
797 void AliMUON::SetMaxStepAlu(Float_t p1)
802 //___________________________________________
803 void AliMUON::SetMaxDestepGas(Float_t p1)
808 //___________________________________________
809 void AliMUON::SetMaxDestepAlu(Float_t p1)
813 //___________________________________________
814 void AliMUON::SetAcceptance(Bool_t acc, Float_t angmin, Float_t angmax)
817 fAccMin=angmin*TMath::Pi()/180;
818 fAccMax=angmax*TMath::Pi()/180;
821 for (Int_t st = 0; st < AliMUONConstants::NCh() / 2; st++) {
822 // Loop over 2 chambers in the station
823 for (Int_t stCH = 0; stCH < 2; stCH++) {
825 // Set chamber inner and outer radius according to acceptance cuts
826 Chamber(ch).SetRInner(AliMUONConstants::DefaultChamberZ(ch)*TMath::Tan(fAccMin));
827 Chamber(ch).SetROuter(AliMUONConstants::DefaultChamberZ(ch)*TMath::Tan(fAccMax));
832 //___________________________________________
833 void AliMUON::SetSegmentationModel(Int_t id, Int_t isec, AliSegmentation *segmentation)
835 ((AliMUONChamber*) (*fChambers)[id])->SetSegmentationModel(isec, segmentation);
838 //___________________________________________
839 void AliMUON::SetResponseModel(Int_t id, AliMUONResponse *response)
841 ((AliMUONChamber*) (*fChambers)[id])->SetResponseModel(response);
844 void AliMUON::SetReconstructionModel(Int_t id, AliMUONClusterFinderVS *reconst)
846 ((AliMUONChamber*) (*fChambers)[id])->SetReconstructionModel(reconst);
849 void AliMUON::SetNsec(Int_t id, Int_t nsec)
851 ((AliMUONChamber*) (*fChambers)[id])->SetNsec(nsec);
855 //___________________________________________
859 void AliMUON::MakePadHits(Float_t xhit,Float_t yhit, Float_t zhit,
860 Float_t eloss, Float_t tof, Int_t idvol)
863 // Calls the charge disintegration method of the current chamber and adds
864 // the simulated cluster to the root treee
867 Float_t newclust[6][500];
872 // Integrated pulse height on chamber
878 ((AliMUONChamber*) (*fChambers)[idvol])
879 ->DisIntegration(eloss, tof, xhit, yhit, zhit, nnew, newclust);
884 for (Int_t i=0; i<nnew; i++) {
885 if (Int_t(newclust[3][i]) > 0) {
888 clhits[1] = Int_t(newclust[5][i]);
890 clhits[2] = Int_t(newclust[0][i]);
892 clhits[3] = Int_t(newclust[1][i]);
894 clhits[4] = Int_t(newclust[2][i]);
896 clhits[5] = Int_t(newclust[3][i]);
897 // Pad: chamber sector
898 clhits[6] = Int_t(newclust[4][i]);
905 //----------------------------------------------------------------------
907 void AliMUON::Digitise(Int_t nev,Int_t bgrEvent,Option_t *option,Option_t *opt,Text_t *filename)
909 // keep galice.root for signal and name differently the file for
910 // background when add! otherwise the track info for signal will be lost !
912 static Bool_t first=kTRUE;
914 char *addBackground = strstr(option,"Add");
917 AliMUONChamber* iChamber;
918 AliSegmentation* segmentation;
923 TObjArray *list=new TObjArray;
924 static TClonesArray *pAddress=0;
925 if(!pAddress) pAddress=new TClonesArray("TVector",1000);
928 AliMUON *pMUON = (AliMUON *) gAlice->GetModule("MUON");
929 AliHitMap** hitMap= new AliHitMap* [AliMUONConstants::NCh()];
930 for (Int_t i=0; i<AliMUONConstants::NCh(); i++) {hitMap[i]=0;}
931 if (addBackground ) {
934 cout<<"filename"<<fFileName<<endl;
935 file=new TFile(fFileName);
936 cout<<"I have opened "<<fFileName<<" file "<<endl;
937 fHits2 = new TClonesArray("AliMUONHit",1000 );
938 fPadHits2 = new TClonesArray("AliMUONPadHit",10000);
943 // Get Hits Tree header from file
944 if(fHits2) fHits2->Clear();
945 if(fPadHits2) fPadHits2->Clear();
946 if(fTrH1) delete fTrH1;
950 sprintf(treeName,"TreeH%d",bgrEvent);
951 fTrH1 = (TTree*)gDirectory->Get(treeName);
952 //printf("fTrH1 %p of treename %s for event %d \n",fTrH1,treeName,bgrEvent);
955 printf("ERROR: cannot find Hits Tree for event:%d\n",bgrEvent);
957 // Set branch addresses
960 sprintf(branchname,"%s",GetName());
961 if (fTrH1 && fHits2) {
962 branch = fTrH1->GetBranch(branchname);
963 if (branch) branch->SetAddress(&fHits2);
965 if (fTrH1 && fPadHits2) {
966 branch = fTrH1->GetBranch("MUONCluster");
967 if (branch) branch->SetAddress(&fPadHits2);
970 //Int_t ntracks1 =(Int_t)fTrH1->GetEntries();
971 //printf("background - ntracks1 - %d\n",ntracks1);
974 // loop over cathodes
978 for (int icat=0; icat<2; icat++) {
980 Int_t * nmuon = new Int_t [AliMUONConstants::NCh()];
981 for (Int_t i =0; i<AliMUONConstants::NCh(); i++) {
982 iChamber=(AliMUONChamber*) (*fChambers)[i];
983 if (iChamber->Nsec()==1 && icat==1) {
986 segmentation=iChamber->SegmentationModel(icat+1);
988 hitMap[i] = new AliMUONHitMapA1(segmentation, list);
991 //printf("Start loop over tracks \n");
996 TTree *treeH = gAlice->TreeH();
997 Int_t ntracks =(Int_t) treeH->GetEntries();
1000 Float_t ** xhit = new Float_t * [AliMUONConstants::NCh()];
1001 for (jj=0; jj<AliMUONConstants::NCh(); jj++) xhit[jj] = new Float_t[2];
1002 Float_t ** yhit = new Float_t * [AliMUONConstants::NCh()];
1003 for (jj=0; jj<AliMUONConstants::NCh(); jj++) yhit[jj] = new Float_t[2];
1005 for (Int_t track=0; track<ntracks; track++) {
1006 gAlice->ResetHits();
1007 treeH->GetEvent(track);
1010 for(AliMUONHit* mHit=(AliMUONHit*)pMUON->FirstHit(-1);
1012 mHit=(AliMUONHit*)pMUON->NextHit())
1014 Int_t nch = mHit->fChamber-1; // chamber number
1015 if (nch > AliMUONConstants::NCh()-1) continue;
1016 iChamber = &(pMUON->Chamber(nch));
1018 if (addBackground) {
1020 if (mHit->fParticle == kMuonPlus
1021 || mHit->fParticle == kMuonMinus) {
1022 xhit[nch][nmuon[nch]]=mHit->fX;
1023 yhit[nch][nmuon[nch]]=mHit->fY;
1025 if (nmuon[nch] >2) printf("nmuon %d\n",nmuon[nch]);
1033 // Loop over pad hits
1034 for (AliMUONPadHit* mPad=
1035 (AliMUONPadHit*)pMUON->FirstPad(mHit,fPadHits);
1037 mPad=(AliMUONPadHit*)pMUON->NextPad(fPadHits))
1039 Int_t cathode = mPad->fCathode; // cathode number
1040 Int_t ipx = mPad->fPadX; // pad number on X
1041 Int_t ipy = mPad->fPadY; // pad number on Y
1042 Int_t iqpad = Int_t(mPad->fQpad);// charge per pad
1046 if (cathode != (icat+1)) continue;
1047 // fill the info array
1048 Float_t thex, they, thez;
1049 segmentation=iChamber->SegmentationModel(cathode);
1050 segmentation->GetPadC(ipx,ipy,thex,they,thez);
1051 // Float_t rpad=TMath::Sqrt(thex*thex+they*they);
1052 // if (rpad < rmin || iqpad ==0 || rpad > rmax) continue;
1054 new((*pAddress)[countadr++]) TVector(2);
1055 TVector &trinfo=*((TVector*) (*pAddress)[countadr-1]);
1056 trinfo(0)=(Float_t)track;
1057 trinfo(1)=(Float_t)iqpad;
1063 if (mHit->fParticle == kMuonPlus ||
1064 mHit->fParticle == kMuonMinus) {
1065 digits[4]=mPad->fHitNumber;
1066 } else digits[4]=-1;
1068 AliMUONTransientDigit* pdigit;
1069 // build the list of fired pads and update the info
1070 if (!hitMap[nch]->TestHit(ipx, ipy)) {
1072 list->AddAtAndExpand(
1073 new AliMUONTransientDigit(nch,digits),counter);
1075 hitMap[nch]->SetHit(ipx, ipy, counter);
1077 pdigit=(AliMUONTransientDigit*)list->At(list->GetLast());
1079 TObjArray *trlist=(TObjArray*)pdigit->TrackList();
1080 trlist->Add(&trinfo);
1082 pdigit=(AliMUONTransientDigit*) hitMap[nch]->GetHit(ipx, ipy);
1084 (*pdigit).fSignal+=iqpad;
1085 (*pdigit).fPhysics+=iqpad;
1086 // update list of tracks
1087 TObjArray* trlist=(TObjArray*)pdigit->TrackList();
1088 Int_t lastEntry=trlist->GetLast();
1089 TVector *pTrack=(TVector*)trlist->At(lastEntry);
1090 TVector &ptrk=*pTrack;
1091 Int_t lastTrack=Int_t(ptrk(0));
1092 Int_t lastCharge=Int_t(ptrk(1));
1093 if (lastTrack==track) {
1095 trlist->RemoveAt(lastEntry);
1096 trinfo(0)=lastTrack;
1097 trinfo(1)=lastCharge;
1098 trlist->AddAt(&trinfo,lastEntry);
1100 trlist->Add(&trinfo);
1102 // check the track list
1103 Int_t nptracks=trlist->GetEntriesFast();
1105 for (Int_t tr=0;tr<nptracks;tr++) {
1106 TVector *ppTrack=(TVector*)trlist->At(tr);
1107 TVector &pptrk=*ppTrack;
1108 trk[tr]=Int_t(pptrk(0));
1109 chtrk[tr]=Int_t(pptrk(1));
1111 } // end if nptracks
1113 } //end loop over clusters
1117 // open the file with background
1119 if (addBackground) {
1120 ntracks =(Int_t)fTrH1->GetEntries();
1124 for (Int_t track=0; track<ntracks; track++) {
1126 if (fHits2) fHits2->Clear();
1127 if (fPadHits2) fPadHits2->Clear();
1129 fTrH1->GetEvent(track);
1133 for(int i=0;i<fHits2->GetEntriesFast();++i)
1135 mHit=(AliMUONHit*) (*fHits2)[i];
1136 Int_t nch = mHit->fChamber-1; // chamber number
1137 if (nch >9) continue;
1138 iChamber = &(pMUON->Chamber(nch));
1139 Int_t rmin = (Int_t)iChamber->RInner();
1140 Int_t rmax = (Int_t)iChamber->ROuter();
1141 Float_t xbgr=mHit->fX;
1142 Float_t ybgr=mHit->fY;
1145 for (Int_t imuon =0; imuon < nmuon[nch]; imuon++) {
1146 Float_t dist= (xbgr-xhit[nch][imuon])*(xbgr-xhit[nch][imuon])
1147 +(ybgr-yhit[nch][imuon])*(ybgr-yhit[nch][imuon]);
1148 if (dist<100) cond=kTRUE;
1150 if (!cond) continue;
1153 // Loop over pad hits
1154 for (AliMUONPadHit* mPad=
1155 (AliMUONPadHit*)pMUON->FirstPad(mHit,fPadHits2);
1157 mPad=(AliMUONPadHit*)pMUON->NextPad(fPadHits2))
1159 // mPad = (AliMUONPadHit*) (*fPadHits2)[j];
1160 Int_t cathode = mPad->fCathode; // cathode number
1161 Int_t ipx = mPad->fPadX; // pad number on X
1162 Int_t ipy = mPad->fPadY; // pad number on Y
1163 Int_t iqpad = Int_t(mPad->fQpad);// charge per pad
1165 if (cathode != (icat+1)) continue;
1166 Float_t thex, they, thez;
1167 segmentation=iChamber->SegmentationModel(cathode);
1168 segmentation->GetPadC(ipx,ipy,thex,they,thez);
1169 Float_t rpad=TMath::Sqrt(thex*thex+they*they);
1170 if (rpad < rmin || iqpad ==0 || rpad > rmax) continue;
1171 new((*pAddress)[countadr++]) TVector(2);
1172 TVector &trinfo=*((TVector*) (*pAddress)[countadr-1]);
1173 trinfo(0)=-1; // tag background
1182 AliMUONTransientDigit* pdigit;
1183 // build the list of fired pads and update the info
1184 if (!hitMap[nch]->TestHit(ipx, ipy)) {
1185 list->AddAtAndExpand(new AliMUONTransientDigit(nch,digits),counter);
1187 hitMap[nch]->SetHit(ipx, ipy, counter);
1190 pdigit=(AliMUONTransientDigit*)list->At(list->GetLast());
1192 TObjArray *trlist=(TObjArray*)pdigit->
1194 trlist->Add(&trinfo);
1196 pdigit=(AliMUONTransientDigit*) hitMap[nch]->GetHit(ipx, ipy);
1198 (*pdigit).fSignal+=iqpad;
1200 // update list of tracks
1201 TObjArray* trlist=(TObjArray*)pdigit->
1203 Int_t lastEntry=trlist->GetLast();
1204 TVector *pTrack=(TVector*)trlist->
1206 TVector &ptrk=*pTrack;
1207 Int_t lastTrack=Int_t(ptrk(0));
1208 if (lastTrack==-1) {
1211 trlist->Add(&trinfo);
1213 // check the track list
1214 Int_t nptracks=trlist->GetEntriesFast();
1216 for (Int_t tr=0;tr<nptracks;tr++) {
1217 TVector *ppTrack=(TVector*)trlist->At(tr);
1218 TVector &pptrk=*ppTrack;
1219 trk[tr]=Int_t(pptrk(0));
1220 chtrk[tr]=Int_t(pptrk(1));
1222 } // end if nptracks
1224 } //end loop over clusters
1227 //Int_t nentr2=list->GetEntriesFast();
1228 //printf(" \n counter2, nentr2 %d %d \n",counter,nentr2);
1229 TTree *fAli=gAlice->TreeK();
1232 if (fAli) file =fAli->GetCurrentFile();
1234 } // if addBackground
1240 Int_t nentries=list->GetEntriesFast();
1242 for (Int_t nent=0;nent<nentries;nent++) {
1243 AliMUONTransientDigit *address=(AliMUONTransientDigit*)list->At(nent);
1244 if (address==0) continue;
1245 Int_t ich=address->fChamber;
1246 Int_t q=address->fSignal;
1247 iChamber=(AliMUONChamber*) (*fChambers)[ich];
1249 // Digit Response (noise, threshold, saturation, ...)
1250 // if (address->fPhysics !=0 ) address->fPhysics+=(Int_t)Noise;
1251 AliMUONResponse * response=iChamber->ResponseModel();
1252 q=response->DigitResponse(q);
1256 digits[0]=address->fPadX;
1257 digits[1]=address->fPadY;
1259 digits[3]=address->fPhysics;
1260 digits[4]=address->fHit;
1262 TObjArray* trlist=(TObjArray*)address->TrackList();
1263 Int_t nptracks=trlist->GetEntriesFast();
1264 //printf("nptracks, trlist %d %p\n",nptracks,trlist);
1266 // this was changed to accomodate the real number of tracks
1267 if (nptracks > 10) {
1268 cout<<"Attention - nptracks > 10 "<<nptracks<<endl;
1272 printf("Attention - nptracks > 2 %d \n",nptracks);
1273 printf("cat,ich,ix,iy,q %d %d %d %d %d \n",icat,ich,digits[0],digits[1],q);
1275 for (Int_t tr=0;tr<nptracks;tr++) {
1276 TVector *ppP=(TVector*)trlist->At(tr);
1277 if(!ppP ) printf("ppP - %p\n",ppP);
1279 tracks[tr]=Int_t(pp(0));
1280 charges[tr]=Int_t(pp(1));
1281 //printf("tracks, charges - %d %d\n",tracks[tr],charges[tr]);
1282 } //end loop over list of tracks for one pad
1283 // Sort list of tracks according to charge
1285 SortTracks(tracks,charges,nptracks);
1287 if (nptracks < 10 ) {
1288 for (Int_t i=nptracks; i<10; i++) {
1295 pMUON->AddDigits(ich,tracks,charges,digits);
1298 //cout<<"I'm out of the loops for digitisation"<<endl;
1299 // gAlice->GetEvent(nev);
1300 gAlice->TreeD()->Fill();
1301 pMUON->ResetDigits();
1305 for(Int_t ii=0;ii<AliMUONConstants::NCh();++ii) {
1313 } //end loop over cathodes
1316 sprintf(hname,"TreeD%d",nev);
1317 gAlice->TreeD()->Write(hname);
1319 gAlice->TreeD()->Reset();
1323 // gObjectTable->Print();
1326 void AliMUON::SortTracks(Int_t *tracks,Int_t *charges,Int_t ntr)
1329 // Sort the list of tracks contributing to a given digit
1330 // Only the 3 most significant tracks are acctually sorted
1334 // Loop over signals, only 3 times
1339 Int_t idx[3] = {-2,-2,-2};
1340 Int_t jch[3] = {-2,-2,-2};
1341 Int_t jtr[3] = {-2,-2,-2};
1344 if (ntr<3) imax=ntr;
1346 for(i=0;i<imax;i++){
1352 if((i == 1 && j == idx[i-1])
1353 ||(i == 2 && (j == idx[i-1] || j == idx[i-2]))) continue;
1355 if(charges[j] > qmax) {
1363 jch[i]=charges[jmax];
1364 jtr[i]=tracks[jmax];
1381 //___________________________________________
1382 void AliMUON::Trigger(Int_t nev){
1383 // call the Trigger Algorithm and fill TreeR
1385 Int_t singlePlus[3] = {0,0,0};
1386 Int_t singleMinus[3] = {0,0,0};
1387 Int_t singleUndef[3] = {0,0,0};
1388 Int_t pairUnlike[3] = {0,0,0};
1389 Int_t pairLike[3] = {0,0,0};
1392 AliMUONTriggerDecision* decision= new AliMUONTriggerDecision(1);
1393 decision->Trigger();
1394 decision->GetGlobalTrigger(singlePlus, singleMinus, singleUndef,
1395 pairUnlike, pairLike);
1396 // add a local trigger in the list
1397 AddGlobalTrigger(singlePlus, singleMinus, singleUndef, pairUnlike, pairLike);
1400 for (Int_t icirc=0; icirc<AliMUONConstants::NTriggerCircuit(); icirc++) {
1401 if(decision->GetITrigger(icirc)==1) {
1402 Int_t localtr[7]={0,0,0,0,0,0,0};
1403 Int_t loLpt[2]={0,0}; Int_t loHpt[2]={0,0}; Int_t loApt[2]={0,0};
1404 decision->GetLutOutput(icirc, loLpt, loHpt, loApt);
1406 localtr[1] = decision->GetStripX11(icirc);
1407 localtr[2] = decision->GetDev(icirc);
1408 localtr[3] = decision->GetStripY11(icirc);
1409 for (i=0; i<2; i++) { // convert the Lut output in 1 digit
1410 localtr[4] = localtr[4]+Int_t(loLpt[i]*TMath::Power(2,i));
1411 localtr[5] = localtr[5]+Int_t(loHpt[i]*TMath::Power(2,i));
1412 localtr[6] = localtr[6]+Int_t(loApt[i]*TMath::Power(2,i));
1414 AddLocalTrigger(localtr); // add a local trigger in the list
1419 gAlice->TreeR()->Fill();
1422 sprintf(hname,"TreeR%d",nev);
1423 gAlice->TreeR()->Write(hname);
1424 gAlice->TreeR()->Reset();
1425 printf("\n End of trigger for event %d", nev);
1429 //____________________________________________
1430 void AliMUON::FindClusters(Int_t nev,Int_t lastEntry)
1432 TClonesArray *dig1, *dig2;
1434 dig1 = new TClonesArray("AliMUONDigit",1000);
1435 dig2 = new TClonesArray("AliMUONDigit",1000);
1436 AliMUONDigit *digit;
1438 // Loop on chambers and on cathode planes
1441 for (Int_t ich=0;ich<10;ich++) {
1442 AliMUONChamber* iChamber=(AliMUONChamber*) (*fChambers)[ich];
1443 AliMUONClusterFinderVS* rec = iChamber->ReconstructionModel();
1444 gAlice->ResetDigits();
1445 gAlice->TreeD()->GetEvent(lastEntry);
1446 TClonesArray *muonDigits = this->DigitsAddress(ich);
1447 ndig=muonDigits->GetEntriesFast();
1448 printf("\n 1 Found %d digits in %p %d", ndig, muonDigits,ich);
1449 TClonesArray &lhits1 = *dig1;
1451 for (k=0; k<ndig; k++) {
1452 digit=(AliMUONDigit*) muonDigits->UncheckedAt(k);
1453 if (rec->TestTrack(digit->fTracks[0]))
1454 new(lhits1[n++]) AliMUONDigit(*digit);
1456 gAlice->ResetDigits();
1457 gAlice->TreeD()->GetEvent(lastEntry+1);
1458 muonDigits = this->DigitsAddress(ich);
1459 ndig=muonDigits->GetEntriesFast();
1460 printf("\n 2 Found %d digits in %p %d", ndig, muonDigits, ich);
1461 TClonesArray &lhits2 = *dig2;
1464 for (k=0; k<ndig; k++) {
1465 digit= (AliMUONDigit*) muonDigits->UncheckedAt(k);
1466 if (rec->TestTrack(digit->fTracks[0]))
1467 new(lhits2[n++]) AliMUONDigit(*digit);
1471 AliMUONClusterInput::Instance()->SetDigits(ich, dig1, dig2);
1472 rec->FindRawClusters();
1477 gAlice->TreeR()->Fill();
1480 sprintf(hname,"TreeR%d",nev);
1481 gAlice->TreeR()->Write(hname);
1482 gAlice->TreeR()->Reset();
1483 printf("\n End of cluster finding for event %d", nev);
1487 //gObjectTable->Print();
1491 void AliMUON::Streamer(TBuffer &R__b)
1493 // Stream an object of class AliMUON.
1494 AliMUONChamber *iChamber;
1495 AliMUONTriggerCircuit *iTriggerCircuit;
1496 AliSegmentation *segmentation;
1497 AliMUONResponse *response;
1498 TClonesArray *digitsaddress;
1499 TClonesArray *rawcladdress;
1501 if (R__b.IsReading()) {
1502 Version_t R__v = R__b.ReadVersion(); if (R__v) { }
1503 AliDetector::Streamer(R__b);
1505 R__b >> fPadHits; // diff
1506 R__b >> fNLocalTrigger;
1507 R__b >> fLocalTrigger;
1508 R__b >> fNGlobalTrigger;
1509 R__b >> fGlobalTrigger;
1511 R__b >> fRawClusters;
1512 R__b.ReadArray(fNdch);
1513 R__b.ReadArray(fNrawch);
1518 R__b >> fTriggerCircuits;
1519 for (i =0; i<AliMUONConstants::NTriggerCircuit(); i++) {
1520 iTriggerCircuit=(AliMUONTriggerCircuit*) (*fTriggerCircuits)[i];
1521 iTriggerCircuit->Streamer(R__b);
1523 // Stream chamber related information
1524 for (i =0; i<AliMUONConstants::NCh(); i++) {
1525 iChamber=(AliMUONChamber*) (*fChambers)[i];
1526 iChamber->Streamer(R__b);
1527 if (iChamber->Nsec()==1) {
1528 segmentation=iChamber->SegmentationModel(1);
1530 segmentation->Streamer(R__b);
1532 segmentation=iChamber->SegmentationModel(1);
1534 segmentation->Streamer(R__b);
1536 segmentation=iChamber->SegmentationModel(2);
1537 segmentation->Streamer(R__b);
1539 response=iChamber->ResponseModel();
1541 response->Streamer(R__b);
1542 digitsaddress=(TClonesArray*) (*fDchambers)[i];
1543 digitsaddress->Streamer(R__b);
1544 if (i < AliMUONConstants::NTrackingCh()) {
1545 rawcladdress=(TClonesArray*) (*fRawClusters)[i];
1546 rawcladdress->Streamer(R__b);
1551 R__b.WriteVersion(AliMUON::IsA());
1552 AliDetector::Streamer(R__b);
1554 R__b << fPadHits; // diff
1555 R__b << fNLocalTrigger;
1556 R__b << fLocalTrigger;
1557 R__b << fNGlobalTrigger;
1558 R__b << fGlobalTrigger;
1560 R__b << fRawClusters;
1561 R__b.WriteArray(fNdch, AliMUONConstants::NCh());
1562 R__b.WriteArray(fNrawch, AliMUONConstants::NTrackingCh());
1569 R__b << fTriggerCircuits;
1570 for (i =0; i<AliMUONConstants::NTriggerCircuit(); i++) {
1571 iTriggerCircuit=(AliMUONTriggerCircuit*) (*fTriggerCircuits)[i];
1572 iTriggerCircuit->Streamer(R__b);
1574 for (i =0; i<AliMUONConstants::NCh(); i++) {
1575 iChamber=(AliMUONChamber*) (*fChambers)[i];
1576 iChamber->Streamer(R__b);
1577 if (iChamber->Nsec()==1) {
1578 segmentation=iChamber->SegmentationModel(1);
1580 segmentation->Streamer(R__b);
1582 segmentation=iChamber->SegmentationModel(1);
1584 segmentation->Streamer(R__b);
1585 segmentation=iChamber->SegmentationModel(2);
1587 segmentation->Streamer(R__b);
1589 response=iChamber->ResponseModel();
1591 response->Streamer(R__b);
1592 digitsaddress=(TClonesArray*) (*fDchambers)[i];
1593 digitsaddress->Streamer(R__b);
1594 if (i < AliMUONConstants::NTrackingCh()) {
1595 rawcladdress=(TClonesArray*) (*fRawClusters)[i];
1596 rawcladdress->Streamer(R__b);
1601 AliMUONPadHit* AliMUON::FirstPad(AliMUONHit* hit, TClonesArray *clusters)
1604 // Initialise the pad iterator
1605 // Return the address of the first padhit for hit
1606 TClonesArray *theClusters = clusters;
1607 Int_t nclust = theClusters->GetEntriesFast();
1608 if (nclust && hit->fPHlast > 0) {
1609 AliMUON::fMaxIterPad=hit->fPHlast;
1610 AliMUON::fCurIterPad=hit->fPHfirst;
1611 return (AliMUONPadHit*) clusters->UncheckedAt(AliMUON::fCurIterPad-1);
1617 AliMUONPadHit* AliMUON::NextPad(TClonesArray *clusters)
1619 AliMUON::fCurIterPad++;
1620 if (AliMUON::fCurIterPad <= AliMUON::fMaxIterPad) {
1621 return (AliMUONPadHit*) clusters->UncheckedAt(AliMUON::fCurIterPad-1);
1628 AliMUONRawCluster *AliMUON::RawCluster(Int_t ichamber, Int_t icathod, Int_t icluster)
1630 TClonesArray *muonRawCluster = RawClustAddress(ichamber);
1632 TTree *treeR = gAlice->TreeR();
1633 Int_t nent=(Int_t)treeR->GetEntries();
1634 treeR->GetEvent(nent-2+icathod-1);
1635 //treeR->GetEvent(icathod);
1636 //Int_t nrawcl = (Int_t)muonRawCluster->GetEntriesFast();
1638 AliMUONRawCluster * mRaw = (AliMUONRawCluster*)muonRawCluster->UncheckedAt(icluster);
1639 //printf("RawCluster _ nent nrawcl icluster mRaw %d %d %d%p\n",nent,nrawcl,icluster,mRaw);
1644 AliMUON& AliMUON::operator = (const AliMUON& rhs)