NAIA  1.0.2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups
TrTrackFill.cpp
Go to the documentation of this file.
1 #include "Containers/TrTrack.h"
3 
4 #include "NtpMaker/NtpTools.h"
5 
6 #include "bcorr.h"
7 
8 #include <iostream>
9 
10 namespace NAIA {
11 using namespace TrTrack;
12 
13 static std::array<unsigned long int, numSpans> patterns = {3, 5, 6, 7, 0, 0, 3};
14 std::array<int, numFits> fitAlgoCode{1, 6, 7};
15 static bool TrackHasExtHits(TrTrackR *trackPtr, Span span) {
16  switch (span) {
17  case Span::InnerOnly:
18  return true;
19  case Span::InnerL1:
20  return trackPtr->TestHitLayerJHasXY(1);
21  case Span::InnerL9:
22  return trackPtr->TestHitLayerJHasXY(9);
23  case Span::FullSpan:
24  return (trackPtr->TestHitLayerJHasXY(1) && trackPtr->TestHitLayerJHasXY(9));
27  case Span::InnerNoMS:
28  return true;
29  default:
30  throw std::runtime_error("Span not supported");
31  }
32 }
33 
34 static constexpr std::array<double, 9> powersOfTen = {1, 1e1, 1e2, 1e3, 1e4, 1e5, 1e6, 1e7, 1e8};
35 
36 void ComputePatterns(TrTrackR *trackPtr) {
38 
39  for (int il = 2; il < 9; il++) {
40  if (!trackPtr->TestHitLayerJ(il))
41  continue;
42 
43  if (il < 7) {
44  patterns[Span::UpperHalfInner] += static_cast<unsigned long int>(9 * powersOfTen[il - 1]);
45  }
46 
47  if (il > 2) {
48  patterns[Span::LowerHalfInner] += static_cast<unsigned long int>(9 * powersOfTen[il - 1]);
49  }
50  }
51 }
52 
53 bool TrTrackBaseData::_FitIDExists(Fit fit, Span span) const {
54  auto itr = _fit_ID.find(fit);
55  if (itr == end(_fit_ID)) {
56  return false;
57  }
58 
59  auto fit_ID_itr = itr->second.find(span);
60  if (fit_ID_itr == end(itr->second)) {
61  return false;
62  }
63 
64  return (fit_ID_itr->second > 0);
65 }
66 
67 Span TrTrackBaseData::_GetBestSpan(Fit fit) const {
68  Span bestspan = _FitIDExists(fit, Span::FullSpan)
70  : (_FitIDExists(fit, Span::InnerL1) > 0
72  : (_FitIDExists(fit, Span::InnerL9) > 0 ? Span::InnerL9 : Span::InnerOnly));
73  return bestspan;
74 }
75 
77  int refit;
78  float mass;
79  int charge;
80 };
81 
82 ReFitParameters InitTrkReFit(float inner_charge, bool _isMC, float production_charge) {
83  ReFitParameters pars{};
84 
85  pars.charge = static_cast<int>(inner_charge + 0.5f);
86  if (pars.charge < 1)
87  pars.charge = 1;
88  pars.mass = TrFit::Mproton; // Proton
89  if (pars.charge >= 2)
90  pars.mass = TrFit::Mhelium / 2.0f * pars.charge; // Helium+Ion
91 
92  if (!_isMC) { // Data
93  if (pars.charge == static_cast<int>(production_charge + 0.5f))
94  pars.refit = 0;
95  else
96  pars.refit = 3;
97  } else {
98  pars.refit = 3; // MC
99  }
100  return pars;
101 }
102 
103 bool TrTrackBaseData::Fill(TrTrackR *trackPtr, TrTrackFillType type) {
104 
105  // some helper default variables
106  int temp_fit_ID = 0;
107  if (type == TrTrackFillType::Standalone) {
108  _beta = 1.0f;
109  temp_fit_ID = -1;
110  }
111 
112  // New Charge-refit Logic from Qi
113  float tmp_inner_charge = trackPtr->GetQ_all(_beta, temp_fit_ID).Mean;
114  if (tmp_inner_charge > 1.5) { // more accurate HighZ charge
115  if (trackPtr->GetQYJ_all(2, _beta, temp_fit_ID).InnerQ > 8.5)
116  tmp_inner_charge = trackPtr->GetQYJ_all(2, _beta, temp_fit_ID).InnerQ;
117  }
118 
119  FitCharge = tmp_inner_charge;
120 
121  auto fitPars = InitTrkReFit(tmp_inner_charge, _isMC, FitCharge);
122  _tmpCharge = fitPars.charge;
123 
124  ComputePatterns(trackPtr);
125 
126  // Rigidity
127  for (auto fit : fitTypes) {
128  // Kalman with electron mass hyp. to be done in dedicated fill method
129  if (fit == Fit::KalmanElectron)
130  continue;
131 
132  for (auto span : spanTypes) {
133  if (type == TrTrackFillType::Standalone) {
134  switch (span) {
137  case Span::InnerL9:
138  case Span::InnerNoMS:
139  // for standalone we only consider InnerOnly, InnerL1 and FullSpan
140  continue;
141  break;
142  default:
143  break;
144  }
145  }
146 
147  if (TrackHasExtHits(trackPtr, span)) {
148  Logging::MuteOutput(); // this can get quite verbose...
149  _fit_ID[fit][span] = trackPtr->iTrTrackPar(fitAlgoCode[fit], static_cast<int>(patterns[span]),
150  30 + fitPars.refit, fitPars.mass, _tmpCharge);
152  if (_fit_ID[fit][span] > 0) {
153  double rigidity;
154  AMSPlane pl(TVector3(0, 0, 0), TVector3(1, 0, 0), TVector3(0, 1, 0));
155  trackPtr->Interpolate(pl, rigidity, _fit_ID[fit][span]);
156  Rigidity[fit][span] = static_cast<float>(rigidity);
157  TrChiSq[fit][span][Side::X] =
158  static_cast<float>(trackPtr->GetChisqX(_fit_ID[fit][span]) / trackPtr->GetNdofX(_fit_ID[fit][span]));
159  TrChiSq[fit][span][Side::Y] =
160  static_cast<float>(trackPtr->GetChisqY(_fit_ID[fit][span]) / trackPtr->GetNdofY(_fit_ID[fit][span]));
161  }
162  }
163  }
164  }
165  trackPtr->RecalcHitCoordinates(0, false, false, _tmpCharge); // using default fit and inner tracker charge to restore
166  // coordinate
167 
168  int base_fit_ID = FitIDExists(Fit::Choutko, Span::InnerOnly) ? _fit_ID[Fit::Choutko][Span::InnerOnly] : -1;
169  if (type == TrTrackFillType::Standalone) {
170  base_fit_ID = -1;
171  }
172 
173  // Charge
174  // - Inner tracker
175  Charge[ChargeRecoType::STD] = trackPtr->GetQ_all(_beta, base_fit_ID).Mean;
176  Charge[ChargeRecoType::HL] = trackPtr->GetQH_all(2, _beta, base_fit_ID).Mean;
177  // Charge[ChargeRecoType::YJ] does not support "global" charge;
178  ChargeRMS[ChargeRecoType::STD] = trackPtr->GetQ_all(_beta, base_fit_ID).RMS;
179  ChargeRMS[ChargeRecoType::HL] = trackPtr->GetQH_all(2, _beta, base_fit_ID).RMS;
180  // ChargeRMS[ChargeRecoType::YJ] does not support "global" charge;
181  InnerCharge[ChargeRecoType::STD] = trackPtr->GetInnerQ_all(_beta, base_fit_ID).Mean;
182  InnerCharge[ChargeRecoType::HL] = trackPtr->GetInnerQH_all(2, _beta, base_fit_ID).Mean;
183  InnerCharge[ChargeRecoType::YJ] = trackPtr->GetQYJ_all(2, _beta, base_fit_ID).InnerQ;
184  InnerChargeRMS[ChargeRecoType::STD] = trackPtr->GetInnerQ_all(_beta, base_fit_ID).RMS;
185  InnerChargeRMS[ChargeRecoType::HL] = trackPtr->GetInnerQH_all(2, _beta, base_fit_ID).RMS;
186  InnerChargeRMS[ChargeRecoType::YJ] = trackPtr->GetQYJ_all(2, _beta, base_fit_ID).InnerQRMS;
187 
188  // geometry and position
189  for (int ijl = 0; ijl < 9; ijl++) {
190  if (!trackPtr->GetHitLJ(ijl + 1))
191  continue;
192  AMSPlaneM plm = trackPtr->GetHitCooLJN(ijl + 1);
193  TVector3 mglob = plm.getMGlobal();
194  if (trackPtr->GetHitLJ(ijl + 1)->GetXCluster())
195  TrTrackHitPos[ijl][0] = static_cast<float>(mglob.x());
196  if (trackPtr->GetHitLJ(ijl + 1)->GetYCluster())
197  TrTrackHitPos[ijl][1] = static_cast<float>(mglob.y());
198  if (trackPtr->GetHitLJ(ijl + 1))
199  TrTrackHitPos[ijl][2] = static_cast<float>(mglob.z());
200  }
201 
202  if (type == TrTrackFillType::SecondTrack) {
203  return true;
204  }
205 
206  // - single layers
207  for (int ijl = 0; ijl < 9; ijl++) {
208  Fit fit = Fit::Choutko;
209  Span span = Span::InnerOnly;
210 
211  if (trackPtr->GetHitLJ(ijl + 1)) {
212  LayerChargeStatus[ijl] = trackPtr->GetHitLJ(ijl + 1)->GetQStatus();
213 
214  LayerChargeXY[ijl][ChargeRecoType::STD] = trackPtr->GetHitLJ(ijl + 1)->GetQ(2, _beta, Rigidity[fit][span]);
215  LayerChargeXY[ijl][ChargeRecoType::HL] = trackPtr->GetLayerJQH(ijl + 1, 2, _beta, _fit_ID[fit][span]);
216  LayerChargeXY[ijl][ChargeRecoType::YJ] = trackPtr->GetLayerQYJ(ijl + 1, 2, _beta, _fit_ID[fit][span]);
217  }
218  }
219 
220  for (const auto fitPos : fitPositionHeights) {
221  // Define a Plane from the Hits Coordinates
222  AMSPlaneM plm_res;
223  TVector3 mglob;
224  if (fitPos <= TrTrack::FitPositionHeight::Layer9) { // Just for the Layers
225  plm_res = trackPtr->GetHitCooLJN(fitPos + 1);
226  mglob = plm_res.getMGlobal();
227  }
228  for (auto fit : fitTypes) {
229  for (auto span : spanTypes) {
230  if (type == TrTrackFillType::Standalone) {
231  switch (span) {
234  case Span::InnerL9:
235  case Span::InnerNoMS:
236  // for standalone we only consider InnerOnly, InnerL1 and FullSpan
237  continue;
238  break;
239  default:
240  break;
241  }
242  }
243 
244  if (FitIDExists(fit, span)) {
245  int fit_ID = _fit_ID.at(fit).at(span);
246  if (fit_ID < 0)
247  continue;
248 
249  double rigidity;
250 
251  // Define a Plane from a given Nominal HeightZ to store the FitPositions
252  AMSPlane plm_fitpos(TVector3(0, 0, fitPositionHeightZ[fitPos]), TVector3(1, 0, 0), TVector3(0, 1, 0));
253  trackPtr->Interpolate(plm_fitpos, rigidity, fit_ID);
254  TVector3 pglob_fitpos = plm_fitpos.getP();
255  TrTrackFitPos[fitPos][fit][span][Side::X] = static_cast<float>(pglob_fitpos.x());
256  TrTrackFitPos[fitPos][fit][span][Side::Y] = static_cast<float>(pglob_fitpos.y());
257  }
258  }
259  }
260  }
261 
262  return true;
263 }
264 
265 bool TrTrackPlusData::Fill(TrTrackR *trackPtr) {
266  const auto &_beta = trkBase->_beta;
267  const auto &_tmpCharge = trkBase->_tmpCharge;
268 
269  if (trkBase->InnerCharge.empty())
270  return false;
271 
272  auto *pev = AMSEventR::Head();
273 
274  int refit = ((trkBase->_isMC) || (_tmpCharge != trackPtr->GetAdvancedFitCharge())) ? 3 : 1;
275  float fitMass = (_tmpCharge >= 2) ? TrFit::Mhelium / 2 * _tmpCharge : TrFit::Mproton;
276 
277  auto getPartialPattern = [](TrTrackR *track, unsigned int jLayer) {
278  unsigned int pattern = 0;
279  for (unsigned int ijl = 1; ijl < 10; ijl++) {
280  if (track->TestHitLayerJ(ijl) && ijl != jLayer)
281  pattern += 9 * powersOfTen[ijl - 1];
282  }
283  return pattern;
284  };
285 
286  for (unsigned int ijl = 2; ijl < 9; ijl++) {
287  TrackFeetDistance[ijl - 1] = pev->GetTkFeetDist(ijl, trackPtr);
288  }
289 
290  // Rigidity
291  for (auto fit : fitTypes) {
292 
293  // Kalman with electron mass hyp. to be done in dedicated fill method
294  if (fit == Fit::KalmanElectron)
295  continue;
296 
297  for (auto span : spanTypes) {
298  if (trkBase->FitIDExists(fit, span)) {
299  _fit_ID[fit][span] =
300  trackPtr->iTrTrackPar(fitAlgoCode[fit], static_cast<int>(patterns[span]), 30 + refit, fitMass, _tmpCharge);
301  if (_fit_ID[fit][span] < 0)
302  continue;
303 
304  double rigidity;
305  if (fit == Fit::Kalman) {
306  // TOI rigidity for both downward and upward going particles.
307  float zpl = (_beta > 0) ? 195 : -195;
308  AMSPlane pl_TOI(TVector3(0, 0, zpl), TVector3(1, 0, 0), TVector3(0, 1, 0));
309  trackPtr->Interpolate(pl_TOI, rigidity, _fit_ID[fit][span], fitMass, _tmpCharge, 1, (_beta > 0) ? 1 : -1);
310  RigidityTOI[fit][span] = static_cast<float>(rigidity);
311  // Rigidity at RICH
312  AMSPlane pl_RICH(TVector3(0, 0, -70), TVector3(1, 0, 0), TVector3(0, 1, 0));
313  trackPtr->Interpolate(pl_RICH, rigidity, _fit_ID[fit][span], fitMass, _tmpCharge, 1);
314  RigidityRICH[fit][span] = static_cast<float>(rigidity);
315  }
316  // Theta and Phi
317  AMSPlane pl(TVector3(0, 0, 0), TVector3(1, 0, 0), TVector3(0, 1, 0));
318  trackPtr->Interpolate(pl, rigidity, _fit_ID[fit][span]);
319  Theta[fit][span] = static_cast<float>(pl.getD().Theta());
320  Phi[fit][span] = static_cast<float>(pl.getD().Phi());
321 
322  const TrTrackPar &trackPar = trackPtr->gTrTrackPar(_fit_ID[fit][span]);
323  InvRigErr[fit][span] = static_cast<float>(trackPar.ErrRinv);
324  }
325  }
326  // using default fit and inner tracker charge to restore coordinate
327  trackPtr->RecalcHitCoordinates(0, 0, 0, _tmpCharge);
328 
329  // doesn't make sense to try if inner only fit failed...
330  if (trkBase->FitIDExists(fit, Span::InnerOnly)) {
331  for (unsigned int ijl = 1; ijl < 10; ijl++) {
332  if (!trackPtr->TestHitLayerJ(ijl))
333  continue;
334  auto partialPattern = getPartialPattern(trackPtr, ijl);
335 
336  int pfit_ID = trackPtr->iTrTrackPar(fitAlgoCode[fit], partialPattern, 30 + refit, fitMass, _tmpCharge);
337  if (pfit_ID < 0)
338  continue;
339 
340  const TrTrackPar &partialTrackPar = trackPtr->gTrTrackPar(pfit_ID);
341  PartialRigidity[ijl - 1][fit] = partialTrackPar.Rigidity;
342  PartialInvRigErr[ijl - 1][fit] = partialTrackPar.ErrRinv;
343  PartialTrChiSq[ijl - 1][fit][Side::X] = static_cast<float>(partialTrackPar.ChisqX / partialTrackPar.NdofX);
344  PartialTrChiSq[ijl - 1][fit][Side::Y] = static_cast<float>(partialTrackPar.ChisqY / partialTrackPar.NdofY);
345 
346  // Define a Plane from a given Nominal HeightZ to store the Partial FitPositions
347  double rigidity;
348  AMSPlane plm_fitpos(TVector3(0, 0, fitPositionHeightZ[ijl - 1]), TVector3(1, 0, 0), TVector3(0, 1, 0));
349  trackPtr->Interpolate(plm_fitpos, rigidity, pfit_ID);
350  TVector3 pglob_fitpos = plm_fitpos.getP();
351  PartialTrTrackFitPos[ijl - 1][fit][Side::X] = static_cast<float>(pglob_fitpos.x());
352  PartialTrTrackFitPos[ijl - 1][fit][Side::Y] = static_cast<float>(pglob_fitpos.y());
353 
354  // Define a Plane from the Hits Coordinates to calculate the Partial Residuals
355  // by using the real Height of the event
356  AMSPlaneM plm_res = trackPtr->GetHitCooLJN(ijl + 1);
357  TVector3 mglob = plm_res.getMGlobal();
358  trackPtr->Interpolate(plm_res, rigidity, pfit_ID);
359  TVector3 pglob_res = plm_res.getP();
360  PartialTrTrackResidual[ijl - 1][fit][Side::X] = static_cast<float>(mglob.x() - pglob_res.x());
361  PartialTrTrackResidual[ijl - 1][fit][Side::Y] = static_cast<float>(mglob.y() - pglob_res.y());
362  }
363  }
364  }
365  trackPtr->RecalcHitCoordinates(0, 0, 0, _tmpCharge); // using default fit and inner tracker charge to restore
366  // coordinate
367 
368  auto dir_fit = TrTrack::Fit::Choutko;
369  auto dir_span = trkBase->GetBestSpan(dir_fit);
370  if (trkBase->FitIDExists(dir_fit, dir_span)) {
371  AMSDir trk_dir{Theta[dir_fit][dir_span], Phi[dir_fit][dir_span]};
372  // Once again, I come to you to complain about the worst API ever designed: gbatch
373  // 5 LOC when 2 would have been enough
374  double tmp;
375  AMSEventR::Head()->GetStoermerCutoff(tmp, -1, trk_dir);
376  DirectionalStoermerCutoff[0] = tmp;
377  AMSEventR::Head()->GetStoermerCutoff(tmp, 1, trk_dir);
378  DirectionalStoermerCutoff[1] = tmp;
379  }
380 
381  // - single layers
382  constexpr Fit base_fit = Fit::Choutko;
383  constexpr Span base_span = Span::InnerOnly;
384  if (trkBase->FitIDExists(base_fit, base_span)) {
385  int base_fit_ID = _fit_ID.at(base_fit).at(base_span);
386 
387  for (int ijl = 0; ijl < 9; ijl++) {
388  if (trackPtr->GetHitLJ(ijl + 1)) {
389  float rigidity = (base_fit_ID > 0) ? trkBase->Rigidity.at(base_fit).at(base_span) : 0;
390 
391  LayerCharge[ijl][ChargeRecoType::STD][Side::X] = trackPtr->GetHitLJ(ijl + 1)->GetQ(0, _beta, rigidity);
392  LayerCharge[ijl][ChargeRecoType::HL][Side::X] = trackPtr->GetLayerJQH(ijl + 1, 0, _beta, base_fit_ID);
393  LayerCharge[ijl][ChargeRecoType::YJ][Side::X] = trackPtr->GetLayerQYJ(ijl + 1, 0, _beta, base_fit_ID);
394 
395  if (trackPtr->GetHitLJ(ijl + 1)->GetXCluster())
396  LayerEdep[ijl][Side::X] = trackPtr->GetHitLJ(ijl + 1)->GetXCluster()->GetEdep();
397  if (trackPtr->GetHitLJ(ijl + 1)->GetYCluster())
398  LayerEdep[ijl][Side::Y] = trackPtr->GetHitLJ(ijl + 1)->GetYCluster()->GetEdep();
399 
400  LayerCharge[ijl][ChargeRecoType::STD][Side::Y] = trackPtr->GetHitLJ(ijl + 1)->GetQ(1, _beta, rigidity);
401  LayerCharge[ijl][ChargeRecoType::HL][Side::Y] = trackPtr->GetLayerJQH(ijl + 1, 1, _beta, base_fit_ID);
402  LayerCharge[ijl][ChargeRecoType::YJ][Side::Y] = trackPtr->GetLayerQYJ(ijl + 1, 1, _beta, base_fit_ID);
403  }
404  }
405  }
406 
407  for (const auto fitPos : fitPositionHeights) {
408  // Define a Plane from the Hits Coordinates
409  AMSPlaneM plm_res;
410  TVector3 mglob;
411  if (fitPos <= TrTrack::FitPositionHeight::Layer9) { // Just for the Layers
412  plm_res = trackPtr->GetHitCooLJN(fitPos + 1);
413  mglob = plm_res.getMGlobal();
414  }
415  for (auto fit : fitTypes) {
416  for (auto span : spanTypes) {
417  if (trkBase->FitIDExists(fit, span)) {
418  int fit_ID = _fit_ID.at(fit).at(span);
419  if (fit_ID < 0)
420  continue;
421  double rigidity;
422 
423  // Define a Plane from a given Nominal HeightZ to store the FitPositions
424  AMSPlane plm_fitpos(TVector3(0, 0, fitPositionHeightZ[fitPos]), TVector3(1, 0, 0), TVector3(0, 1, 0));
425  trackPtr->Interpolate(plm_fitpos, rigidity, fit_ID);
426  TVector3 pglob_fitpos = plm_fitpos.getP();
427 
428  // From the Plane defined by the Hits Cooordinates, calculate the Residuals using the real Height associated
429  // with the event
430  if (fitPos <= TrTrack::FitPositionHeight::Layer9) { // Just for the Layers
431  if (!trackPtr->TestHitLayerJ(fitPos + 1))
432  continue;
433  trackPtr->Interpolate(plm_res, rigidity, fit_ID);
434  TVector3 pglob_res = plm_res.getP();
435  TrTrackResidual[fitPos][fit][span][Side::X] = static_cast<float>(mglob.x() - pglob_res.x());
436  TrTrackResidual[fitPos][fit][span][Side::Y] = static_cast<float>(mglob.y() - pglob_res.y());
437  }
438  }
439  }
440  }
441  }
442 
443  static constexpr std::array<float, 5> window = {0.1, 1., 2., 5., 10.};
444 
445  // from dbar code
446  for (int jLayer = 1; jLayer <= 9; jLayer++) {
447 
448  ClusterSignalRatio[jLayer - 1] = pev->GetTrackerRawSignalRatio(jLayer, 10);
449 
450  // identify the clusters used in trtrack
451  TrClusterR *trackClusterPtrX = trackPtr->GetHitLJ(jLayer) ? trackPtr->GetHitLJ(jLayer)->GetXCluster() : nullptr;
452  TrClusterR *trackClusterPtrY = trackPtr->GetHitLJ(jLayer) ? trackPtr->GetHitLJ(jLayer)->GetYCluster() : nullptr;
453 
454  // Get track interpolation to jLayer
455  double rigidity;
456  AMSPlane plm(TVector3(0, 0, fitPositionHeightZ[jLayer - 1]), TVector3(1, 0, 0), TVector3(0, 1, 0));
457  trackPtr->Interpolate(plm, rigidity, _fit_ID[Fit::Kalman][Span::InnerOnly]);
458  TVector3 pglob = plm.getP();
459  AMSPoint fitcoo = AMSPoint(pglob.x(), pglob.y(), pglob.z());
460 
461  // TODO: Check if zero threshold is correct
462  static constexpr float noiseThreshold = 0;
463 
464  for (int icl = 0; icl < pev->nTrCluster(); icl++) {
465  auto *cluster = pev->pTrCluster(icl);
466 
467  if (!cluster || cluster->GetLayerJ() != jLayer)
468  continue;
469 
470  float edep = 1000 * cluster->GetEdep();
471  if (cluster == trackClusterPtrX) {
472  NClusters[jLayer - 1][DistanceFromTrack::OnTrack][Side::X]++;
473  ClustersEdep[jLayer - 1][DistanceFromTrack::OnTrack][Side::X] += edep;
474  continue;
475  }
476  if (cluster == trackClusterPtrY) {
477  NClusters[jLayer - 1][DistanceFromTrack::OnTrack][Side::Y]++;
478  ClustersEdep[jLayer - 1][DistanceFromTrack::OnTrack][Side::Y] += edep;
479  continue;
480  }
481 
482  if (edep < noiseThreshold)
483  continue; // apply a threshold to account for noise
484 
485  // Deal with multiplicities: Choose closest to track
486  float clusterDistanceToTrack = std::numeric_limits<float>::max();
487  for (int im = 0; im < cluster->GetMultiplicity(); im++) {
488  AMSPlaneM pl_mult = cluster->GetGCoordN(im);
489  TVector3 mglob_mult = pl_mult.getMGlobal();
490 
491  clusterDistanceToTrack =
492  std::min(clusterDistanceToTrack,
493  fabs(static_cast<float>(fitcoo[cluster->GetSide()] - mglob_mult[cluster->GetSide()])));
494  }
495 
496  Side side = cluster->GetSide() == 0 ? Side::X : Side::Y;
497 
498  NClusters[jLayer - 1][DistanceFromTrack::AllLayer][side]++;
499  ClustersEdep[jLayer - 1][DistanceFromTrack::AllLayer][side] += edep;
500  if (edep > MaxClusterEdep[jLayer - 1][side]) {
501  MaxClusterEdep[jLayer - 1][side] = edep;
502  MaxClusterDistance[jLayer - 1][side] = clusterDistanceToTrack;
503  }
504 
505  // FIXME: I don't really like using an int instead of the right enum
506  for (unsigned int iw = 0; iw < window.size(); iw++) {
507  if (std::fabs(clusterDistanceToTrack) < window[iw]) {
508  NClusters[jLayer - 1][static_cast<DistanceFromTrack>(iw + 1)][side]++;
509  ClustersEdep[jLayer - 1][static_cast<DistanceFromTrack>(iw + 1)][side] += edep;
510  }
511  }
512  }
513  }
514  return true;
515 }
516 
517 bool TrTrackBaseData::FillElectronVars(TrTrackR *trackPtr, float zEcalCOG, bool refitKalman) {
518  // Rigidity
519  auto fit = Fit::KalmanElectron;
520  auto span = _GetBestSpan(Fit::Kalman);
521 
522  if (TrackHasExtHits(trackPtr, span) && refitKalman) {
523  Logging::MuteOutput(); // this can get quite verbose...
524  _fit_ID[fit][span] = trackPtr->iTrTrackPar(fitAlgoCode[fit], static_cast<int>(patterns[span]), 32,
525  static_cast<float>(TrFit::Melectron), 1);
527  if (_fit_ID[fit][span] > 0) {
528  double rigidity;
529  AMSPlane pl(TVector3(0, 0, 0), TVector3(1, 0, 0), TVector3(0, 1, 0));
530  trackPtr->Interpolate(pl, rigidity, _fit_ID[fit][span], TrFit::Melectron, 1);
531  Rigidity[fit][span] = static_cast<float>(rigidity);
532  TrChiSq[fit][span][Side::X] =
533  static_cast<float>(trackPtr->GetChisqX(_fit_ID[fit][span]) / trackPtr->GetNdofX(_fit_ID[fit][span]));
534  TrChiSq[fit][span][Side::Y] =
535  static_cast<float>(trackPtr->GetChisqY(_fit_ID[fit][span]) / trackPtr->GetNdofY(_fit_ID[fit][span]));
536  }
537  } else {
538  return false;
539  }
540 
541  if (zEcalCOG < std::numeric_limits<float>::max()) {
542  for (auto fit : fitTypes) {
543  for (auto span : spanTypes) {
544  if (FitIDExists(fit, span)) {
545  int fit_ID = _fit_ID.at(fit).at(span);
546  double rigidity;
547  AMSPlane plm(TVector3(0, 0, zEcalCOG), TVector3(1, 0, 0), TVector3(0, 1, 0));
548  trackPtr->Interpolate(plm, rigidity, fit_ID);
549  TVector3 pglob = plm.getP();
550  TrTrackFitPos[FitPositionHeight::EcalCOG][fit][span][Side::X] = static_cast<float>(pglob.x());
551  TrTrackFitPos[FitPositionHeight::EcalCOG][fit][span][Side::Y] = static_cast<float>(pglob.y());
552  }
553  }
554  }
555  }
556 
557  return true;
558 }
559 
560 bool TrTrackPlusData::FillElectronVars(TrTrackR *trackPtr, bool refitKalman) {
561  const auto &base_fit_ID = trkBase->_fit_ID;
562  const auto &_beta = trkBase->_beta;
563 
564  {
565  auto fit = Fit::KalmanElectron;
566  auto span = trkBase->GetBestSpan(Fit::Kalman);
567  if (trkBase->FitIDExists(fit, span) && refitKalman) {
568  int fit_ID = base_fit_ID.at(fit).at(span);
569  // TOI rigidity for both downward and upward going particles.
570  double rigidity;
571  float zpl = (_beta > 0) ? 195 : -195;
572  AMSPlane pl_TOI(TVector3(0, 0, zpl), TVector3(1, 0, 0), TVector3(0, 1, 0));
573  trackPtr->Interpolate(pl_TOI, rigidity, fit_ID, TrFit::Melectron, 1, 1, (_beta > 0) ? 1 : -1);
574  RigidityTOI[fit][span] = static_cast<float>(rigidity);
575  // Rigidity at RICH
576  AMSPlane pl_RICH(TVector3(0, 0, -70), TVector3(1, 0, 0), TVector3(0, 1, 0));
577  trackPtr->Interpolate(pl_RICH, rigidity, fit_ID, TrFit::Melectron, 1, 1);
578  RigidityRICH[fit][span] = static_cast<float>(rigidity);
579  // Theta and Phi
580  AMSPlane pl(TVector3(0, 0, 0), TVector3(1, 0, 0), TVector3(0, 1, 0));
581  trackPtr->Interpolate(pl, rigidity, fit_ID, TrFit::Melectron, 1);
582  Theta[fit][span] = static_cast<float>(pl.getD().Theta());
583  Phi[fit][span] = static_cast<float>(pl.getD().Phi());
584 
585  const TrTrackPar &trackPar = trackPtr->gTrTrackPar(fit_ID);
586  InvRigErr[fit][span] = static_cast<float>(trackPar.ErrRinv);
587  }
588  }
589 
590  return true;
591 }
592 } // namespace NAIA
Hu Liu reconstruction.
Definition: Utils.h:92
Track constructed with the upper part of the inner tracker (layers 2 to 6)
Definition: Utils.h:162
static bool TrackHasExtHits(TrTrackR *trackPtr, Span span)
Definition: TrTrackFill.cpp:15
Track constructed with the upper part of the inner tracker (layers 3 to 8)
Definition: Utils.h:163
constexpr std::array< Span, numSpans > spanTypes
Definition: Utils.h:167
void UnmuteOutput()
Definition: Logging.cpp:36
constexpr std::array< float, numFitPositionHeights > fitPositionHeightZ
Definition: Utils.h:135
void ComputePatterns(TrTrackR *trackPtr)
Definition: TrTrackFill.cpp:36
constexpr std::array< Fit, numFits > fitTypes
Definition: Utils.h:186
Track constructed with inner tracker + layer9 hits.
Definition: Utils.h:160
GenFit kalman filter track fit.
Definition: Utils.h:181
TrTrack container class description.
std::array< int, numFits > fitAlgoCode
Definition: TrTrackFill.cpp:14
ReFitParameters InitTrkReFit(float inner_charge, bool _isMC, float production_charge)
Definition: TrTrackFill.cpp:82
DistanceFromTrack
Definition: Utils.h:214
void MuteOutput()
Definition: Logging.cpp:22
Track constructed without correcting for multiple scattering.
Definition: Utils.h:164
GenFit kalman filter track fit assuming electron mass.
Definition: Utils.h:183
static constexpr std::array< double, 9 > powersOfTen
Definition: TrTrackFill.cpp:34
NAIAChain::EventItr end(NAIAChain &chain)
Definition: NAIAChain.h:298
static std::array< unsigned long int, numSpans > patterns
Definition: TrTrackFill.cpp:13
Yi Jia reconstruction.
Definition: Utils.h:93
Standard tracker charge reconstruction.
Definition: Utils.h:91
constexpr std::array< FitPositionHeight, numFitPositionHeights > fitPositionHeights
Definition: Utils.h:123
standard track fit
Definition: Utils.h:180