From 2bfc8d7e03c4d4803a9df3bd83e8b72853aaef66 Mon Sep 17 00:00:00 2001 From: "Christopher J. Markiewicz" Date: Tue, 24 Oct 2017 09:54:04 -0400 Subject: [PATCH] ENH: Add get_norm_zooms for zooms in mm/s units --- nibabel/analyze.py | 4 ++++ nibabel/nifti1.py | 33 +++++++++++++++++++++++++++++++++ nibabel/spatialimages.py | 4 ++++ 3 files changed, 41 insertions(+) diff --git a/nibabel/analyze.py b/nibabel/analyze.py index ba1529e3b9..2384c260da 100644 --- a/nibabel/analyze.py +++ b/nibabel/analyze.py @@ -710,6 +710,10 @@ def set_zooms(self, zooms): pixdims = hdr['pixdim'] pixdims[1:ndim + 1] = zooms[:] + def get_norm_zooms(self): + ''' Get zooms in mm/s units ''' + return self.get_zooms() + def as_analyze_map(self): """ Return header as mapping for conversion to Analyze types diff --git a/nibabel/nifti1.py b/nibabel/nifti1.py index 4d766a76f5..729229b46c 100644 --- a/nibabel/nifti1.py +++ b/nibabel/nifti1.py @@ -1626,6 +1626,39 @@ def set_xyzt_units(self, xyz=None, t=None): t_code = unit_codes[t] self.structarr['xyzt_units'] = xyz_code + t_code + def get_norm_zooms(self, raise_unknown=False): + ''' Get zooms in mm/s units ''' + raw_zooms = self.get_zooms() + xyz_zooms = raw_zooms[:3] + t_zoom = raw_zooms[3] if len(raw_zooms) > 3 else None + + xyz_code, t_code = self.get_xyzt_units() + xyz_msg = t_msg = '' + if xyz_code == 'unknown': + xyz_msg = 'Unknown spatial units' + xyz_code = 'mm' + if t_code == 'unknown' and t_zoom is not None: + t_msg = 'Unknown time units' + t_code = 'sec' + if raise_unknown and (xyz_msg, t_msg) != ('', ''): + if xyz_msg and t_msg: + msg = 'Unknown spatial and time units' + else: + msg = xyz_msg or t_msg + raise ValueError("Error: {}".format(msg)) + if xyz_msg: + warnings.warn('{} - assuming mm'.format(xyz_msg)) + if t_msg: + warnings.warn('{} - assuming sec'.format(t_msg)) + + xyz_factor = {'meter': 0.001, 'mm': 1, 'usec': 1000}[xyz_code] + t_factor = {'sec': 1, 'msec': 1000, 'usec': 1000000}[t_code] + + xyz_zooms = tuple(np.array(xyz_zooms) / xyz_factor) + t_zoom = (t_zoom / t_factor,) if t_zoom is not None else () + + return xyz_zooms + t_zoom + def _clean_after_mapping(self): ''' Set format-specific stuff after converting header from mapping diff --git a/nibabel/spatialimages.py b/nibabel/spatialimages.py index 2554600649..1d8b7e8947 100644 --- a/nibabel/spatialimages.py +++ b/nibabel/spatialimages.py @@ -241,6 +241,10 @@ def set_zooms(self, zooms): raise HeaderDataError('zooms must be positive') self._zooms = zooms + def get_norm_zooms(self, raise_unknown=False): + ''' Get zooms in mm/s units ''' + return self.get_zooms() + def get_base_affine(self): shape = self.get_data_shape() zooms = self.get_zooms()