Skip to content

Commit

Permalink
Merge pull request #33 from rest-for-physics/trackLineAna
Browse files Browse the repository at this point in the history
New methods added for track analysis
  • Loading branch information
juanangp authored May 19, 2023
2 parents d1c43ce + 051ac3b commit b85c78a
Show file tree
Hide file tree
Showing 4 changed files with 157 additions and 6 deletions.
2 changes: 2 additions & 0 deletions inc/TRestTrackEvent.h
Original file line number Diff line number Diff line change
Expand Up @@ -108,9 +108,11 @@ class TRestTrackEvent : public TRestEvent {

Int_t GetOriginTrackID(Int_t tck);

Double_t GetMaxTrackRelativeZ();
void GetMaxTrackBoundaries(TVector3& orig, TVector3& end);
void GetOriginEnd(std::vector<TGraph*>& originGr, std::vector<TGraph*>& endGr,
std::vector<TLegend*>& leg);
TRestVolumeHits GetMaxTrackBoundaries3D(TVector3& orig, TVector3& end);
void DrawOriginEnd(TPad* pad, std::vector<TGraph*>& originGr, std::vector<TGraph*>& endGr,
std::vector<TLegend*>& leg);

Expand Down
9 changes: 6 additions & 3 deletions inc/TRestTrackLineAnalysisProcess.h
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,12 @@
class TRestTrackLineAnalysisProcess : public TRestEventProcess {
private:
/// A pointer to the input event Track Event
TRestTrackEvent* fTrackEvent;
TRestTrackEvent* fTrackEvent; //!

/// A pointer to the output event Track event
TRestTrackEvent* fOutTrackEvent;
TRestTrackEvent* fOutTrackEvent; //!

std::string fLineAnaMethod = "default"; //<

void Initialize() override;

Expand All @@ -49,6 +51,7 @@ class TRestTrackLineAnalysisProcess : public TRestEventProcess {

void PrintMetadata() override {
BeginPrintProcess();
RESTMetadata << "Track Analysis method " << fLineAnaMethod << RESTendl;
EndPrintProcess();
}

Expand All @@ -59,6 +62,6 @@ class TRestTrackLineAnalysisProcess : public TRestEventProcess {
// Destructor
~TRestTrackLineAnalysisProcess();

ClassDefOverride(TRestTrackLineAnalysisProcess, 1);
ClassDefOverride(TRestTrackLineAnalysisProcess, 2);
};
#endif
131 changes: 131 additions & 0 deletions src/TRestTrackEvent.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -313,6 +313,84 @@ void TRestTrackEvent::SetLevels() {
fLevels = maxLevel;
}

///////////////////////////////////////////////
/// \brief This function retrieves the origin and the end track positions
/// based after the reconstruction of a 3D track. It requires the track to have
/// the same number of hits in X and Y. Two different directions are scanned and
/// the one which maximizes the track length is retrieved. Afterwards the position
/// of the closer hit to the half integral of the track is obtained. Then, the origin
/// of the track is defined as the further edge to the half integral, while the track
/// end is defined as the closest edge.
///
TRestVolumeHits TRestTrackEvent::GetMaxTrackBoundaries3D(TVector3& orig, TVector3& end) {
TRestTrack* tckX = GetMaxEnergyTrackInX();
TRestTrack* tckY = GetMaxEnergyTrackInY();

if (tckX == nullptr || tckY == nullptr) {
RESTWarning << "Track is empty, skipping" << RESTendl;
return {};
}

TRestVolumeHits hitsX = (TRestVolumeHits) * (tckX->GetVolumeHits());
TRestVolumeHits hitsY = (TRestVolumeHits) * (tckY->GetVolumeHits());

const int nHits = std::min(hitsX.GetNumberOfHits(), hitsY.GetNumberOfHits());
TRestVolumeHits best3DHits, hits3D;

for (int i = 0; i < nHits; i++) {
double enX = hitsX.GetEnergy(i);
double enY = hitsY.GetEnergy(i);
double posXZ = hitsX.GetZ(i);
double posYZ = hitsY.GetZ(i);
double avgZ = (enX * posXZ + enY * posYZ) / (enX + enY);
best3DHits.AddHit(hitsX.GetX(i), hitsY.GetY(i), avgZ, enX + enY, 0, XYZ, 0, 0, 0);
const int j = nHits - i - 1;
enY = hitsY.GetEnergy(j);
posYZ = hitsY.GetZ(j);
avgZ = (enX * posXZ + enY * posYZ) / (enX + enY);
hits3D.AddHit(hitsX.GetX(i), hitsY.GetY(j), avgZ, enX + enY, 0, XYZ, 0, 0, 0);
}

double length = (best3DHits.GetPosition(0) - best3DHits.GetPosition(nHits - 1)).Mag();

if ((hits3D.GetPosition(0) - hits3D.GetPosition(nHits - 1)).Mag() > length) {
best3DHits = hits3D;
}

double totEn = 0;
for (unsigned int i = 0; i < best3DHits.GetNumberOfHits(); i++) {
totEn += best3DHits.GetEnergy(i);
}

const TVector3 pos0 = best3DHits.GetPosition(0);
const TVector3 posE = best3DHits.GetPosition(best3DHits.GetNumberOfHits() - 1);

double integ = 0;
unsigned int pos = 0;
for (pos = 0; pos < best3DHits.GetNumberOfHits(); pos++) {
integ += best3DHits.GetEnergy(pos);
if (integ > totEn / 2.) break;
}

auto intPos = best3DHits.GetPosition(pos);
const double intToFirst = (pos0 - intPos).Mag();
const double intToLast = (posE - intPos).Mag();

RESTDebug << "Integ pos " << pos << " Pos to first " << intToFirst << " last " << intToLast << RESTendl;
if (intToFirst < intToLast) {
end = pos0;
orig = posE;
} else {
orig = pos0;
end = posE;
}

RESTDebug << "Origin " << orig.X() << " " << orig.Y() << " " << orig.Z() << RESTendl;
RESTDebug << "End " << end.X() << " " << end.Y() << " " << end.Z() << RESTendl;

return best3DHits;
}

///////////////////////////////////////////////
/// \brief This function retreive the origin and the end of the track
/// based on the most energetic hit. The origin is defined as the further
Expand All @@ -323,6 +401,11 @@ void TRestTrackEvent::GetMaxTrackBoundaries(TVector3& orig, TVector3& end) {
TRestTrack* tckX = GetMaxEnergyTrackInX();
TRestTrack* tckY = GetMaxEnergyTrackInY();

if (tckX == nullptr || tckY == nullptr) {
RESTWarning << "Track is empty, skipping" << RESTendl;
return;
}

TVector3 origX, endX;
// Retreive origin and end of the track for the XZ projection
tckX->GetBoundaries(origX, endX);
Expand All @@ -337,6 +420,54 @@ void TRestTrackEvent::GetMaxTrackBoundaries(TVector3& orig, TVector3& end) {
end = TVector3(endX.X(), endY.Y(), endZ);
}

///////////////////////////////////////////////
/// \brief Function to calculate the relative Z of the most energetic
/// track to crosscheck if the track is upwards or downwards
///
Double_t TRestTrackEvent::GetMaxTrackRelativeZ() {
TRestTrack* tckX = GetMaxEnergyTrackInX();
TRestTrack* tckY = GetMaxEnergyTrackInY();

if (tckX == nullptr || tckY == nullptr) {
RESTWarning << "Track is empty, skipping" << RESTendl;
return -1;
}

std::vector<std::pair<double, double> > zEn;
double totEn = 0;

for (size_t i = 0; i < tckX->GetVolumeHits()->GetNumberOfHits(); i++) {
double en = tckX->GetVolumeHits()->GetEnergy(i);
double z = tckX->GetVolumeHits()->GetZ(i);
zEn.push_back(std::make_pair(z, en));
totEn += en;
}

for (size_t i = 0; i < tckY->GetVolumeHits()->GetNumberOfHits(); i++) {
double en = tckY->GetVolumeHits()->GetEnergy(i);
double z = tckY->GetVolumeHits()->GetZ(i);
zEn.push_back(std::make_pair(z, en));
totEn += en;
}

std::sort(zEn.begin(), zEn.end());

double integ = 0;
size_t pos = 0;
for (pos = 0; pos < zEn.size(); pos++) {
integ += zEn[pos].second;
if (integ >= totEn / 2.) break;
}

double length = zEn.front().first - zEn.back().first;
double diff = zEn.front().first - zEn[pos].first;

if (length == 0)
return 0;
else
return diff / length;
}

void TRestTrackEvent::PrintOnlyTracks() {
cout << "TrackEvent " << GetID() << endl;
cout << "-----------------------" << endl;
Expand Down
21 changes: 18 additions & 3 deletions src/TRestTrackLineAnalysisProcess.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@
/// length, energy and downwards (bool).
///
/// ### Parameters
/// None
/// * **lineAnaMethod**: Method to evaluate the origin and end of the track, currently
/// 3D method and default are implemented
///
/// ### Observables
/// * **trackBalanceXZ**: Track balance between the most energetic track and all tracks in the XZ projection
Expand All @@ -50,6 +51,8 @@
/// * **angle**: Track polar angle in radians
/// * **downwards**: (bool) true if the track direction is downwards, false otherwise
/// * **totalEnergy**: Energy of the track
/// * **relativeZ**: Relative Z position in which the half of the integral is reached,
/// when this value is below 0.5 it means that the track is downwards and upwards otherwise
///
/// ### Examples
/// \code
Expand Down Expand Up @@ -140,11 +143,21 @@ TRestEvent* TRestTrackLineAnalysisProcess::ProcessEvent(TRestEvent* inputEvent)
Double_t angle = -10;
bool downwards = true;
Double_t trackEnergyX = 0, trackEnergyY = 0;
Double_t trackBalanceX = 0, trackBalanceY = 0, trackBalance = 0;
Double_t trackBalanceX = 0, trackBalanceY = 0, trackBalance = 0, relZ = 0;

if (tckX && tckY) {
// Retreive origin and end of the track for the XZ projection
fTrackEvent->GetMaxTrackBoundaries(orig, end);
if (fLineAnaMethod == "3D") {
fTrackEvent->GetMaxTrackBoundaries3D(orig, end);
} else {
if (fLineAnaMethod != "default") {
RESTWarning
<< "Line analysis method " << fLineAnaMethod
<< " is not implemented, supported methods are: default and 3D. Falling back to default."
<< RESTendl;
}
fTrackEvent->GetMaxTrackBoundaries(orig, end);
}

RESTDebug << "Origin: " << orig.X() << " y: " << orig.Y() << " z: " << orig.Z() << RESTendl;
RESTDebug << "End : " << end.X() << " y: " << end.Y() << " z: " << end.Z() << RESTendl;
Expand All @@ -167,6 +180,7 @@ TRestEvent* TRestTrackLineAnalysisProcess::ProcessEvent(TRestEvent* inputEvent)
if (trackEnergyX > 0 && trackEnergyY > 0)
trackBalance =
(trackEnergyX + trackEnergyY) / (fTrackEvent->GetEnergy("X") + fTrackEvent->GetEnergy("Y"));
relZ = fTrackEvent->GetMaxTrackRelativeZ();
}

Double_t trackEnergy = trackEnergyX + trackEnergyY;
Expand All @@ -185,6 +199,7 @@ TRestEvent* TRestTrackLineAnalysisProcess::ProcessEvent(TRestEvent* inputEvent)
SetObservableValue("angle", angle);
SetObservableValue("downwards", downwards);
SetObservableValue("totalEnergy", trackEnergy);
SetObservableValue("relativeZ", relZ);

if (!tckX || !tckY) return nullptr;

Expand Down

0 comments on commit b85c78a

Please sign in to comment.