StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
StEEmcGenericClusterMaker.cxx
1 #include "StEEmcGenericClusterMaker.h"
2 
3 #include "TH1F.h"
4 #include "TH2F.h"
5 #include "TLine.h"
6 
7 #include "StEEmcPool/StEEmcA2EMaker/StEEmcA2EMaker.h"
8 
9 #include "StEvent.h"
10 #include "StEmcDetector.h"
11 #include "StEmcCollection.h"
12 
13 #include "StMessMgr.h"
14 
15 #include "StMuDSTMaker/COMMON/StMuTrack.h"
16 #include "StMuDSTMaker/COMMON/StMuDst.h"
17 #include "StMuDSTMaker/COMMON/StMuDstMaker.h"
18 
19 #include "StEEmcUtil/EEmcGeom/EEmcGeomDefs.h"
20 
22 
23 // ----------------------------------------------------------------------------
25  : StMaker(name)
26 {
27 
28  mEEanalysis=a2e; /* adc to energy maker */
29 
30  // mCollection=new StEEmcClusterCollection();
31 
32  mEEmcGeom=new EEmcGeomSimple();
33  mESmdGeom=EEmcSmdGeom::instance();
34  mESmdMap =EEmcSmdMap::instance();
35 
48 
49  StEEmcClusterVec_t t;
50  std::vector< StEEmcClusterVec_t > layers;
51  for ( Int_t i = 0; i < 4; i++ ) layers.push_back(t);
52  for ( Int_t i = 0; i < 12; i++ ) mTowerClusters.push_back(layers);
53 
54  StEEmcSmdClusterVec_t s;
55  std::vector< StEEmcSmdClusterVec_t > planes;
56  planes.push_back(s);
57  planes.push_back(s);
58  for ( Int_t i = 0; i < 12; i++ ) mSmdClusters.push_back(planes);
59 
60  mSmdMatchRange = 40;
61 
62 
63 
68  mClusterTrackSeparation[0] = 0.05;
69  mClusterTrackSeparation[1] = 0.075;
70  mClusterTrackSeparation[2] = 0.075;
71  mClusterTrackSeparation[3] = 0.075;
72  mClusterTrackSeparation[4] = 3.0;
73  mClusterTrackSeparation[5] = 3.0;
75  Clear();
76 
77 }
78 
79 // ----------------------------------------------------------------------------
80 Int_t StEEmcGenericClusterMaker::Init()
81 {
82 
83  // If it's missing from the constructor, obtain pointer to
84  // the "default" eemc adc 2 energy maker. If it doesn't
85  // exist, crash and burn.
86  if (!mEEanalysis) mEEanalysis=(StEEmcA2EMaker*)GetMaker("EEmcAdc2Energy");
87  assert(mEEanalysis);// no input calib maker
88 
89  return StMaker::Init();
90 }
91 
92 // ----------------------------------------------------------------------------
93 Int_t StEEmcGenericClusterMaker::Make() // runs after user's Make()
94 {
95  Int_t result = StMaker::Make();
96  makeClusterMap();
97  makeTrackMap();
98  makeStEvent();
99  makeHistograms();
100 
101  // add clusters to collection
102 
103  /***
104  mCollection->setNumberOfClusters(numberOfClusters());
105  for ( Int_t sec=0;sec<12;sec++ )
106  {
107  for ( Int_t lay=0;lay<4;lay++ )
108  {
109  for ( UInt_t i=0;i<mTowerClusters[sec][lay].size();i++ )
110  {
111  mCollection->add( mTowerClusters[sec][lay][i] );
112  }
113  }
114  for ( Int_t pln=0;pln<2;pln++ )
115  {
116  for ( UInt_t i=0;i<mSmdClusters[sec][pln].size();i++ )
117  {
118  mCollection->add( mSmdClusters[sec][pln][i] );
119  }
120  }
121  }
122  ***/
123 
124  return result;
125 
126 }
127 
128 void StEEmcGenericClusterMaker::makeHistograms()
129 {
130 
131 
132 }
133 
134 void StEEmcGenericClusterMaker::makeClusterMap()
135 {
136 
137 
138  // loop over all sectors
139  for ( UInt_t sec=0;sec<12;sec++ )
140  {
141 
142  // get vectors of clusters in this sector
143  StEEmcClusterVec_t &Tclusters = mTowerClusters[sec][0];
144  StEEmcClusterVec_t &Pclusters = mTowerClusters[sec][1];
145  StEEmcClusterVec_t &Qclusters = mTowerClusters[sec][2];
146  StEEmcClusterVec_t &Rclusters = mTowerClusters[sec][3];
147  StEEmcSmdClusterVec_t &Uclusters = mSmdClusters[sec][0];
148  StEEmcSmdClusterVec_t &Vclusters = mSmdClusters[sec][1];
149 
150  // loop over all cluster pairs and build associative maps
151  for ( UInt_t t=0;t<Tclusters.size(); t++ )// towers
152  {
153 
154  StEEmcCluster &c = Tclusters[t];
155  EEmatch *mymatch = &mClusterMap[c.key()];
156 
157  for ( UInt_t p=0;p<Pclusters.size();p++ )
158  if ( match(c,Pclusters[p]) ) mymatch->pre1.push_back(Pclusters[p]);
159  for ( UInt_t q=0;q<Qclusters.size();q++ )
160  if ( match(c,Qclusters[q]) ) mymatch->pre2.push_back(Qclusters[q]);
161  for ( UInt_t r=0;r<Rclusters.size();r++ )
162  if ( match(c,Rclusters[r]) ) mymatch->post.push_back(Rclusters[r]);
163  for ( UInt_t u=0;u<Uclusters.size();u++ )
164  if ( match(c,Uclusters[u]) ) mymatch->smdu.push_back(Uclusters[u]);
165  for ( UInt_t v=0;v<Vclusters.size();v++ )
166  if ( match(c,Vclusters[v]) ) mymatch->smdv.push_back(Vclusters[v]);
167 
168 
169  for ( UInt_t p=0;p<Pclusters.size();p++ )
170  if ( match(c,Pclusters[p]) ) c.addMatch( Pclusters[p].key(), 1 );
171  for ( UInt_t q=0;q<Qclusters.size();q++ )
172  if ( match(c,Qclusters[q]) ) c.addMatch( Qclusters[q].key(), 2 );
173  for ( UInt_t r=0;r<Rclusters.size();r++ )
174  if ( match(c,Rclusters[r]) ) c.addMatch( Rclusters[r].key(), 3 );
175  for ( UInt_t u=0;u<Uclusters.size();u++ )
176  if ( match(c,Uclusters[u]) ) c.addMatch( Uclusters[u].key(), 4 );
177  for ( UInt_t v=0;v<Vclusters.size();v++ )
178  if ( match(c,Vclusters[v]) ) c.addMatch( Vclusters[v].key(), 5 );
179 
180  }
181 
182 #if 0
183  // print matches
184  for ( UInt_t i=0;i<Tclusters.size();i++ )
185  {
186 
187  std::cout << "sec=" << sec << " i=" << i << " ------------------------------------" << std::endl;
188  StEEmcCluster c=Tclusters[i];
189  c.print();
190  Int_t k=c.key();
191  EEmatch m=mClusterMap[k];
192  for ( UInt_t j=0;j<m.pre1.size();j++ )
193  m.pre1[j].print();
194  for ( UInt_t j=0;j<m.pre2.size();j++ )
195  m.pre2[j].print();
196  for ( UInt_t j=0;j<m.post.size();j++ )
197  m.post[j].print();
198  for ( UInt_t j=0;j<m.smdu.size();j++ )
199  m.smdu[j].printLine();
200  for ( UInt_t j=0;j<m.smdv.size();j++ )
201  m.smdv[j].printLine();
202 
203  }
204 
205 #endif
206 #if 0
207  // print matches
208  for ( UInt_t i=0;i<Tclusters.size();i++ )
209  {
210  std::cout << "sec=" << sec << " i=" << i << " ------------------------------------" << std::endl;
211  StEEmcCluster c=Tclusters[i];
212  c.print();
213 
214  std::cout << "pre1 matches: ";
215  for ( Int_t j=0;j<c.numberOfMatchingClusters(1);j++ )
216  std::cout << c.getMatch(j,1) << " ";
217  std::cout << std::endl;
218 
219  std::cout << "pre2 matches: ";
220  for ( Int_t j=0;j<c.numberOfMatchingClusters(2);j++ )
221  std::cout << c.getMatch(j,2) << " ";
222  std::cout << std::endl;
223 
224 
225  std::cout << "post matches: ";
226  for ( Int_t j=0;j<c.numberOfMatchingClusters(3);j++ )
227  std::cout << c.getMatch(j,3) << " ";
228  std::cout << std::endl;
229 
230 
231  }
232 #endif
233 
234 
235  }
236 
237 
238 
239 
240 
241 }
242 
244 {
245 
246  LOG_DEBUG << GetName() << " -I- entering makeTrackMap()" << endm;
247 
248  StMuDstMaker *maker = (StMuDstMaker*)GetMaker("MuDst");
249  if ( !maker )
250  {
251  LOG_DEBUG << GetName() << " -I- mudst maker not in chain?" << endm;
252  return;
253  }
254 
255  StMuDst *mudst = maker->muDst();
256 
257  //--
258  //-- Match primary tracks to tower, pre/postshower clusters
259  //--
260  Int_t nprimary = (Int_t)mudst->numberOfPrimaryTracks();
261 
262  LOG_DEBUG<<" checking nprimary="<<nprimary<< " tracks"<<endm;
263 
264  for ( Int_t iprimary = 0; iprimary < nprimary; iprimary++ )
265  {
266  StMuTrack *track = mudst->primaryTracks(iprimary);
267  if (!track)continue;
268 
270  for ( Int_t sec=0;sec<12;sec++ )
271  {
272 
274  for ( Int_t layer = 0; layer < 4; layer++ )
275  {
276 
277  for ( Int_t ii=0;ii<numberOfClusters(sec,layer); ii++ )
278  {
279  StEEmcCluster mycluster = cluster(sec,layer,ii);
280  if ( match(mycluster, track) )
281  {
282  LOG_DEBUG << GetName() << " -I- matched cluster to track in layer=" << layer << endm;
283  //mycluster.print();
284  //std::cout << "cluster: eta=" << mycluster.momentum().Eta() << " phi=" << mycluster.momentum().Phi() << std::endl;
285  //std::cout << "track: eta=" << track->eta() << " phi=" << track->phi() << std::endl;
286  mClusterTrackMap[ mycluster.key() ].push_back( track );
287  }
288  }
289 
290  }
291  }
292 
293  }
294 
295 
296 
297  //--
298  //-- Match global tracks flagged as background to tower, pre/postshower
299  //-- clusters
300  //--
301  Int_t nglobal = (Int_t)mudst->numberOfGlobalTracks();
302  for ( Int_t iglobal = 0; iglobal < nglobal; iglobal++ )
303  {
304  StMuTrack *track = mudst->globalTracks(iglobal);
305  if (!track) continue;
306 
307  // verify track from background tracker
308  if (! (track->flag()==901) ) continue;
309 
311  for ( Int_t sec=0;sec<12;sec++ )
312  {
313 
315  for ( Int_t layer = 0; layer < 4; layer++ )
316  {
317 
318  for ( Int_t ii=0;ii<numberOfClusters(sec,layer); ii++ )
319  {
320  StEEmcCluster mycluster = cluster(sec,layer,ii);
321  if ( matchBackgroundTrack(mycluster, track) )
322  {
323  LOG_DEBUG << GetName() << " -I- matched cluster to background track in layer=" << layer << endm;
324  //mycluster.print();
325  //std::cout << "cluster: eta=" << mycluster.momentum().Eta() << " phi=" << mycluster.momentum().Phi() << std::endl;
326  //std::cout << "track: eta=" << track->eta() << " phi=" << track->phi() << std::endl;
327  mBackgroundTrackMap[ mycluster.key() ].push_back( track );
328  }
329  }
330 
331  }
332  }
333 
334  }
335 
336 
337 
338 }
339 
340 
341 
343 {
344 
345  /*
346  * create StEmcClusters and fill StEvent (to be added)
347  */
348 
349  StEvent *stevent=(StEvent*)GetInputDS("StEvent");
350  if ( !stevent ) {
351  // assume we're running on MuDst and no collections need populated
352  return;
353  }
354 
358  StEmcDetector *detector=stevent->emcCollection()->detector(kEndcapEmcTowerId);
359  if ( !detector )
360  {
361  // meh Warning("fillStEvent","detector == NULL, MAJOR StEvent problem, continuing");
362  return;
363  }
367  detector=stevent->emcCollection()->detector(kEndcapEmcPreShowerId);
368  if ( !detector )
369  {
370  // meh Warning("fillStEvent","detector == NULL for pre/post, no clusters for you");
371  return;
372  }
376  StDetectorId ids[]={ kEndcapSmdUStripId, kEndcapSmdVStripId };
377 
378 
379  for ( Int_t iplane=0; iplane<2; iplane++ )
380  {
381 
382  detector=stevent->emcCollection()->detector(ids[iplane]);
383  if ( !detector )
384  {
385  // meh Warning("fillStEvent","detector == NULL for smd plane, no clusters for you");
386  return;
387  }
388 
389  }
390 
391 
392  return;
393 }
394 
395 // ----------------------------------------------------------------------------
397 {
398  StMaker::Clear();
399  // clears storage arrays
400  for ( Int_t sector=0; sector<12; sector++ ) {
401  for ( Int_t layer=0; layer<4; layer++ )
402  mTowerClusters[sector][layer].clear();
403  for ( Int_t plane=0; plane<2; plane++ )
404  mSmdClusters[sector][plane].clear();
405  }
406  for ( Int_t i=0;i<6;i++ ) mNumberOfClusters[i]=0;
407 
408  // clear the cluster map
409  mClusterMap.clear();
410  mClusterTrackMap.clear();
411  mBackgroundTrackMap.clear();
412 
413  // reset the cluster id
414  mClusterId = 0;
415 
416  // clear the collection
417  // mCollection->Clear();
418 
419 
420 }
421 
422 // ----------------------------------------------------------------------------
424 {
426  assert( c.towers().size() ); // cluster with no towers?
427 
428  Int_t key = nextClusterId(); /* next available cluster id */
429  Int_t sector = c.tower(0).sector(); /* sector of seed tower */
430  Int_t layer = c.tower(0).layer(); /* layer of the cluster */
431  c.key(key);
432  mTowerClusters[sector][layer].push_back(c);
433 
434  assert( mTowerClusters[sector][layer].back().towers().size() );
435 
436  // add this cluster to the cluster map
437  EEmatch match;
438  match.tower.push_back(c);
439  mClusterMap[ key ] = match;
440 
441  // add this cluster to the cluster track map
442  std::vector< StMuTrack* > v, u;
443  mClusterTrackMap[ key ] = v;
444  mBackgroundTrackMap[ key ] = u;
445 
446  mNumberOfClusters[c.tower(0).layer()]++;
447 
448 
449 }
450 
451 // ----------------------------------------------------------------------------
453 {
454  return c1.tower(0).isNeighbor( c2.tower(0) );
455 }
456 
457 Bool_t StEEmcGenericClusterMaker::match(const StEEmcCluster &c1, const StEEmcSmdCluster &c2) const
458 {
459  StEEmcTower seed=c1.tower(0);
460  if ( seed.sector() != c2.sector() ) return false;
461 
462  Int_t min[2],max[2];
463  mESmdMap -> getRangeU( seed.sector(), seed.subsector(), seed.etabin(), min[0], max[0] );
464  mESmdMap -> getRangeV( seed.sector(), seed.subsector(), seed.etabin(), min[1], max[1] );
465 
466  Int_t plane = c2.plane();
467  Float_t mean = c2.mean();
468  Int_t mid = (max[plane]+min[plane])/2;
469  Float_t del = mean - mid;
470 
471  return TMath::Abs(del)<mSmdMatchRange;
472 }
473 
474 Bool_t StEEmcGenericClusterMaker::match(const StEEmcSmdCluster &c1, const StEEmcSmdCluster &c2) const
475 {
476 
477  Bool_t myMatch = false;
478  if ( ( c1.energy() > 0.8 * c2.energy() &&
479  c1.energy() < 1.2 * c2.energy() ) ||
480  ( c2.energy() > 0.8 * c1.energy() &&
481  c2.energy() < 1.2 * c1.energy() ) ) myMatch = true;
482 
483  if ( !myMatch ) return false;
484 
485  for ( Int_t sec=0;sec<12;sec++ )
486  for ( UInt_t i=0; i < mTowerClusters[sec][0].size(); i++ )
487  {
488 
489  const StEEmcCluster &c=mTowerClusters[sec][0][i];
490  if ( match ( c, c1 ) && match( c, c2 ) ) return true;
491 
492  }
493 
494  return false;
495 
496 }
497 
498 Bool_t StEEmcGenericClusterMaker::match(const StEEmcCluster &cluster, const StMuTrack *track) const
499 {
500 
501  const StPhysicalHelixD helix = track -> outerHelix();
502  const Float_t match_at_z[]={
503  kEEmcZSMD, // match tower clusters at smd
504  kEEmcZPRE1, // match pre1 at pre1
505  kEEmcZPRE2, // match pre2 at pre2
506  kEEmcZPOST // match post at post
507  };
508 
509  Int_t layer = cluster.tower(0).layer();
510 
511  TVector3 r(0.,0.,-1.);
512  if ( extrapolateToZ( helix, match_at_z[ layer ], r ) )
513  {
514  TVector3 position = cluster.position();
515  Float_t dphi = fmod( position.Phi() - r.Phi(), TMath::TwoPi() );
516  Float_t deta = position.Eta() - r.Eta();
517  Float_t dr=TMath::Sqrt(deta*deta+dphi*dphi);
518 
519  if ( dr < mClusterTrackSeparation[layer] ) return true;
520 
521  }
522 
523  return false;
524 
525 }
526 
527 Bool_t StEEmcGenericClusterMaker::extrapolateToZ( const StPhysicalHelixD &helix, const double z, TVector3 &r) const
528 {
529  const double kMinDipAngle = 1.0e-13;
530  double dipAng = helix.dipAngle();
531  double z0 = helix.origin().z();
532  if(dipAng<kMinDipAngle)
533  return kFALSE;
534  double s = ( z - z0 ) / sin(dipAng) ;
535  StThreeVectorD hit = helix.at(s);
536  r.SetXYZ(hit.x(),hit.y(),hit.z());
537  return kTRUE;
538 }
539 
540 
541 Bool_t StEEmcGenericClusterMaker::matchBackgroundTrack(const StEEmcCluster &cluster, const StMuTrack *track ) const
542 {
543 
544  //
545  // First and last point on the background tracks are stored as the
546  // origin points of the inner and outer helix.
547  //
548  StPhysicalHelixD outer = track -> outerHelix();
549  StPhysicalHelixD inner = track -> helix();
550  StThreeVectorD p1 = inner.origin();
551  StThreeVectorD p2 = outer.origin();
552 
553  Int_t layer = cluster.tower(0).layer();
554 
555  Double_t z1 = p1.z();
556  Double_t z2 = p2.z();
557 
558  if ( z2 <= z1 ) return false;
559 
560  const Float_t match_at_z[]={
561  kEEmcZSMD, // match tower clusters at smd
562  kEEmcZPRE1, // match pre1 at pre1
563  kEEmcZPRE2, // match pre2 at pre2
564  kEEmcZPOST // match post at post
565  };
566 
567  Double_t zmatch = match_at_z[ layer ];
568 
569  //
570  // Compute the intersection point with the track (assume straight line)
571  // extrapolated to the layer where we want to make the match
572  //
573  Double_t scale = zmatch - z1;
574  scale /= z2 - z1;
575 
576  StThreeVectorD myposition = p1 + scale * (p2 - p1);
577 
578  // Compare position
579  TVector3 r(myposition.x(),myposition.y(),myposition.z());
580  TVector3 position = cluster.position();
581 
582  Float_t dphi = fmod( position.Phi() - r.Phi(), TMath::TwoPi() );
583  Float_t deta = position.Eta() - r.Eta();
584  Float_t dr=TMath::Sqrt(deta*deta+dphi*dphi);
585 
586  if ( dr < mClusterTrackSeparation[layer] ) return true;
587 
588  return false;
589 
590 }
591 
592 
593 // ----------------------------------------------------------------------------
595 {
596  const EEmatch &matches = clusterMatch( cluster );
597  return (plane==0)? (Int_t)matches.smdu.size() : (Int_t)matches.smdv.size();
598 }
599 
601 {
602  EEmatch &matches = clusterMatch( cluster );
603  return (plane==0)? matches.smdu[index] : matches.smdv[index];
604 }
605 
606 const StEEmcSmdCluster &StEEmcGenericClusterMaker::matchingSmdCluster (const StEEmcCluster &cluster, Int_t plane, Int_t index ) const
607 {
608  const EEmatch &matches = clusterMatch( cluster );
609  return (plane==0)? matches.smdu[index] : matches.smdv[index];
610 }
611 
612 
StEEmcTower & tower(Int_t t)
Get the specified tower within the cluster.
Definition: StEEmcCluster.h:79
static TObjArray * globalTracks()
returns pointer to the global tracks list
Definition: StMuDst.h:303
EEmc ADC –&gt; energy maker.
Bool_t isNeighbor(const StEEmcTower &t) const
Definition: StEEmcTower.cxx:98
StMuDst * muDst()
Definition: StMuDstMaker.h:425
Int_t numberOfClusters() const
returns the total number of clusters summed over all layers
StEEmcGenericClusterMaker(const Char_t *name, const StEEmcA2EMaker *a2e=NULL)
void layer(Int_t l)
Sets the layer, [0-4]=[TPQR].
Definition: StEEmcTower.h:31
virtual void Clear(Option_t *opts="")
User defined functions.
TVector3 position() const
Definition: StEEmcCluster.h:73
virtual void Clear(Option_t *option="")
User defined functions.
Definition: StMaker.cxx:634
Bool_t extrapolateToZ(const StPhysicalHelixD &helix, const double z, TVector3 &r) const
extrapolates helix to position z (borrowed from StEEmcPool/TTM)
void add(const StEEmcCluster &cluster)
Add a tower (pre/postshower) cluster to the list of clusters.
Bool_t match(const StEEmcCluster &c1, const StEEmcCluster &c2) const
Int_t numberOfMatchingSmdClusters(const StEEmcCluster &cluster, Int_t plane) const
StEEmcTowerVec_t & towers()
Get the vector of towers in this cluster.
Definition: StEEmcCluster.h:89
void print() const
Prints cluster data.
Int_t etabin() const
Returns the etabin of this tower, pre- or postshower element.
Definition: StEEmcTower.h:45
virtual Int_t Make()
Definition: StMaker.cxx:898
EEmatch & clusterMatch(const StEEmcCluster &c)
Int_t subsector() const
Returns subsector of this tower, pre- or postshower element.
Definition: StEEmcTower.h:43
short flag() const
Returns flag, (see StEvent manual for type information)
Definition: StMuTrack.h:230
Base class for representing tower, preshower and postshower elements.
Definition: StEEmcTower.h:11
StEEmcSmdCluster & matchingSmdCluster(const StEEmcCluster &cluster, Int_t plane, Int_t index)
static TObjArray * primaryTracks()
returns pointer to a list of tracks belonging to the selected primary vertex
Definition: StMuDst.h:301
Int_t sector() const
Returns sector of this tower, pre- or postshower element.
Definition: StEEmcTower.h:41
const StThreeVector< double > & origin() const
-sign(q*B);
Definition: StHelix.hh:224
virtual const char * GetName() const
special overload
Definition: StMaker.cxx:237
EEMC simple geometry.
A base class for representing clusters of EEMC smd strips.
A base class for describing clusters of EEMC towers.
Definition: StEEmcCluster.h:50
StEEmcCluster & cluster(Int_t sector, Int_t layer, Int_t index)