26 #include "art_root_io/TFileService.h" 27 #include "art_root_io/TFileDirectory.h" 59 #include "TTimeStamp.h" 60 #include "TLorentzVector.h" 62 #include "TEfficiency.h" 100 double CalcDist(
double X1,
double Y1,
double Z1,
double X2,
double Y2,
double Z2 );
101 double CalcPIDA( std::vector<const anab::Calorimetry*> calos );
102 double PIDAFunc(
double dedx,
double resrng );
174 auto const*
geom = lar::providerFrom<geo::Geometry>();
177 const double origin[3] = {0.};
179 TPC.LocalToWorld(origin, center);
181 double tpcDim[3] = {
TPC.HalfWidth(),
TPC.HalfHeight(), 0.5*
TPC.Length() };
194 fRecoTree = tfs->make<TTree>(
"ReconstructedTree",
"analysis tree");
244 fTrueTree = tfs->make<TTree>(
"TruthTree",
"truth_tree");
260 std::cout <<
"\nFinished all the events for module " <<
fTrackModuleLabel <<
"..." 287 XDriftVelocity = detProp.DriftVelocity()*1
e-3;
288 WindowSize = detProp.NumberTimeSamples() * clockData.TPCClock().TickPeriod() * 1e3;
301 std::vector<art::Ptr<recob::Track> > tracklist;
302 auto trackListHandle = evt.
getHandle< std::vector<recob::Track> >(fTrackModuleLabel);
306 auto trackh = evt.
getHandle< std::vector<recob::Track> >(fTrackModuleLabel);
308 std::vector<art::Ptr<raw::ExternalTrigger> > triglist;
309 auto trigListHandle = evt.
getHandle< std::vector<raw::ExternalTrigger> >(fCounterT0ModuleLabel);
313 const sim::ParticleList& plist = pi_serv->ParticleList();
315 for (
int qq=0; qq<1000; ++qq) {
316 True_PdgCode [ qq ] = True_Contained[ qq ] = True_Length [ qq ] = True_ID[qq] = True_Primary[qq] = 0;
317 True_StartX [ qq ] = True_StartY [ qq ] = True_StartZ [ qq ] = 0;
318 True_EndX [ qq ] = True_EndY [ qq ] = True_EndZ [ qq ] = 0;
323 bool InTPC =
false, StIn =
false, EnIn =
false;
324 double ThisStX=0, ThisStY=0, ThisStZ=0, ThisEnX=0, ThisEnY=0, ThisEnZ=0;
326 int ThisPDG=0, ThisCon=-1, ThisID=-1, ThisPri=-1;
331 if (particle->
Process() ==
"primary") ThisPri=1;
335 const TLorentzVector& tmpPosition=particle->
Position(
a);
336 double const tmpPosArray[]={tmpPosition[0],tmpPosition[1],tmpPosition[2]};
337 geo::TPCID tpcid = geom->FindTPCAtPosition(tmpPosArray);
346 ThisStX = tmpPosArray[0];
347 ThisStY = tmpPosArray[1];
348 ThisStZ = tmpPosArray[2];
350 if (
abs(particle->
PdgCode()) == 13 ) ++TrueMuons;
351 else if (
abs(particle->
PdgCode()) == 11 ) ++TrueElectrons;
352 else if (
abs(particle->
PdgCode()) == 22 ) ++TrueGammas;
353 else if (
abs(particle->
PdgCode()) == 2212 ) ++TrueProtons;
360 ThisEnX = tmpPosArray[0];
361 ThisEnY = tmpPosArray[1];
362 ThisEnZ = tmpPosArray[2];
366 if(!StIn && !EnIn ) ThisCon = 0;
367 if(!StIn && EnIn ) ThisCon = 1;
368 if( StIn && !EnIn ) ThisCon = 2;
369 if( StIn && EnIn ) ThisCon = 3;
370 ThisLen = CalcDist( ThisStX, ThisStY, ThisStZ, ThisEnX, ThisEnY, ThisEnZ );
377 if (InTPC && True_Particles < 1000) {
378 True_PdgCode [ True_Particles ] = ThisPDG;
379 True_ID [ True_Particles ] = ThisID;
380 True_Contained[ True_Particles ] = ThisCon;
381 True_Primary [ True_Particles ] = ThisPri;
382 True_Length [ True_Particles ] = ThisLen;
383 True_StartX [ True_Particles ] = ThisStX;
384 True_StartY [ True_Particles ] = ThisStY;
385 True_StartZ [ True_Particles ] = ThisStZ;
386 True_EndX [ True_Particles ] = ThisEnX;
387 True_EndY [ True_Particles ] = ThisEnY;
388 True_EndZ [ True_Particles ] = ThisEnZ;
397 if ( trackListHandle.isValid() ) {
398 art::FindManyP<recob::Hit> fmht (trackListHandle, evt, fTrackModuleLabel);
399 art::FindMany<anab::T0> fmt0 (trackListHandle, evt, fMCTruthT0ModuleLabel);
400 art::FindMany<anab::T0> fmphot (trackListHandle, evt, fPhotonT0ModuleLabel);
401 art::FindMany<anab::Calorimetry> fmcal (trackListHandle, evt, fCalorimetryModuleLabel);
402 int ntracks_reco=tracklist.size();
406 std::cout <<
"\n***** Looking at new track " <<
Track <<
" of " << ntracks_reco <<
", event " << evt.
event() <<
", Module " << fTrackModuleLabel <<
std::endl;
411 TrackLength = track.
Length();
414 if (NumTraj < 2)
continue;
417 TrackTheta_XZ = std::atan2(dir.X(), dir.Z());
418 TrackTheta_YZ = std::atan2(dir.Y(), dir.Z());
419 TrackEta_XY = std::atan2(dir.X(), dir.Y());
420 TrackEta_ZY = std::atan2(dir.Z(), dir.Y());
421 TrackTheta = dir.Theta();
422 TrackPhi = dir.Phi();
425 std::vector< art::Ptr<recob::Hit> > allHits = fmht.at(
Track);
426 int NumHits = allHits.size();
429 if ( allHits[
hit]->
View() == 2 ) ++TrackHits[0];
430 if ( allHits[
hit]->
View() == 1 ) ++TrackHits[1];
431 if ( allHits[
hit]->
View() == 0 ) ++TrackHits[2];
433 std::cout <<
"There were " << TrackHits[0] <<
", " << TrackHits[1] <<
", " << TrackHits[2] <<
" one each plane. " <<
std::endl;
439 if ( fmt0.isValid() ) {
440 std::vector<const anab::T0*> T0s = fmt0.at(
Track);
441 for (
size_t t0size =0; t0size < T0s.size(); t0size++) {
442 MCTruthT0 = T0s[t0size]->Time();
444 MCTruthTrackID = T0s[t0size]->TriggerBits();
446 TickT0 = MCTruthTickT0;
449 std::cout <<
"\n\nWorking out this TrackID" <<
std::endl;
450 std::map<int,double> trkide;
451 for(
size_t h = 0;
h < allHits.size(); ++
h){
453 std::vector<sim::IDE> ides;
454 std::vector<sim::TrackIDE>
TrackIDs = bt_serv->HitToTrackIDEs(clockData, hit);
455 for(
size_t e = 0;
e < TrackIDs.size(); ++
e){
456 trkide[TrackIDs[
e].trackID] += TrackIDs[
e].energy;
459 double maxe = -1, tote = 0;
463 if ((ii->second)>maxe){
466 std::cout <<
"Highest E track was " << TrackID <<
", deposited " << maxe <<
std::endl;
469 std::cout <<
"Old Best track was " << MCTruthTrackID <<
", New Best track is " << TrackID <<
std::endl;
470 if ( fabs(MCTruthTrackID) != fabs(TrackID) ) std::cout <<
"!!!!!I HAVE A TOTALLY DIFFERENT TRACK!!!!!!\n" << std::endl;
471 else if ( MCTruthTrackID != TrackID ) std::cout <<
"The TrackIDs are different signs.\n" <<
std::endl;
472 else std::cout <<
"The TrackIDs are the same.\n" <<
std::endl;
474 std::cout <<
"The MCTruthTrackID is now " << MCTruthTrackID <<
std::endl;
478 if ( fmphot.isValid() && fUsePhotons) {
479 std::vector<const anab::T0*> PhotT0 = fmphot.at(
Track);
480 for (
size_t T0it=0; T0it<PhotT0.size(); ++T0it) {
481 PhotonCounterT0 = PhotT0[T0it]->Time();
482 PhotonCounterTickT0 = PhotonCounterT0 /
sampling_rate(clockData);
483 PhotonCounterID = PhotT0[T0it]->TriggerBits();
485 TickT0 = PhotonCounterTickT0;
489 if (TickT0 == -1.)
continue;
490 double XCorFac = detProp.ConvertTicksToX( TickT0, 0, 0, 0 );
491 std::cout <<
"The TickT0 is " << TickT0 <<
", giving an x correction to each hit of around " << XCorFac <<
std::endl;
497 std::vector < TVector3 > CorrectedLocations;
498 CorrectedLocations.clear();
499 for (
unsigned int point=0; point < NumTraj; ++point ) {
501 TVector3 CorrectLoc = ThisLoc;
502 CorrectLoc[0] = CorrectLoc[0] - detProp.ConvertTicksToX( TickT0, allHits[NumTraj-(1+point)]->
WireID().
Plane, allHits[NumTraj-(1+point)]->
WireID().
TPC, allHits[NumTraj-(1+point)]->
WireID().Cryostat );
503 CorrectedLocations.push_back(CorrectLoc);
505 CorrectedStartX = CorrectedLocations[0][0];
506 CorrectedStartY = CorrectedLocations[0][1];
507 CorrectedStartZ = CorrectedLocations[0][2];
508 CorrectedEndX = CorrectedLocations[NumTraj-1][0];
509 CorrectedEndY = CorrectedLocations[NumTraj-1][1];
510 CorrectedEndZ = CorrectedLocations[NumTraj-1][2];
519 if ( MyParticle->
TrackId() != fabs(MCTruthTrackID) )
521 MatchedTrackID =
Track;
523 MCTruthInformation ( clockData, MyParticle );
527 double St_St = CalcDist( MCStartX, MCStartY, MCStartZ, CorrectedStartX, CorrectedStartY, CorrectedStartZ );
528 double St_En = CalcDist( MCStartX, MCStartY, MCStartZ, CorrectedEndX , CorrectedEndY , CorrectedEndZ );
530 double En_St = CalcDist( MCEndX , MCEndY , MCEndZ , CorrectedStartX, CorrectedStartY, CorrectedStartZ );
531 double En_En = CalcDist( MCEndX , MCEndY , MCEndZ , CorrectedEndX , CorrectedEndY , CorrectedEndZ );
534 if ( (St_En < St_St) && (En_St < En_En) ) {
535 std::cout <<
"I think that this track is backwards." <<
std::endl;
540 std::cout <<
"MC Start ("<< MCStartX <<
", " << MCStartY <<
", " << MCStartZ <<
")\n" 541 <<
"Reco Start ("<< CorrectedStartX <<
", " << CorrectedStartY <<
", " << CorrectedStartZ <<
")\n" 542 <<
"MC End ("<< MCEndX <<
", " << MCEndY <<
", " << MCEndZ <<
")\n" 543 <<
"Reco End ("<< CorrectedEndX <<
", " << CorrectedEndY <<
", " << CorrectedEndZ <<
")\n" 544 <<
"Dist of MC Start to Track Start/End is " << St_St <<
", " << St_En <<
"\n" 545 <<
"Dist of MC End to Track Start/End is " << En_St <<
", " << En_En <<
"\n";
547 std::cout <<
"The track is the wrong way around...Will need to correct later.\n";
554 if (fabs(MCPdgCode) == 13 ) ++MuonAll;
555 else if (fabs(MCPdgCode) == 11 ) ++ElectronAll;
556 else if (MCPdgCode == 2212 ) ++ProtonAll;
557 else if (MCPdgCode == 22 ) ++GammaAll;
561 TrackBoundaries( CorrectedLocations[0], CorrectedLocations[NumTraj-1] );
565 std::vector<const anab::Calorimetry*> calos = fmcal.at(
Track);
566 PIDA = CalcPIDA ( calos );
571 int QuickThresh = 25;
572 if (PIDA_Plane2 > QuickThresh ) {
573 std::cout <<
"\nTrack " <<
Track <<
" has a PIDA value of " << PIDA <<
", " << NumTraj <<
" traj points and " << NumHits <<
" hits, PdGCode " << MCPdgCode <<
" , MCTrackID " << MCTrackId <<
std::endl;
575 if (fabs(MCPdgCode) == 13 ) ++MuonBad;
576 else if (fabs(MCPdgCode) == 11) ++ElectronBad;
577 else if (MCPdgCode == 2212 ) ++ProtonBad;
578 else if (MCPdgCode == 22 ) ++GammaBad;
581 if (PIDA_Plane2 > 15 && PIDA_Plane2 < 25 && (RecoContainment == 1 || RecoContainment == 3) ) {
583 if (fabs(MCPdgCode) == 13 ) ++MuonRange;
584 else if (fabs(MCPdgCode) == 11) ++ElectronRange;
585 else if (MCPdgCode == 2212 ) ++ProtonRange;
586 else if (MCPdgCode == 22 ) ++GammaRange;
593 std::cout <<
"\n==== When subject to macro cuts ===" <<
std::endl;
595 if (fabs(MCPdgCode) == 13) std::cout <<
"This is a muon." <<
std::endl;
596 else if (fabs(MCPdgCode) == 2212) std::cout <<
"This is a proton." <<
std::endl;
598 std::cout <<
"This is a " << MCPdgCode <<
", not interested, so continuing." <<
std::endl;
602 if (MCContainment == 0 || MCContainment == 2 ) std::cout <<
"Would get cut by MC cut on stopping particles." <<
std::endl;
603 else if (MCContainment == 1 ) std::cout <<
"Would get cut by MC cut on contained particles." <<
std::endl;
604 else if (MCContainment == 3 ) std::cout <<
"This is a fully contained track.." <<
std::endl;
606 if (RecoContainment == 0 || RecoContainment == 2 ) std::cout <<
"Would get cut by Reco cut on stopping particles." <<
std::endl;
607 else if (RecoContainment == 1 ) std::cout <<
"Would get cut by Reco cut on contained particles." <<
std::endl;
608 else if (RecoContainment == 3 ) std::cout <<
"This is a fully contained track." <<
std::endl;
610 if (PIDA > 25) std::cout <<
"Unreasonably high PIDA of " << PIDA <<
". ";
611 else std::cout <<
"Has a Reasonabe PIDA of " << PIDA <<
". ";
612 if (PIDA_Plane2 > 25 ) std::cout <<
"Unreasonably high PIDA_Plane2 of " << PIDA_Plane2 <<
std::endl;
613 else std::cout <<
"Has a Reasonabe PIDA_Plane2 of " << PIDA_Plane2 <<
std::endl;
614 if (PIDA > 14 && PIDA < 18) std::cout <<
"Would lie in the proton PIDA area" <<
std::endl;
615 if (PIDA > 5 && PIDA < 9 ) std::cout <<
"Would lie in the muon PIDA area" <<
std::endl;
617 if (CaloPlane2 < 5) std::cout <<
"Has less than 5 collection plane hits." <<
std::endl;
618 else if (CaloPlane2 < 10) std::cout <<
"Has less than 10 collection plane hits." <<
std::endl;
619 else std::cout <<
"Has more than 10 collection plane hits " << CaloPlane2 <<
std::endl;
621 if (!MCCorOrient ) std::cout <<
"The track was the wrong way around!" <<
std::endl;
622 else std::cout <<
"The track was the right way around!" <<
std::endl;
624 if ( fabs( CorrectedEndX - MCEndX ) > 2.5 ) std::cout <<
"Missed the end point of the particle in X" <<
std::endl;
625 if ( fabs( CorrectedEndY - MCEndY ) > 2.5 ) std::cout <<
"Missed the end point of the particle in Y" <<
std::endl;
626 if ( fabs( CorrectedEndZ - MCEndZ ) > 2.5 ) std::cout <<
"Missed the end point of the particle in Z" <<
std::endl;
633 double PIDA = 0, dEdxSum = 0;
634 int UsedHits = 0, TotHits = 0;
637 double SumdEdx_St = 0., SumdEdx_En = 0., ResRng_St = 0, ResRng_En = 0;
638 unsigned int AvHits = 5;
640 ResRng_St = calos[2]->ResidualRange()[0];
641 ResRng_En = calos[2]->ResidualRange()[calos[2]->dEdx().size()-1];
644 if ( calos[2]->
dEdx().
size() < (2*AvHits) ) {
645 AvHits = 1 + (0.5 * calos[2]->dEdx().size());
647 for (
unsigned int PlHit=0; PlHit < calos[2]->dEdx().size(); ++PlHit ) {
648 if ( PlHit <= AvHits ) {
649 SumdEdx_St += calos[2]->dEdx()[PlHit];
651 if ( calos[2]->
dEdx().
size() - PlHit <= AvHits ) {
652 SumdEdx_En += calos[2]->dEdx()[PlHit];
656 double AvdEdx_St = SumdEdx_St / AvHits;
657 double AvdEdx_En = SumdEdx_En / AvHits;
659 bool LowResSt =
false;
660 if ( ResRng_St < ResRng_En )
662 bool LowdEdxSt =
false;
663 if ( AvdEdx_St < AvdEdx_En )
666 if ( LowResSt && (!MCCorOrient) ) {
667 std::cout <<
"Track backwards, but calorimetry correct so setting everything to true...." <<
std::endl;
669 double TmpX, TmpY, TmpZ;
670 TmpX = CorrectedStartX; TmpY = CorrectedStartY; TmpZ = CorrectedStartZ;
671 CorrectedStartX = CorrectedEndX ; CorrectedStartY = CorrectedEndY ; CorrectedStartZ = CorrectedEndZ ;
672 CorrectedEndX = TmpX ; CorrectedEndY = TmpY ; CorrectedEndZ = TmpZ ;
673 std::cout <<
"Reco Start ("<< CorrectedStartX <<
", " << CorrectedStartY <<
", " << CorrectedStartZ <<
")\n" 674 <<
"Reco End ("<< CorrectedEndX <<
", " << CorrectedEndY <<
", " << CorrectedEndZ <<
")\n";
676 std::cout <<
"AvdEdx_St is " << AvdEdx_St <<
", and AvdEdx_En is " << AvdEdx_En <<
"....ResRng_St is " << ResRng_St <<
", and ResRng_En is " << ResRng_En
677 <<
" ====>>> LowResSt " << LowResSt <<
", LowdEdxSt " << LowdEdxSt <<
", and TruthOrient? " << MCCorOrient <<
std::endl;
679 if ( !MCCorOrient ) {
680 std::cout <<
"This track is wrong?" <<
std::endl;
688 double PlanePIDA=0;
int PlaneHits=0;
689 for (
int PlaneHit=0; PlaneHit < (
int)calos[
Plane]->
dEdx().size(); ++PlaneHit ) {
690 double ThisdEdx = calos[
Plane]->dEdx()[PlaneHit];
691 double ThisResR = calos[
Plane]->ResidualRange()[PlaneHit];
697 dEdxPlane0[CaloPlane0] = ThisdEdx;
698 ResRPlane0[CaloPlane0] = ThisResR;
701 dEdxPlane1[CaloPlane1] = ThisdEdx;
702 ResRPlane1[CaloPlane1] = ThisResR;
705 dEdxPlane2[CaloPlane2] = ThisdEdx;
706 ResRPlane2[CaloPlane2] = ThisResR;
722 if ( ThisResR < 30 ) {
723 PlanePIDA += PIDAFunc( ThisdEdx, ThisResR );
730 UsedHits += PlaneHits;
732 PlanePIDA = PlanePIDA/PlaneHits;
733 if (
Plane == 0 ) PIDA_Plane0 = PlanePIDA;
734 else if (
Plane == 1 ) PIDA_Plane1 = PlanePIDA;
735 else if (
Plane == 2 ) PIDA_Plane2 = PlanePIDA;
739 PIDA = PIDA / UsedHits;
740 AvdEdx = dEdxSum / TotHits;
747 if (MCCorOrient ==
false) {
748 TVector3 larTemp = larStart;
751 std::cout <<
"Swapping positions for reco containment. " <<
std::endl;
753 std::cout <<
"The track positions are (" << larStart[0] <<
", " << larStart[1] <<
", " << larStart[2] <<
") ("<< larEnd[0] <<
", " << larEnd[1] <<
", " << larEnd[2] <<
") and boundaries are " 754 << boundaries[0] <<
" -> " << boundaries[1] <<
", " << boundaries[2] <<
" -> " << boundaries[3] <<
", " <<boundaries[4] <<
" -> " << boundaries[5] <<
std::endl;
756 double XStartDiff =
std::min( fabs(boundaries[0]-larStart[0]), fabs(boundaries[1]-larStart[0]) );
757 double YStartDiff =
std::min( fabs(boundaries[2]-larStart[1]), fabs(boundaries[3]-larStart[1]) );
758 double ZStartDiff =
std::min( fabs(boundaries[4]-larStart[2]), fabs(boundaries[5]-larStart[2]) );
759 if ( larStart[0] < boundaries[0] || larStart[0] > boundaries[1] ) XStartDiff = -XStartDiff;
760 if ( larStart[1] < boundaries[2] || larStart[1] > boundaries[3] ) YStartDiff = -YStartDiff;
761 if ( larStart[2] < boundaries[4] || larStart[2] > boundaries[5] ) ZStartDiff = -ZStartDiff;
762 RecoStartInTPC =
false;
763 if ( XStartDiff > fBoundaryEdge && XStartDiff > 0 &&
764 YStartDiff > fBoundaryEdge && YStartDiff > 0 &&
765 ZStartDiff > fBoundaryEdge && ZStartDiff > 0
767 RecoStartInTPC =
true;
771 double XEndDiff =
std::min( fabs(boundaries[0]-larEnd[0]), fabs(boundaries[1]-larEnd[0]) );
772 double YEndDiff =
std::min( fabs(boundaries[2]-larEnd[1]), fabs(boundaries[3]-larEnd[1]) );
773 double ZEndDiff =
std::min( fabs(boundaries[4]-larEnd[2]), fabs(boundaries[5]-larEnd[2]) );
774 if ( larEnd[0] < boundaries[0] || larEnd[0] > boundaries[1] ) XEndDiff = -XEndDiff;
775 if ( larEnd[1] < boundaries[2] || larEnd[1] > boundaries[3] ) YEndDiff = -YEndDiff;
776 if ( larEnd[2] < boundaries[4] || larEnd[2] > boundaries[5] ) ZEndDiff = -ZEndDiff;
777 RecoEndInTPC =
false;
778 if ( XEndDiff > fBoundaryEdge && XEndDiff > 0 &&
779 YEndDiff > fBoundaryEdge && YEndDiff > 0 &&
780 ZEndDiff > fBoundaryEdge && ZEndDiff > 0
789 if(!RecoStartInTPC && !RecoEndInTPC ) RecoContainment = 0;
790 if(!RecoStartInTPC && RecoEndInTPC ) RecoContainment = 1;
791 if( RecoStartInTPC && !RecoEndInTPC ) RecoContainment = 2;
792 if( RecoStartInTPC && RecoEndInTPC ) RecoContainment = 3;
794 if( XStartDiff < 0 || XEndDiff < 0 ) {
795 std::cout <<
"This particle was outside active vol...." <<
std::endl;
796 if (
std::max( fabs(larStart[1]-MCStartY), fabs(larStart[2]-MCStartZ ) ) < 5 &&
797 std::max( fabs(larEnd[1] -MCEndY) , fabs(larEnd[2] -MCEndZ ) ) < 5
799 std::cout <<
"But the Y and Z difference are small, so changing to MCContainment" <<
std::endl;
800 RecoContainment = MCContainment;
804 std::cout <<
"RecoStartInTPC? " << RecoStartInTPC <<
", RecoEndInTPC? " << RecoEndInTPC
805 <<
", StartFromEdge " << StartFromEdge <<
", EndFromEdge " << EndFromEdge
806 <<
", RecoContainment " << RecoContainment <<
", MCContainment " << MCContainment
815 std::vector<double> TPCLengthHits(numberTrajectoryPoints, 0);
816 std::vector<double> TPCEnDepos(numberTrajectoryPoints, 0);
817 bool BeenInVolume =
false;
818 int FirstHit=0, LastHit=0;
820 for(
unsigned int MCHit=0; MCHit < TPCLengthHits.size(); ++MCHit) {
821 const TLorentzVector& tmpPosition=particle->
Position(MCHit);
822 double const tmpPosArray[]={tmpPosition[0],tmpPosition[1],tmpPosition[2]};
825 TPCLengthHits[MCHit] =
pow (
pow( (particle->
Vx(MCHit-1)-particle->
Vx(MCHit)),2)
826 +
pow( (particle->
Vy(MCHit-1)-particle->
Vy(MCHit)),2)
827 +
pow( (particle->
Vz(MCHit-1)-particle->
Vz(MCHit)),2)
829 TPCEnDepos[MCHit] = 1000 * (particle->
E(MCHit-1) - particle->
E(MCHit));
832 geo::TPCID tpcid = geom->FindTPCAtPosition(tmpPosArray);
834 if (MCHit == 0 ) MCStartInTPC =
true;
835 if (MCHit == numberTrajectoryPoints-1 ) MCEndInTPC =
true;
840 double DriftTimeCorrection = fabs( tmpPosition[0] - XPlanePosition ) / XDriftVelocity;
841 double TimeAtPlane = particle->
T() + DriftTimeCorrection;
847 MCEndX = particle->
Vx(MCHit) ; MCEndY = particle->
Vy(MCHit) ; MCEndZ = particle->
Vz(MCHit);
848 if ( !BeenInVolume ) {
851 MCStartX = particle->
Vx(MCHit) ; MCStartY = particle->
Vy(MCHit) ; MCStartZ = particle->
Vz(MCHit);
856 if(!MCStartInTPC && !MCEndInTPC ) MCContainment = 0;
857 if(!MCStartInTPC && MCEndInTPC ) MCContainment = 1;
858 if( MCStartInTPC && !MCEndInTPC ) MCContainment = 2;
859 if( MCStartInTPC && MCEndInTPC ) MCContainment = 3;
860 std::cout <<
"This track is from a " << particle->
PdgCode() <<
", StartInTPC? " << MCStartInTPC <<
", EndInTPC? " << MCEndInTPC <<
", MCContainment " << MCContainment <<
std::endl;
863 MCEnergy = particle->
E(FirstHit);
864 MCEnergyDeposited = particle->
E(FirstHit) - particle->
E(LastHit);
865 for (
int Hit = FirstHit+1;
Hit <= LastHit; ++
Hit ) {
866 MCTPCLength += TPCLengthHits[
Hit];
873 for (
int Hit = FirstHit+1;
Hit <= LastHit; ++
Hit ) {
874 NewDist += TPCLengthHits[
Hit];
875 double ThdEdx = TPCEnDepos[
Hit] / TPCLengthHits[
Hit];
876 double ThResR = MCTPCLength - NewDist;
878 if (TPCEnDepos[
Hit] == 0)
continue;
879 double ThPIDA = PIDAFunc( ThdEdx, ThResR );
885 std::cout <<
"Looking at Hit " <<
Hit <<
" to " << LastHit <<
". Total length was " << MCTPCLength <<
", now gone " << NewDist <<
". " 886 <<
"dEdx here was " << ThdEdx <<
", ResRange was " << ThResR <<
", so PIDA = " << ThPIDA <<
" = " << ThdEdx <<
" * " << ThResR <<
"^"<<PIDApower<<
".\n" 887 <<
"The PIDA sum is now " << SumPIDA <<
", and I have used " << MCHits <<
" hits." 891 MCPIDA = SumPIDA / MCHits;
892 std::cout <<
"The MCPIDA is " << MCPIDA <<
std::endl;
895 MCPdgCode = particle->
PdgCode();
896 MCTrackId = particle->
TrackId();
897 if (particle->
Process() ==
"primary") {
899 if (MCTruthTrackID < 0)
903 std::cout <<
"What kind of primary identifier? " << MCIsPrimary <<
std::endl;
904 TLorentzVector& momentumStart = (TLorentzVector&)particle->
Momentum(FirstHit);
905 TVector3 mcstartmom = particle->
Momentum(FirstHit).Vect();
906 MCTheta_XZ = std::atan2(momentumStart.Px(), momentumStart.Pz());
907 MCTheta_YZ = std::atan2(momentumStart.Py(), momentumStart.Pz());
908 MCEta_XY = std::atan2(momentumStart.Px(), momentumStart.Py());
909 MCEta_ZY = std::atan2(momentumStart.Pz(), momentumStart.Py());
910 MCTheta = mcstartmom.Theta();
911 MCPhi = mcstartmom.Phi();
917 double Sq = TMath::Power( X1-X2 , 2 ) + TMath::Power( Y1-Y2 , 2 ) + TMath::Power( Z1-Z2 , 2 );
918 double Va = TMath::Power( Sq, 0.5 );
923 double Va = dedx *
pow( resrng, PIDApower );
929 MCTPCLength = MCEnergy = MCEnergyDeposited = MCPIDA = 0;
930 MCPdgCode = MCTrackId = MatchedTrackID = MCContainment = 0;
931 MCStartX = MCStartY = MCStartZ = MCEndX = MCEndY = MCEndZ = 0;
933 PIDA = PIDA_Plane0 = PIDA_Plane1 = PIDA_Plane2 = StartFromEdge = EndFromEdge = TrackLength = 0;
934 CorrectedStartX = CorrectedStartY = CorrectedStartZ = CorrectedEndX = CorrectedEndY = CorrectedEndZ = 0;
935 TrackHits[0] = TrackHits[1] = TrackHits[2] = RecoContainment = 0;
937 MCStartInTPC = MCEndInTPC = RecoStartInTPC = RecoEndInTPC =
false;
940 CaloPlane0 = CaloPlane1 = CaloPlane2 = 0;
942 ResRPlane0[ii] = ResRPlane1[ii] = ResRPlane2[ii] = 0;
943 dEdxPlane0[ii] = dEdxPlane1[ii] = dEdxPlane2[ii] = 0;
double E(const int i=0) const
unsigned int NumberTrajectoryPoints() const
art::ServiceHandle< geo::Geometry > geom
const TLorentzVector & Position(const int i=0) const
EventNumber_t event() const
double ResRPlane1[kMaxHits]
std::string fHitsModuleLabel
double ResRPlane0[kMaxHits]
Encapsulate the construction of a single cyostat.
double CalcPIDA(std::vector< const anab::Calorimetry * > calos)
art::ServiceHandle< cheat::ParticleInventoryService > pi_serv
AdcChannelData::View View
Handle< PROD > getHandle(SelectorBase const &) const
std::vector< TrackID > TrackIDs
std::string fMCTruthT0ModuleLabel
void MCTruthInformation(detinfo::DetectorClocksData const &clockData, const simb::MCParticle *particle)
Point_t const & LocationAtPoint(size_t i) const
bool isValid
Whether this ID points to a valid element.
Geometry information for a single TPC.
std::string fCounterT0ModuleLabel
size_t NumberTrajectoryPoints() const
Various functions related to the presence and the number of (valid) points.
Vector_t VertexDirection() const
std::string fPhotonT0ModuleLabel
CryostatID_t Cryostat
Index of cryostat.
std::string fCalorimetryModuleLabel
double dEdxPlane1[kMaxHits]
Geometry information for a single cryostat.
EDAnalyzer(fhicl::ParameterSet const &pset)
std::string Process() const
double dEdxPlane2[kMaxHits]
art framework interface to geometry description
decltype(auto) constexpr size(T &&obj)
ADL-aware version of std::size.
double dEdx(float dqdx, float Efield)
double PIDAFunc(double dedx, double resrng)
double Length(size_t p=0) const
Access to various track properties.
#define DEFINE_ART_MODULE(klass)
IDparameter< geo::WireID > WireID
Member type of validated geo::WireID parameter.
IteratorBox< TPC_iterator,&GeometryCore::begin_TPC,&GeometryCore::end_TPC > IterateTPCs() const
Enables ranged-for loops on all TPCs of the detector.
void analyze(art::Event const &e) override
double T(const int i=0) const
virtual ~ProtonIdentification()
static int max(int a, int b)
The data type to uniquely identify a TPC.
Detector simulation of raw signals on wires.
Encapsulate the geometry of a wire.
double Vx(const int i=0) const
Declaration of signal hit object.
std::string fTrackModuleLabel
T min(sqlite3 *const db, std::string const &table_name, std::string const &column_name)
Encapsulate the construction of a single detector plane.
Contains all timing reference information for the detector.
const TPCGeo & TPC(unsigned int itpc) const
Return the itpc'th TPC in the cryostat.
art::ServiceHandle< cheat::BackTrackerService > bt_serv
double CalcDist(double X1, double Y1, double Z1, double X2, double Y2, double Z2)
const TLorentzVector & Momentum(const int i=0) const
void beginRun(art::Run const &run) override
Provides recob::Track data product.
double dEdxPlane0[kMaxHits]
double PhotonCounterTickT0
double Vz(const int i=0) const
int trigger_offset(DetectorClocksData const &data)
double ResRPlane2[kMaxHits]
TrackCollectionProxyElement< TrackCollProxy > Track
Proxy to an element of a proxy collection of recob::Track objects.
auto const & get(AssnsNode< L, R, D > const &r)
void fill_ptr_vector(std::vector< Ptr< T >> &ptrs, H const &h)
TPCID_t TPC
Index of the TPC within its cryostat.
void endRun(art::Run const &) override
double sampling_rate(DetectorClocksData const &data)
Returns the period of the TPC readout electronics clock.
recob::tracking::Plane Plane
void TrackBoundaries(TVector3 larStart, TVector3 larEnd)
const double * PlaneLocation(unsigned int p) const
double Vy(const int i=0) const
Track from a non-cascading particle.A recob::Track consists of a recob::TrackTrajectory, plus additional members relevant for a "fitted" track:
constexpr Point origin()
Returns a origin position with a point of the specified type.
QTextStream & endl(QTextStream &s)
Encapsulate the construction of a single detector plane.
ProtonIdentification(fhicl::ParameterSet const &p)