Skip to content

Commit ba8c902

Browse files
author
Félix C. Morency
committed
NF + DOC: Added support for patient orientation following radiological and neurological viewing convention
1 parent efb4719 commit ba8c902

File tree

1 file changed

+62
-7
lines changed

1 file changed

+62
-7
lines changed

nibabel/ecat.py

Lines changed: 62 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -187,7 +187,10 @@
187187
(7, 'ECAT7_Head_First_Decubitus_Left'),
188188
(8, 'ECAT7_Unknown_Orientation'))
189189

190-
190+
#Indexes from the patient_orient_defs structure defined above for the
191+
#neurological and radiological viewing conventions
192+
patient_orient_radiological = [0, 2, 4, 6]
193+
patient_orient_neurological = [1, 3, 5, 7]
191194

192195
class EcatHeader(object):
193196
"""Class for basic Ecat PET header
@@ -654,21 +657,66 @@ def _get_frame_offset(self, frame=0):
654657
offset = (mlist[frame][1]) * 512
655658
return int(offset)
656659

657-
def raw_data_from_fileobj(self, frame=0):
660+
def _get_oriented_data(self, raw_data, orientation=None):
661+
'''
662+
Get data oriented following ``patient_orientation`` header field. If the
663+
``orientation`` parameter is given, return data according to this
664+
orientation.
665+
666+
:param raw_data: Numpy array containing the raw data
667+
:param orientation: None (default), 'neurological' or 'radiological'
668+
:rtype: Numpy array containing the oriented data
669+
'''
670+
if orientation is None:
671+
orientation = self._header['patient_orientation']
672+
elif orientation == 'neurological':
673+
orientation = 1
674+
elif orientation == 'radiological':
675+
orientation = 0
676+
else:
677+
raise ValueError('orientation should be None,\
678+
neurological or radiological')
679+
680+
if orientation in patient_orient_radiological:
681+
raw_data = raw_data[::-1, ::-1, ::-1]
682+
elif orientation in patient_orient_neurological:
683+
raw_data = raw_data[::, ::-1, ::-1]
684+
685+
return raw_data
686+
687+
def raw_data_from_fileobj(self, frame=0, orientation=None):
688+
'''
689+
Get raw data from file object.
690+
691+
:param frame: Time frame index from where to fetch data
692+
:param orientation: None (default), 'neurological' or 'radiological'
693+
:rtype: Numpy array containing (possibly oriented) raw data
694+
695+
.. seealso:: data_from_fileobj
696+
'''
658697
dtype = self._get_data_dtype(frame)
659698
if not self._header.endianness is native_code:
660699
dtype=dtype.newbyteorder(self._header.endianness)
661700
shape = self.get_shape(frame)
662701
offset = self._get_frame_offset(frame)
663702
fid_obj = self.fileobj
664703
raw_data = array_from_file(shape, dtype, fid_obj, offset=offset)
704+
raw_data = self._get_oriented_data(raw_data, orientation)
665705
return raw_data
666706

667-
def data_from_fileobj(self, frame=0):
668-
"""read scaled data from file for a given frame"""
707+
def data_from_fileobj(self, frame=0, orientation=None):
708+
'''
709+
Read scaled data from file for a given frame
710+
711+
:param frame: Time frame index from where to fetch data
712+
:param orientation: None (default), 'neurological' or 'radiological'
713+
:rtype: Numpy array containing (possibly oriented) raw data
714+
715+
.. seealso:: raw_data_from_fileobj
716+
'''
669717
header = self._header
670718
subhdr = self.subheaders[frame]
671-
raw_data = self.raw_data_from_fileobj(frame)
719+
raw_data = self.raw_data_from_fileobj(frame, orientation)
672720
data = raw_data * header['ecat_calibration_factor']
673721
data = data * subhdr['scale_factor']
674722
return data
@@ -796,8 +844,15 @@ def get_frame_affine(self, frame):
796844
"""returns 4X4 affine"""
797845
return self._subheader.get_frame_affine(frame=frame)
798846

799-
def get_frame(self,frame):
800-
return self._subheader.data_from_fileobj(frame)
847+
def get_frame(self,frame, orientation=None):
848+
'''
849+
Get full volume for a time frame
850+
851+
:param frame: Time frame index from where to fetch data
852+
:param orientation: None (default), 'neurological' or 'radiological'
853+
:rtype: Numpy array containing (possibly oriented) raw data
854+
'''
855+
return self._subheader.data_from_fileobj(frame, orientation)
801856

802857
def get_data_dtype(self,frame):
803858
subhdr = self._subheader

0 commit comments

Comments
 (0)