8 #include <FairLogger.h>
10 #include <TGeoPhysicalNode.h>
12 #include <TClonesArray.h>
14 #include <TGraphErrors.h>
51 SetNameTitle(Form(
"TrdRecT%d", mod),
52 "Reconstructor for triangular read-out.");
65 if (
CWRITE()) cout <<
"add @" <<
id <<
" " <<
d->ToString();
67 Int_t ch =
d->GetAddressChannel(), col, row =
GetPadRowCol(ch, col), dtime;
68 Double_t t, r =
d->GetCharge(t, dtime);
69 Int_t tm =
d->GetTimeDAQ() -
fT0, terminator(0);
79 "row[%2d] col[%2d] tm[%2d] terminator[%d]\n", row, col, tm, terminator);
83 std::map<Int_t, std::list<CbmTrdCluster*>>::iterator it =
fBuffer.find(row);
86 Bool_t kINSERT(kFALSE);
87 std::list<CbmTrdCluster*>::iterator itc =
fBuffer[row].begin();
88 for (; itc !=
fBuffer[row].end(); itc++) {
89 if (
CWRITE()) cout << (*itc)->ToString();
91 UShort_t tc = (*itc)->GetStartTime();
97 if (
CWRITE()) printf(
"match time dt=%d\n", dt);
98 if ((*itc)->IsChannelInRange(ch) == 0) {
99 if (!(*itc)->AddDigi(
id, ch, terminator, dt))
break;
101 if (
CWRITE()) cout <<
" => Cl (Ad) " << (*itc)->ToString();
105 if (
CWRITE()) printf(
"break for time dt=%d\n", dt);
124 else if (terminator > 0)
133 else if (terminator > 0)
144 for (std::map<Int_t, std::list<CbmTrdCluster*>>::const_iterator ir =
148 for (std::list<CbmTrdCluster*>::const_iterator itc = (*ir).second.cbegin();
149 itc != (*ir).second.cend();
151 nch += (*itc)->GetNCols();
162 std::list<CbmTrdCluster*>::iterator itc0, itc1;
163 for (std::map<Int_t, std::list<CbmTrdCluster*>>::iterator ir =
167 itc0 = (*ir).second.begin();
168 while ((*ir).second.size() > 1
169 && itc0 != (*ir).second.end()) {
173 Bool_t kMERGE = kFALSE;
174 while (itc1 != (*ir).second.end()) {
176 cout <<
" base cl[0] : " << (*itc0)->ToString()
177 <<
" + cl[1] : " << (*itc1)->ToString();
178 if ((*itc0)->Merge((*itc1))) {
179 if (
CWRITE()) cout <<
" SUM : " << (*itc0)->ToString();
182 itc1 = (*ir).second.erase(itc1);
183 if (itc1 == (*ir).second.end())
break;
190 for (itc0 = (*ir).second.begin(); itc0 != (*ir).second.end(); itc0++) {
236 std::vector<const CbmTrdDigi*>* digis) {
238 LOG(info) << GetName() <<
"::MakeHit: Init static helpers. ";
239 fgEdep =
new TGraphErrors;
240 fgEdep->SetLineColor(kBlue);
242 fgT =
new TGraphErrors;
243 fgT->SetLineColor(kBlue);
244 fgT->SetLineWidth(2);
245 fgPRF =
new TF1(
"prf",
"[0]*exp(-0.5*((x-[1])/[2])**2)", -10, 10);
246 fgPRF->SetLineColor(kRed);
247 fgPRF->SetParNames(
"E",
"x",
"prf");
252 cvs =
new TCanvas(
"c",
"TRD Anode Hypothesis", 10, 600, 1000, 500);
253 cvs->Divide(2, 1, 1.e-5, 1.e-5);
254 TVirtualPad* vp = cvs->cd(1);
255 vp->SetLeftMargin(0.06904908);
256 vp->SetRightMargin(0.009969325);
257 vp->SetTopMargin(0.01402806);
259 vp->SetLeftMargin(0.06904908);
260 vp->SetRightMargin(0.009969325);
261 vp->SetTopMargin(0.01402806);
262 hf =
new TH1I(
"hf",
";x [pw];s [ADC chs]", 100, -3, 3);
263 hf->GetYaxis()->SetRangeUser(-50, 4500);
270 vector<Bool_t> vmask(digis->size(), 0);
271 vector<CbmTrdDigi*> vdgM;
274 for (vector<const CbmTrdDigi*>::iterator
i = digis->begin();
277 cout << (*i)->ToString();
283 Int_t n0(0), ovf(0), cM;
284 if (!(n0 =
LoadDigis(digis, &vdgM, &vmask, t0, cM))) {
286 for (vector<const CbmTrdDigi*>::iterator
i = digis->begin();
289 cout << (*i)->ToString();
305 for (Int_t is(1); is <= n0; is++) {
337 if (!lr && (n0 % 2)) tr = (LS < S ? -1 : 1);
339 Double_t dx(0.), dy(0.), edx(0.21650635),
367 else if (!tM && !lr) {
371 else if (tM && !lr) {
375 else if (!tM && lr) {
377 dy = cM ? 0.5 : -0.5;
389 for (UInt_t idx(0); idx <
vx.size(); idx++)
393 Int_t ishift = Int_t(dx - 0.5) + 1;
396 for (UInt_t idx(0); idx <
vx.size(); idx++)
407 if ((n0 == 5 && ((tM && !lr) || (!tM && lr))) ||
408 n0 == 4 || (n0 == 3 && ((tM && !lr) || (!tM && lr != 0))))
414 LOG(warn) << GetName() <<
"::MakeHit : Idx " << ii
415 <<
" outside range for displacement " << dx <<
".";
418 i0 = TMath::Max(0, ii - 1);
426 xcorr = 0.1 * (b + a * dx);
432 else if (dx < -0.5 * fDigiPar->GetPadSizeX(0))
439 if (dy < -0.5 * fDigiPar->GetPadSizeY(0)) {
446 Float_t fdy(1.), yoff(0.);
460 if ((!tM && lr == 1) || (tM && lr == -1)) yoff *= -1;
474 if ((!tM && lr == 1) || (tM && lr == -1)) yoff *= -1;
481 else if (dy < -0.5 * fDigiPar->GetPadSizeY(0))
487 for (; ia <=
NANODE; ia++) {
488 ya = -1.35 + ia * 0.3;
489 if (dy > ya + 0.15)
continue;
494 Double_t parX[] = {0.713724, -0.318667, 0.0366036};
495 Int_t nex = TMath::Min(n0, 7);
496 edx = parX[0] + parX[1] * nex + parX[2] * nex * nex;
497 Double_t parY[] = {0.0886413, 0., 0.0435141};
498 edy = parY[0] + parY[2] * dy * dy;
501 printf(
"row[%2d] col[%2d] sz[%d%c] M[%d%c] dx[mm]=%6.3f dy[mm]=%6.3f "
502 "t0[clk]=%llu OVF[%c]\n",
506 (lr ? (lr < 0 ?
'L' :
'R') :
'C'),
513 for (UInt_t idx(0); idx <
vs.size(); idx++) {
514 printf(
"%2d%cdt[%2d] s[ADC]=%6.1f+-%6.1f x[pw]=%5.2f+-%5.2f\n",
516 (UInt_t(nL) == idx ?
'*' :
' '),
526 for (UInt_t idx(0); idx <
vs.size(); idx++) {
535 Double_t xc =
vx[n0 + 2];
536 for (Int_t ip(
vs.size()); ip < fgEdep->GetN(); ip++) {
539 fgEdep->SetPoint(ip, xc, 0);
540 fgEdep->SetPointError(ip, 0., 300);
544 Double_t e(0.), chi(100), xlo(*
vx.begin()), xhi(*
vx.rbegin());
547 fgPRF->SetParameter(2, 0.65);
548 fgPRF->SetParLimits(2, 0.45, 10.5);
549 fgEdep->Fit(
fgPRF,
"QBN",
"goff", xlo - 0.5, xhi + 0.5);
550 if (!
fgPRF->GetNDF())
return NULL;
551 chi =
fgPRF->GetChisquare() /
fgPRF->GetNDF();
552 e =
fgPRF->Integral(xlo - 0.5, xhi + 0.5);
555 Float_t gain0 = 210.21387;
570 Float_t gain = gain0;
574 TVector3 local_pad, local_pad_err;
578 Double_t local[3] = {local_pad[0] + dx, local_pad[1] + dy, local_pad[2]},
579 global[3], globalErr[3] = {edx, edy, 0.};
583 for (Int_t idx(1); idx <= n0; idx++) {
587 fgT->SetPoint(idx - 1,
vx[idx],
vt[idx] - dtFEE);
590 for (Int_t ip(n0); ip <
fgT->GetN(); ip++) {
591 fgT->SetPoint(ip, xc, 0);
598 if (n0 > 1 && (
fgT->Fit(
"pol1",
"QC",
"goff") == 0)) {
599 TF1*
f =
fgT->GetFunction(
"pol1");
600 time =
f->GetParameter(0) -
fgDT[2];
601 if (TMath::IsNaN(time)) time = -21;
606 Double_t rangex(
vx[0] - 0.25), rangeX(
vx[n0 + 2] + 0.25);
609 hf->GetXaxis()->SetRangeUser(rangex, rangeX);
611 "%d[%d] row[%d] col[%2d] an[%+d] m[%+4.2f] s[%4.2f] E[%7.2f] chi2[%7.2f]",
617 fgPRF->GetParameter(1),
618 fgPRF->GetParameter(2),
621 hf->GetXaxis()->SetRangeUser(rangex, rangeX);
622 hf->GetYaxis()->SetRangeUser(-100., 4500);
627 hf = (TH1*) hf->DrawClone(
"p");
628 hf->GetXaxis()->SetRangeUser(rangex, rangeX);
629 hf->GetYaxis()->SetRangeUser(-10, 20);
636 cvs->SaveAs(Form(
"cl_%02d_A%d.gif", ic, ia));
639 Int_t nofHits =
fHits->GetEntriesFast();
658 Double_t dx(0.), R(0.);
659 for (Int_t ir(1); ir <= n0; ir++) {
660 if (
vxe[ir] > 0)
continue;
662 dx +=
vs[ir] *
vx[ir];
664 if (TMath::Abs(R) > 0)
return dx / R;
665 LOG(warn) << GetName() <<
"::GetDx : Unexpected null sum.";
671 Double_t dy(0.), T(0.);
672 for (Int_t it(1); it <= n0; it++) {
675 dy +=
vs[it] *
vx[it];
678 if (TMath::Abs(T) > 0)
return dy / T;
679 LOG(warn) << GetName() <<
"::GetDy : Unexpected null sum.";
685 vector<CbmTrdDigi*>* vdgM,
686 vector<Bool_t>* vmask,
707 Double_t r, re(100.),
712 Int_t j(0), col0(-1), col1(0);
714 vector<CbmTrdDigi*>::iterator idgM = vdgM->begin();
715 for (vector<const CbmTrdDigi*>::iterator
i = digis->begin();
729 if (ddt < dt0) dt0 = ddt;
733 if (col0 + j != col1) {
734 LOG(error) << GetName()
735 <<
"::LoadDigis : digis in cluster not in increasing order !";
758 vxe.push_back(0.035);
763 if (ddt < dt0) dt0 = ddt;
787 if (idgM != vdgM->end())
788 LOG(warn) << GetName()
789 <<
"::LoadDigis : not all merged digis have been consumed !";
790 for (idgM = vdgM->begin(); idgM != vdgM->end(); idgM++)
794 if (TMath::Abs(
vs[0]) > 1.e-3) {
797 vs.insert(
vs.begin(), 0);
798 vse.insert(
vse.begin(), 300);
799 vt.insert(
vt.begin(), ddt);
800 vx.insert(
vx.begin(), xc - 0.5);
801 vxe.insert(
vxe.begin(), 0);
803 Int_t n(
vs.size() - 1);
804 if (TMath::Abs(
vs[n]) > 1.e-3) {
811 vxe.push_back(0.035);
815 for (UInt_t idx(0); idx <
vx.size(); idx++) {
824 vector<CbmTrdDigi*>* vdgM,
825 vector<Bool_t>* vmask) {
832 if (digis->size() < 2) {
833 LOG(warn) << GetName() <<
"::MergeDigis : Bad digi config for cluster :";
838 Int_t colR, colT, dt, contor(0);
840 for (vector<const CbmTrdDigi*>::iterator idig = digis->begin(),
842 jdig != digis->end();
843 idig++, jdig++, contor++) {
849 if (colR != colT)
continue;
859 cout <<
"MERGE" << endl;
862 cout <<
"TO" << endl;
864 cout <<
"..." << endl;
868 vdgM->push_back(dgM);
869 (*vmask)[contor] = 1;
870 jdig = digis->erase(jdig);
871 if (jdig == digis->end())
break;
875 LOG(warn) << GetName()
876 <<
"::MergeDigis : Digi to pads matching failed for cluster :";
884 {0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
885 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
886 0.000, 0.000, 0.000, -0.144, -0.091, -0.134, -0.185, -0.120, -0.115,
887 -0.125, -0.125, -0.124, -0.124, -0.122, -0.120, -0.119, -0.116, -0.114,
888 -0.113, -0.111, -0.109, -0.107, -0.105, -0.102, -0.100, -0.098, -0.097,
889 -0.093, -0.091, -0.089, -0.087, -0.084, -0.082, -0.079, -0.077, -0.074,
890 -0.072, -0.068, -0.065, -0.062, -0.059, -0.056, -0.053, -0.049, -0.046,
891 -0.043, -0.039, -0.036, -0.032, -0.029, -0.025, -0.022, -0.018, -0.015,
892 -0.011, -0.007, -0.003, 0.000, 0.003, 0.007, 0.011, 0.014, 0.018,
893 0.022, 0.025, 0.029, 0.032, 0.036, 0.039, 0.043, 0.046, 0.049,
894 0.053, 0.056, 0.059, 0.062, 0.065, 0.068, 0.071, 0.074, 0.077,
895 0.080, 0.082, 0.084, 0.087, 0.090, 0.091, 0.094, 0.096, 0.098,
896 0.100, 0.103, 0.104, 0.107, 0.108, 0.110, 0.113, 0.115, 0.116,
897 0.120, 0.121, 0.121, 0.123, 0.125, 0.124, 0.127, 0.140, 0.119,
898 0.114, 0.028, 0.049, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
899 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
900 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000},
901 {0.003, 0.013, 0.026, 0.039, 0.052, 0.065, 0.078, 0.091, 0.104,
902 0.118, 0.132, 0.145, 0.160, 0.174, 0.189, 0.203, 0.219, 0.234,
903 0.250, 0.267, 0.283, 0.301, 0.319, 0.338, 0.357, 0.375, 0.398,
904 0.419, 0.440, 0.464, 0.491, 0.514, 0.541, 0.569, 0.598, 0.623,
905 0.660, 0.696, 0.728, 0.763, 0.804, 0.847, 0.888, 0.930, 0.988,
906 1.015, 1.076, 1.128, 1.167, 1.228, 1.297, 1.374, 1.443, 1.511,
907 1.564, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
908 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
909 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
910 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000, 0.000,
911 0.000, -1.992, -1.884, -1.765, -1.703, -1.609, -1.572, -1.493, -1.426,
912 -1.356, -1.309, -1.243, -1.202, -1.109, -1.069, -1.026, -0.970, -0.933,
913 -0.881, -0.844, -0.803, -0.767, -0.721, -0.691, -0.659, -0.629, -0.596,
914 -0.569, -0.541, -0.514, -0.490, -0.466, -0.441, -0.419, -0.397, -0.377,
915 -0.357, -0.337, -0.319, -0.301, -0.283, -0.267, -0.250, -0.234, -0.218,
916 -0.203, -0.189, -0.174, -0.160, -0.145, -0.131, -0.119, -0.104, -0.091,
917 -0.078, -0.064, -0.052, -0.039, -0.026, -0.013, -0.002}};
919 {1.537359, 0.483472},
921 {1.154183, -0.090229}};