1
1
''' Testing trackvis module '''
2
+ from functools import partial
3
+ import warnings
2
4
3
5
import numpy as np
4
6
5
7
from ..py3k import BytesIO , asbytes
6
8
from .. import trackvis as tv
9
+ from ..orientations import aff2axcodes
7
10
from ..volumeutils import native_code , swapped_code
11
+ from ..checkwarns import ErrorWarnings , IgnoreWarnings
8
12
9
13
from nose .tools import assert_true , assert_false , assert_equal , assert_raises
10
14
@@ -165,55 +169,118 @@ def test_empty_header():
165
169
166
170
167
171
def test_get_affine ():
172
+ # Test get affine behavior, including pending deprecation
168
173
hdr = tv .empty_header ()
174
+ # Using version 1 affine is not a good idea because is fragile and not
175
+ # very useful. The default atleast_v2=None mode raises a FutureWarning
176
+ with ErrorWarnings ():
177
+ assert_raises (FutureWarning , tv .aff_from_hdr , hdr )
178
+ # testing the old behavior
179
+ old_afh = partial (tv .aff_from_hdr , atleast_v2 = False )
169
180
# default header gives useless affine
170
- assert_array_equal (tv . aff_from_hdr (hdr ),
181
+ assert_array_equal (old_afh (hdr ),
171
182
np .diag ([0 ,0 ,0 ,1 ]))
172
183
hdr ['voxel_size' ] = 1
173
- assert_array_equal (tv . aff_from_hdr (hdr ),
184
+ assert_array_equal (old_afh (hdr ),
174
185
np .diag ([0 ,0 ,0 ,1 ]))
175
186
# DICOM direction cosines
176
187
hdr ['image_orientation_patient' ] = [1 ,0 ,0 ,0 ,1 ,0 ]
177
- assert_array_equal (tv . aff_from_hdr (hdr ),
188
+ assert_array_equal (old_afh (hdr ),
178
189
np .diag ([- 1 ,- 1 ,1 ,1 ]))
179
190
# RAS direction cosines
180
191
hdr ['image_orientation_patient' ] = [- 1 ,0 ,0 ,0 ,- 1 ,0 ]
181
- assert_array_equal (tv . aff_from_hdr (hdr ),
192
+ assert_array_equal (old_afh (hdr ),
182
193
np .eye (4 ))
183
194
# translations
184
195
hdr ['origin' ] = [1 ,2 ,3 ]
185
196
exp_aff = np .eye (4 )
186
197
exp_aff [:3 ,3 ] = [- 1 ,- 2 ,3 ]
187
- assert_array_equal (tv . aff_from_hdr (hdr ),
198
+ assert_array_equal (old_afh (hdr ),
188
199
exp_aff )
200
+ # check against voxel order. This one works
201
+ hdr ['voxel_order' ] = '' .join (aff2axcodes (exp_aff ))
202
+ assert_equal (hdr ['voxel_order' ], 'RAS' )
203
+ assert_array_equal (old_afh (hdr ), exp_aff )
204
+ # This one doesn't
205
+ hdr ['voxel_order' ] = 'LAS'
206
+ assert_raises (tv .HeaderError , old_afh , hdr )
207
+ # This one does work because the routine allows the final dimension to
208
+ # be flipped to try and match the voxel order
209
+ hdr ['voxel_order' ] = 'RAI'
210
+ exp_aff = exp_aff * [[1 ,1 ,- 1 ,1 ]]
211
+ assert_array_equal (old_afh (hdr ), exp_aff )
212
+ # Check round trip case for flipped and unflipped, when positive voxels
213
+ # only allowed. This checks that the flipping heuristic works.
214
+ flipped_aff = exp_aff
215
+ unflipped_aff = exp_aff * [1 ,1 ,- 1 ,1 ]
216
+ for in_aff , o_codes in ((unflipped_aff , 'RAS' ),
217
+ (flipped_aff , 'RAI' )):
218
+ hdr = tv .empty_header ()
219
+ tv .aff_to_hdr (in_aff , hdr , pos_vox = True , set_order = True )
220
+ # Unset easier option
221
+ hdr ['vox_to_ras' ] = 0
222
+ assert_equal (hdr ['voxel_order' ], o_codes )
223
+ # Check it came back the way we wanted
224
+ assert_array_equal (old_afh (hdr ), in_aff )
225
+ # Check that the default case matches atleast_v2=False case
226
+ with IgnoreWarnings ():
227
+ assert_array_equal (tv .aff_from_hdr (hdr ), flipped_aff )
189
228
# now use the easier vox_to_ras field
190
229
hdr = tv .empty_header ()
191
230
aff = np .eye (4 )
192
231
aff [:3 ,:] = np .arange (12 ).reshape (3 ,4 )
193
232
hdr ['vox_to_ras' ] = aff
194
- assert_array_equal (tv .aff_from_hdr (hdr ), aff )
233
+ # Pass v2 flag explicitly to avoid warnings
234
+ assert_array_equal (tv .aff_from_hdr (hdr , atleast_v2 = False ), aff )
195
235
# mappings work too
196
236
d = {'version' : 1 ,
197
- 'voxel_size' : np .array ([1 ,2 ,3 ]),
198
- 'image_orientation_patient' : np .array ([1 ,0 ,0 ,0 ,1 ,0 ]),
199
- 'origin' : np .array ([10 ,11 ,12 ])}
200
- aff = tv .aff_from_hdr (d )
237
+ 'voxel_size' : np .array ([1 ,2 ,3 ]),
238
+ 'image_orientation_patient' : np .array ([1 ,0 ,0 ,0 ,1 ,0 ]),
239
+ 'origin' : np .array ([10 ,11 ,12 ])}
240
+ aff = tv .aff_from_hdr (d , atleast_v2 = False )
201
241
202
242
203
243
def test_aff_to_hdr ():
204
- for version in (1 , 2 ):
205
- hdr = {'version' : version }
206
- affine = np .diag ([1 ,2 ,3 ,1 ])
207
- affine [:3 ,3 ] = [10 ,11 ,12 ]
244
+ # The behavior is changing soon, change signaled by FutureWarnings
245
+ # This is the call to get the old behavior
246
+ old_a2h = partial (tv .aff_to_hdr , pos_vox = False , set_order = False )
247
+ hdr = {'version' : 1 }
248
+ affine = np .diag ([1 ,2 ,3 ,1 ])
249
+ affine [:3 ,3 ] = [10 ,11 ,12 ]
250
+ old_a2h (affine , hdr )
251
+ assert_array_almost_equal (tv .aff_from_hdr (hdr , atleast_v2 = False ), affine )
252
+ # put flip into affine
253
+ aff2 = affine .copy ()
254
+ aff2 [:,2 ] *= - 1
255
+ old_a2h (aff2 , hdr )
256
+ # Historically we flip the first axis if there is a negative determinant
257
+ assert_array_almost_equal (hdr ['voxel_size' ], [- 1 ,2 ,3 ])
258
+ assert_array_almost_equal (tv .aff_from_hdr (hdr , atleast_v2 = False ), aff2 )
259
+ # Test that default mode raises DeprecationWarning
260
+ with ErrorWarnings ():
261
+ assert_raises (FutureWarning , tv .aff_to_hdr , affine , hdr )
262
+ assert_raises (FutureWarning , tv .aff_to_hdr , affine , hdr , None , None )
263
+ assert_raises (FutureWarning , tv .aff_to_hdr , affine , hdr , False , None )
264
+ assert_raises (FutureWarning , tv .aff_to_hdr , affine , hdr , None , False )
265
+ # And has same effect as above
266
+ with IgnoreWarnings ():
208
267
tv .aff_to_hdr (affine , hdr )
209
- assert_array_almost_equal (tv .aff_from_hdr (hdr ), affine )
210
- # put flip into affine
211
- aff2 = affine .copy ()
212
- aff2 [:,2 ] *= - 1
213
- tv .aff_to_hdr (aff2 , hdr )
214
- assert_array_almost_equal (tv .aff_from_hdr (hdr ), aff2 )
215
- if version == 2 :
216
- assert_array_almost_equal (hdr ['vox_to_ras' ], aff2 )
268
+ assert_array_almost_equal (tv .aff_from_hdr (hdr , atleast_v2 = False ), affine )
269
+ # Check pos_vox and order flags
270
+ for hdr in ({}, {'version' :2 }, {'version' :1 }):
271
+ tv .aff_to_hdr (aff2 , hdr , pos_vox = True , set_order = False )
272
+ assert_array_equal (hdr ['voxel_size' ], [1 , 2 , 3 ])
273
+ assert_false ('voxel_order' in hdr )
274
+ tv .aff_to_hdr (aff2 , hdr , pos_vox = False , set_order = True )
275
+ assert_array_equal (hdr ['voxel_size' ], [- 1 , 2 , 3 ])
276
+ assert_equal (hdr ['voxel_order' ], 'RAI' )
277
+ tv .aff_to_hdr (aff2 , hdr , pos_vox = True , set_order = True )
278
+ assert_array_equal (hdr ['voxel_size' ], [1 , 2 , 3 ])
279
+ assert_equal (hdr ['voxel_order' ], 'RAI' )
280
+ if 'version' in hdr and hdr ['version' ] == 1 :
281
+ assert_false ('vox_to_ras' in hdr )
282
+ else :
283
+ assert_array_equal (hdr ['vox_to_ras' ], aff2 )
217
284
218
285
219
286
def test_tv_class ():
@@ -236,19 +303,28 @@ def test_tv_class():
236
303
# check that we check input values
237
304
out_f .truncate (0 ); out_f .seek (0 )
238
305
assert_raises (tv .HeaderError ,
239
- tv .TrackvisFile ,
240
- [],{'id_string' :'not OK' })
306
+ tv .TrackvisFile ,
307
+ [],{'id_string' :'not OK' })
241
308
assert_raises (tv .HeaderError ,
242
- tv .TrackvisFile ,
243
- [],{'version' : 3 })
309
+ tv .TrackvisFile ,
310
+ [],{'version' : 3 })
244
311
assert_raises (tv .HeaderError ,
245
- tv .TrackvisFile ,
246
- [],{'hdr_size' :0 })
312
+ tv .TrackvisFile ,
313
+ [],{'hdr_size' :0 })
247
314
affine = np .diag ([1 ,2 ,3 ,1 ])
248
315
affine [:3 ,3 ] = [10 ,11 ,12 ]
249
- tvf .set_affine (affine )
250
- assert_true (np .all (tvf .get_affine () == affine ))
316
+ # affine methods will raise same warnings and errors as function
317
+ with ErrorWarnings ():
318
+ assert_raises (FutureWarning , tvf .set_affine , affine )
319
+ assert_raises (FutureWarning , tvf .set_affine , affine , None , None )
320
+ assert_raises (FutureWarning , tvf .set_affine , affine , False , None )
321
+ assert_raises (FutureWarning , tvf .set_affine , affine , None , False )
322
+ assert_raises (FutureWarning , tvf .get_affine )
323
+ assert_raises (FutureWarning , tvf .get_affine , None )
324
+ tvf .set_affine (affine , pos_vox = True , set_order = True )
325
+ aff = tvf .get_affine (atleast_v2 = True )
326
+ assert_array_almost_equal (aff , affine )
251
327
# Test that we raise an error with an iterator
252
328
assert_raises (tv .TrackvisFileError ,
253
- tv .TrackvisFile ,
254
- iter ([]))
329
+ tv .TrackvisFile ,
330
+ iter ([]))
0 commit comments