Skip to content

Commit

Permalink
Merge branch 'develop' into coincidenceSorter
Browse files Browse the repository at this point in the history
  • Loading branch information
Oudihat-Radia authored Sep 3, 2024
2 parents 423f9e6 + 65825c2 commit e721839
Show file tree
Hide file tree
Showing 21 changed files with 750 additions and 119 deletions.
13 changes: 8 additions & 5 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,12 @@ jobs:
matrix:
os: [ubuntu-latest, macos-latest]
options: [none, rtk, torch, optic]
exclude:
- os: macos-latest
options: torch

env:
ROOT_VERSION: 'v6-26-08'
ROOT_VERSION: 'v6-32-02'
GEANT4_VERSION: 'v11.2.1'
ITK_VERSION: 'v5.3.0'
ROOT_DIR: $(HOME)/software/root
Expand All @@ -38,8 +41,8 @@ jobs:
uses: actions/cache@v3
with:
path: ~/software
key: ${{ matrix.os }}-geant4-${{ env.GEANT4_VERSION }}-root-${{ env.ROOT_VERSION }}-build4
restore-keys: ${{ matrix.os }}-geant4-${{ env.GEANT4_VERSION }}-root-${{ env.ROOT_VERSION }}-build4
key: ${{ matrix.os }}-geant4-${{ env.GEANT4_VERSION }}-root-${{ env.ROOT_VERSION }}-build1
restore-keys: ${{ matrix.os }}-geant4-${{ env.GEANT4_VERSION }}-root-${{ env.ROOT_VERSION }}-build1
- name: Install dependencies
run: |
if [ "${{ matrix.os }}" == "ubuntu-latest" ]; then
Expand Down Expand Up @@ -129,8 +132,8 @@ jobs:
wget https://download.pytorch.org/libtorch/cpu/libtorch-cxx11-abi-shared-with-deps-1.10.1%2Bcpu.zip
unzip libtorch-cxx11-abi-shared-with-deps-1.10.1+cpu.zip
elif [ "${{ matrix.os }}" == 'macos-latest' ]; then
wget https://download.pytorch.org/libtorch/cpu/libtorch-macos-1.10.1.zip
unzip libtorch-macos-1.10.1.zip
wget https://download.pytorch.org/libtorch/cpu/libtorch-macos-arm64-2.2.0.zip
unzip libtorch-macos-arm64-2.2.0.zip
fi
fi
if [ "${{ matrix.options }}" == 'rtk' ]; then
Expand Down
70 changes: 63 additions & 7 deletions docs/digitizer_and_detector_modeling.rst
Original file line number Diff line number Diff line change
Expand Up @@ -225,7 +225,7 @@ Five types of distribution are available in GATE, namely:
* Gaussian distributions, defined by a mean value and a standard deviation.
* Exponential distributions, defined by its power.
* Manual distributions, defined by a discrete set of points specified in the GATE macro file. The data are linearly interpolated to define the function in a continuous range.
* File distribution, acting as the manual distribution, but where the points are defined in a separate ASCII file, whose name is given as a parameter. This method is appropriate for large numbers of points and allows to describe any distribution in a totally generic way.
* File distribution, acting as the manual distribution, but where the points are defined in a separate ASCII file, whose name is given as a parameter. This method is appropriate for large numbers of points and allows to describe any distribution in a totally generic way. Now, GATE supports reading 2D distributions from ASCII files where values are organized in matrices.

A distribution is declared by specifying its name then by creating a new instance, with its type name::

Expand Down Expand Up @@ -297,7 +297,8 @@ The possible type name available corresponds to the five distributions described
+----------------+--------------------------------------------------------------------------------+
| read | do read the file (should be called after specifying all the other parameters) |
+----------------+--------------------------------------------------------------------------------+

| ReadMatrix2d | do read a data file that organizes its contents in a 2D matrix format |
+----------------+--------------------------------------------------------------------------------+

Singles Digitizers
-------------------
Expand Down Expand Up @@ -518,11 +519,53 @@ In case if the position obtained after applying a Gaussian blurring exceeds the
BEWARE: This relocation procedure is validated only for the first group level of crystals.

**Example**::

/gate/digitizerMgr/crystal/SinglesDigitizer/Singles/insert spatialResolution
/gate/digitizerMgr/crystal/SinglesDigitizer/Singles/spatialResolution/fwhm 1.0 mm
/gate/digitizerMgr/crystal/SinglesDigitizer/Singles/spatialResolution/confineInsideOfSmallestElement true

**Configuring Spatial Resolution with 1D and 2D Distributions**::

This approach is particularly essential for monolithic crystal detectors, where factors like edge effects and interaction positions significantly may influence spatial resolution.
Here is an example of how to configure this in a macro file:

**Example for 2D distribution**::


/gate/distributions/name my_distrib2D
/gate/distributions/insert File
/gate/distributions/my_distrib2D/setFileName Lut(X,Y).txt
/gate/distributions/my_distrib2D/readMatrix2d
/gate/digitizerMgr/crystalUnit/SinglesDigitizer/Singles/insert spatialResolution
/gate/digitizerMgr/crystalUnit/SinglesDigitizer/Singles/spatialResolution/fwhmXdistrib2D my_distrib2D
**Example for 1D distribution**::

/gate/distributions/name my_distrib1D
/gate/distributions/insert File
/gate/distributions/my_distrib1D/setFileName macros/LutY.txt
/gate/distributions/my_distrib1D/read
/gate/digitizerMgr/crystalUnit/SinglesDigitizer/Singles/insert spatialResolution
/gate/digitizerMgr/crystalUnit/SinglesDigitizer/Singles/spatialResolution/fwhmYdistrib my_distrib1D





These commands allow for more precise control over the spatial resolution by using predefined distributions for the X and Y axes.

BEWARE : The file for 2D Distribution should be structured such that:

-The first line contains the x values.

-Each subsequent line begins with a y value followed by the standard deviation (stddev) values corresponding to each x value and y value pair.

**Example**::

-29.50 -28.50 -27.50
-29.50 9.62 13.66 10.22
-28.50 11.38 11.18 10.23
-27.50 12.82 10.43 9.70

Energy Framing
^^^^^^^^^^^^^^
*Previously Thresholder and Upholder*
Expand Down Expand Up @@ -1111,7 +1154,7 @@ Then, the rejection can be set to the whole event or only to those pulses within

Example::

/gate/digitizerMgr/absorber/SinglesDigitizer/Singles/insert multipleRejection
/gate/digitizerMgr/absorber/SinglesDigitizer/Singles/insert multipleRejection
/gate/digitizerMgr/absorber/SinglesDigitizer/Singles/multipleRejection/setMultipleDefinition volumeID
/gate/digitizerMgr/absorber/SinglesDigitizer/Singles/multipleRejection/setEventRejection 1

Expand Down Expand Up @@ -1368,20 +1411,32 @@ The dead time for coincidences works in the same way as that acting on the *sing

Coincidence buffers
~~~~~~~~~~~~~~~~~~~
It simulates the operation of a detector by modeling coincidences, transfer speed limits, and data loss due to buffer capacity overflows. It manages a memory buffer for coincidence events, allowing for the modeling of data loss due to buffer overflow. It uses a read frequency and allows defining the buffer size and read mode, influencing how events are processed. There are two buffer operation modes. Mode 1 empties the entire buffer at each read clock tick, while Mode 0 reads events one by one.

Example::

/gate/digitizerMgr/CoincidenceDigitizer/finalCoinc/insert buffer
/gate/digitizerMgr/CoincidenceDigitizer/finalCoinc/buffer/setBufferSize 64 B
/gate/digitizerMgr/CoincidenceDigitizer/finalCoinc/buffer/setReadFrequency 10 MHz
/gate/digitizerMgr/CoincidenceDigitizer/finalCoinc/buffer/setMode 1


For a coincidence sorter user can chose a presort buffer with a following command:

/gate/digitizer/Coincidences/setPresortBufferSize 256


A presort buffer contains singles that have not yet been checked for coincidence with the already open coincidence windows. The default value is 256, the minimum value is 32. For more details, check https://iopscience.iop.org/article/10.1088/0031-9155/61/18/N522


Multiple coincidence removal
~~~~~~~~~~~~~~~~~~~~~~~~~~~~

If the multiple coincidences are kept and not splitted into pairs (ie. if any of the **keepXXX** multiple coincidence policy is used), the multicoincidences could participate to dataflow occupancy, but could not be written to the disk. Unless otherwise specified, any multicoincidence is then cleared from data just before the disk writing. If needed, this clearing could be performed at any former coincidence processing step, by inserting the **multipleKiller** module at the required level. This module has no parameter and just kill the multicoincidence events. Multiple coincidences split into many pairs are not affected by this module and cannot be distinguished from the normal "simple" coincidences. To insert a multipleKiller, one has to use the syntax::
If the multiple coincidences are kept and not split into pairs (i.e., if any of the **keepXXX** multiple coincidence policies are used), the multicoincidences could contribute to dataflow occupancy but cannot be written to the disk. Unless otherwise specified, any multicoincidence is then cleared from data just before the disk writing. If needed, this clearing could be performed at any earlier coincidence processing step by inserting the **multipleKiller** module at the required level. This module has no parameters and simply removes the multicoincidence events. Multiple coincidences split into many pairs are not affected by this module and cannot be distinguished from normal "simple" coincidences. To insert a multipleKiller, use the syntax::


/gate/digitizerMgr/CoincidenceDigitizer/finalCoinc/insert multiplesKiller

/gate/digitizer/myCoincChain/insert multipleKiller

Example of a digitizer setting
------------------------------
Expand Down Expand Up @@ -1486,6 +1541,7 @@ Example::
87 /gate/digitizer/finalCoinc/buffer/setBufferSize 32 B
88 /gate/digitizer/finalCoinc/buffer/setReadFrequency 14.45 MHz
89 /gate/digitizer/finalCoinc/buffer/setMode 0

Lines 1 to 15: The branch named "Singles" contains the result of applying the adder, readout, blurring, and threshold (50 keV) modules.

Expand Down
8 changes: 7 additions & 1 deletion source/digits_hits/include/GateDistributionFile.hh
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,8 @@ class GateDistributionFile : public GateVDistributionArray
inline G4int GetColumnX() const {return m_column_for_X;}
inline G4int GetColumnY() const {return m_column_for_Y;}

void Read();
void Read();
void ReadMatrix2d();

virtual void DescribeMyself(size_t indent);
private:
Expand All @@ -41,6 +42,11 @@ class GateDistributionFile : public GateVDistributionArray
G4int m_column_for_X;
G4int m_column_for_Y;
GateDistributionFileMessenger* m_messenger;
std::map<std::pair<double, double>, double> stddevMap;

std::vector<double> xValues;
std::vector<double> yValues;

};


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ class GateDistributionFileMessenger: public GateDistributionArrayMessenger
G4UIcmdWithAnInteger *setColXCmd;
G4UIcmdWithAnInteger *setColYCmd;
G4UIcmdWithoutParameter *readCmd;
G4UIcmdWithoutParameter *read2DCmd;
G4UIcmdWithoutParameter *autoXCmd;
};

Expand Down
3 changes: 3 additions & 0 deletions source/digits_hits/include/GateDistributionMessenger.hh
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ class GateDistributionMessenger: public GateNamedObjectMessenger
void SetNewValue(G4UIcommand* aCommand, G4String aString);
void SetUnitX(const G4String& unitX);
void SetUnitY(const G4String& unitY);

inline G4String UnitCategoryX() const {return m_unitX.empty()?"":G4UIcommand::CategoryOf(m_unitX);}
inline G4String UnitCategoryY() const {return m_unitY.empty()?"":G4UIcommand::CategoryOf(m_unitY);}

Expand All @@ -41,8 +42,10 @@ class GateDistributionMessenger: public GateNamedObjectMessenger
G4UIcmdWithoutParameter *getMaxY_Cmd ;
G4UIcmdWithoutParameter *getRandom_Cmd ;
G4UIcmdWithADoubleAndUnit *getValueCmd ;

G4String m_unitX;
G4String m_unitY;

};

#endif
33 changes: 25 additions & 8 deletions source/digits_hits/include/GateSpatialResolution.hh
100755 → 100644
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,10 @@ See LICENSE.md for further details
#include "G4TouchableHistoryHandle.hh"
#include "GateSinglesDigitizer.hh"

class GateVDistribution;

class GateSpatialResolution : public GateVDigitizerModule

{
public:

Expand All @@ -40,9 +43,15 @@ public:

void Digitize() override;



//! These functions return the resolution in use.
G4double GetFWHM() { return m_fwhm; }
G4double GetFWHMx() { return m_fwhmX; }
GateVDistribution* GetFWHMxdistrib() { return m_fwhmXdistrib; }
GateVDistribution* GetFWHMydistrib() { return m_fwhmYdistrib; }
GateVDistribution* GetFWHMxydistrib2D() { return m_fwhmXYdistrib2D; }

G4double GetFWHMx() { return m_fwhmX; }
G4double GetFWHMy() { return m_fwhmY; }
G4double GetFWHMz() { return m_fwhmZ; }

Expand All @@ -51,11 +60,14 @@ public:
If you want a resolution of 10%, SetSpresolution(0.1)
*/
void SetFWHM(G4double val) { m_fwhm = val; }
void SetFWHMxdistrib(GateVDistribution* dist) { m_fwhmXdistrib= dist; }
void SetFWHMydistrib(GateVDistribution* dist) { m_fwhmYdistrib = dist; }
void SetFWHMxydistrib2D(GateVDistribution* dist) { m_fwhmXYdistrib2D= dist; }

void SetFWHMx(G4double val) { m_fwhmX = val; }
void SetFWHMy(G4double val) { m_fwhmY = val; }
void SetFWHMz(G4double val) { m_fwhmZ = val; }


void SetSpatialResolutionParameters();
inline void ConfineInsideOfSmallestElement(const G4bool& value) { m_IsConfined = value; };
inline G4bool IsConfinedInsideOfSmallestElement() const { return m_IsConfined; }

Expand All @@ -64,17 +76,23 @@ public:

void UpdateVolumeID();


//! Implementation of the pure virtual method declared by the base class GateClockDependent
//! print-out the attributes specific of the blurring
void DescribeMyself(size_t );

protected:
G4double m_fwhm;


G4double m_fwhmX;

G4double m_fwhmY;
G4double m_fwhmZ;

GateVDistribution* m_fwhmXdistrib;
GateVDistribution* m_fwhmYdistrib;
GateVDistribution* m_fwhmXYdistrib2D;

G4bool m_IsConfined;
G4Navigator* m_Navigator;
G4TouchableHistoryHandle m_Touchable;
Expand All @@ -83,16 +101,15 @@ protected:

private:

G4int m_systemDepth;

GateDigi* m_outputDigi;
G4int m_systemDepth;

GateDigi* m_outputDigi;;
GateSpatialResolutionMessenger *m_Messenger;

GateDigiCollection* m_OutputDigiCollection;

GateSinglesDigitizer *m_digitizer;

G4bool m_IsFirstEntrance;
G4VoxelLimits limits;
G4double Xmin, Xmax, Ymin, Ymax, Zmin, Zmax;
G4AffineTransform at;
Expand Down
12 changes: 7 additions & 5 deletions source/digits_hits/include/GateSpatialResolutionMessenger.hh
100755 → 100644
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@ See LICENSE.md for further details
#include "GateClockDependentMessenger.hh"
class GateSpatialResolution;
class G4UIcmdWithAString;

class GateSpatialResolutionMessenger : public GateClockDependentMessenger
{
public:
Expand All @@ -41,10 +40,13 @@ public:
private:
GateSpatialResolution* m_SpatialResolution;

G4UIcmdWithADouble* spresolutionCmd;
G4UIcmdWithADouble* spresolutionXCmd;
G4UIcmdWithADouble* spresolutionYCmd;
G4UIcmdWithADouble* spresolutionZCmd;
G4UIcmdWithADoubleAndUnit* spresolutionCmd;
G4UIcmdWithADoubleAndUnit* spresolutionXCmd;
G4UIcmdWithADoubleAndUnit* spresolutionYCmd;
G4UIcmdWithADoubleAndUnit* spresolutionZCmd;
G4UIcmdWithAString *spresolutionXdistribCmd;// Command declaration for 1D X-resolution distribution
G4UIcmdWithAString *spresolutionYdistribCmd;// Command declaration for 1D Y-resolution distribution
G4UIcmdWithAString *spresolutionXYdistrib2DCmd; // Command declaration for 2D XY-resolution distribution
G4UIcmdWithABool* confineCmd;


Expand Down
5 changes: 5 additions & 0 deletions source/digits_hits/include/GateToTree.hh
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,10 @@ public:
static void SetOutputIDName(G4int id_system, const char * anOutputIDName, size_t depth);
G4bool getHitsEnabled() const;
void setHitsEnabled(G4bool mHitsEnabled);

G4bool getHitsCommonOutputEnabled() const;
void setHitsCommonOutputEnabled(G4bool mHitsCommonOutputEnabled);

void addCollection(const std::string &str); //called by messenger
//OK GND 2022
void setCCenabled(G4bool mCCenabled){m_cc_enabled=mCCenabled;};
Expand Down Expand Up @@ -135,6 +139,7 @@ private:
std::vector<std::string> m_listOfSinglesCollection;
std::vector<std::string> m_listOfCoincidencesCollection;
G4bool m_hits_enabled;
G4bool m_hitsCommonOutput_enabled;
G4String m_uselessFileName; //only for GiveNameOfFile which return a reference..

G4bool m_opticalData_enabled = false;
Expand Down
4 changes: 4 additions & 0 deletions source/digits_hits/include/GateToTreeMessenger.hh
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,10 @@ private:
G4UIcmdWithoutParameter *m_enableHitsOutput;
G4UIcmdWithoutParameter *m_disableHitsOutput;

G4UIcmdWithoutParameter *m_enableHitsCommonOutput;
G4UIcmdWithoutParameter *m_disableHitsCommonOutput;


G4UIcmdWithoutParameter *m_enableOpticalDataOutput;
G4UIcmdWithoutParameter *m_disableOpticalDataOutput;

Expand Down
2 changes: 2 additions & 0 deletions source/digits_hits/include/GateVDistribution.hh
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,8 @@ class GateVDistribution : public GateNamedObject
virtual G4double MaxX() const=0;
virtual G4double MaxY() const=0;
virtual G4double Value(G4double x) const=0;
virtual G4double Value2D(G4double x, G4double y) const;

// Returns a random number following the current distribution
// should be optimised according to each distrbution type
virtual G4double ShootRandom() const=0;
Expand Down
Loading

0 comments on commit e721839

Please sign in to comment.