UCL / STIR

Software for Tomographic Image Reconstruction
http://stir.sourceforge.net/
Other
115 stars 95 forks source link

Gate Scanner geometry checks fails for GE D690 unlisting #563

Closed robbietuk closed 4 years ago

robbietuk commented 4 years ago

Discussion leading up to this may be found in https://github.com/UCL/STIR-GATE-Connection/issues/14, I will summerise.

STIR scanner defines the transaxial properties of the GE Discovery 690 to be:

  1. Transaxial blocks per bucket = 2
  2. Transaxial crystals per block = 9
  3. Transaxial crystals per singles unit = 1

STIR checks compares these scanner parameters with the geometry given in the .hroot, which would make sense to define as

number of Rsectors := 64
number of modules_X := 1 
number of modules_Y := 1
number of modules_Z := 4
number of submodules_X := 1
number of submodules_Y := 1
number of submodules_Z := 1
number of crystals_X := 1
number of crystals_Y := 9
number of crystals_Z := 6

corresponding to a Cylindrical system defined as

#   MODULE
/gate/rsector/daughters/name                     module
...
#   C R Y S T A L
/gate/module/daughters/name                    crystal
/gate/module/daughters/insert                  box
//gate/crystal/setMaterial                     LYSO
...
#   R E P E A T    C R Y S T A L
/gate/crystal/repeaters/insert                cubicArray
/gate/crystal/cubicArray/setRepeatNumberX     1
/gate/crystal/cubicArray/setRepeatNumberY     9
/gate/crystal/cubicArray/setRepeatNumberZ     6
...
#   R E P E A T    MODULE
/gate/module/repeaters/insert                  cubicArray
/gate/module/cubicArray/setRepeatNumberX       1
/gate/module/cubicArray/setRepeatNumberY       1
/gate/module/cubicArray/setRepeatNumberZ       4
...
#   R E P E A T    RSECTOR
/gate/rsector/repeaters/insert                   ring
/gate/rsector/ring/setRepeatNumber               64
#   A T T A C H    S Y S T E M 
/gate/systems/cylindricalPET/rsector/attach   rsector
/gate/systems/cylindricalPET/module/attach    module
/gate/systems/cylindricalPET/crystal/attach   crystal

This is used at https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/include/stir/IO/InputStreamFromROOTFileForCylindricalPET.inl#L20-L107 However, the checks https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/listmode_buildblock/CListModeDataROOT.cxx#L237-L297 fail with the error ERROR: the number of transaxial blocks per bucket, the number of axial crystals per block, the number of axial crystals per singles unit, the number of transaxial crystals per singles unit,

This check is impossible to pass for the D690 scanner for the transaxial components, as

I can also reference #96 which also references https://github.com/UCL/STIR/pull/190 and #79 / #80

E: This .hroot is the same that @eliseemond used in this presentation: https://www.ccppetmr.ac.uk/sites/www.ccppetmr.ac.uk/files/Emond_STIR_TOF.pdf

robbietuk commented 4 years ago

I wonder if this->module_repeater_y from https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/include/stir/IO/InputStreamFromROOTFileForCylindricalPET.inl#L59-L65 should actually be this->submodule_repeater_y.

Infact, should submodule_repeater_y be reserved for singles_unit and therefore not present in this computation?

Regardless, get_num_transaxial_blocks_per_bucket_v and get_num_transaxial_crystals_per_block_v seem to contridict each other. Both use the module_repeater_y variable.

KrisThielemans commented 4 years ago

From https://opengate.readthedocs.io/en/latest/digitizer_and_detector_modeling.html and https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/include/stir/IO/InputStreamFromROOTFileForCylindricalPET.inl#L101 I think we should be setting singles_readout_depth=4 for GEscanners (no idea how that corresponds to actual dead-time in their electronics, but they do report singles per crystals).

The module/submodule stuff seems a bit of a mess. You're certainly right that the get_num_*axial_crystals_per_block_v functions should't use module_repeater_y.

80 discussed some of this at the start, but the final implementation in #190 seems to have been incorrect. sigh. what about this

get_num_transaxial_blocks_per_bucket_= submodule_repeater_y;
get_num_transaxial_crystals_per_block_ = crystal_repeater_y

implying

get_num_transaxial_buckets_= module_repeater_y * num_Rsectors

or something like that. (As I wrote in #80, GATE seems to have one more level with the RSector stuff, at least along the ring).

Note that unlisting itself won't be influenced as it works in terms of crystals (see https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/IO/InputStreamFromROOTFileForCylindricalPET.cxx#L93).

Here's some stuff for the ECAT system: https://github.com/UCL/STIR/blob/7dc238f5ec228554f594f1f2228450eb4618472b/src/include/stir/IO/InputStreamFromROOTFileForECATPET.inl#L50-L61

robbietuk commented 4 years ago

Additionaly documentation regarding rsector, modules, submodules, crystals, and layers https://opengate.readthedocs.io/en/latest/defining_a_system_scanner_ct_pet_spect_optical.html#cylindricalpet

robbietuk commented 4 years ago

Yes, GE Scanners should use readout depth of 4 for STIR. However, this means we might need to consider "pile-up" (more than photon interacting with a crystal in a time window) and deadtime (which we do not model). https://opengate.readthedocs.io/en/latest/digitizer_and_detector_modeling.html#pile-up https://opengate.readthedocs.io/en/latest/digitizer_and_detector_modeling.html#dead-time

Regarding STIR's interpretation of the Gate scanners. While your suggestion makes most sense, it still would not pass for the current implementation of the D690, e.g. get_num_transaxial_blocks_per_bucket = 2 but 'number of modules_Y =1` in the Gate D690 geometry.


Therefore I wonder if these checks on the Gate geometry, at least at this intermediate level, are even required, especially as the unlisting does not use them, it uses crystals indicies. As long as num_rings and get_num_dets_per_ring are correct, does STIR need further geometrical information from Gate? Perhaps get_num_trans_crystals_per_singles_unit and get_num_axial_crystals_per_singles_unit are required still.

KrisThielemans commented 4 years ago
we've come to the conclusion that we can directly map GATE cylindrical PET scanner to STIR (in terms of geometry) via GATE STIR
crystal crystal
submodule block
module bucket
rsector (just puts buckets along the ring)

This ignores actual dead-time issues, which is a different thing altogether, and we currently don't have dead-time specific modelling in STIR anyway (except in the ECAT7 normalisation code).

Of course, at present STIR ignores the "blocky" nature of the placement of the detectors.

KrisThielemans commented 4 years ago

@robbietuk this can be closed?

robbietuk commented 4 years ago

Yes