def test_orient_by_rois(): streamlines = [np.array([[0, 0., 0], [1, 0., 0.], [2, 0., 0.]]), np.array([[2, 0., 0.], [1, 0., 0], [0, 0, 0.]])] # Make two ROIs: mask1_vol = np.zeros((4, 4, 4), dtype=bool) mask2_vol = np.zeros_like(mask1_vol) mask1_vol[0, 0, 0] = True mask2_vol[1, 0, 0] = True mask1_coords = np.array(np.where(mask1_vol)).T mask2_coords = np.array(np.where(mask2_vol)).T # If there is an affine, we'll use it: affine = np.eye(4) affine[:, 3] = [-1, 100, -20, 1] # Transform the streamlines: x_streamlines = [sl + affine[:3, 3] for sl in streamlines] for copy in [True, False]: for sl, affine in zip([streamlines, x_streamlines], [None, affine]): for mask1, mask2 in \ zip([mask1_vol, mask1_coords], [mask2_vol, mask2_coords]): new_streamlines = orient_by_rois(sl, mask1, mask2, affine=affine, copy=copy) if copy: flipped_sl = [sl[0], sl[1][::-1]] else: flipped_sl = [np.array([[0, 0., 0], [1, 0., 0.], [2, 0., 0.]]), np.array([[0, 0., 0.], [1, 0., 0], [2, 0, 0.]])] if affine is not None: flipped_sl = [s + affine[:3, 3] for s in flipped_sl] npt.assert_equal(new_streamlines, flipped_sl)
def test_orient_by_rois(): streamlines = [np.array([[0, 0., 0], [1, 0., 0.], [2, 0., 0.]]), np.array([[2, 0., 0.], [1, 0., 0], [0, 0, 0.]])] # Make two ROIs: mask1_vol = np.zeros((4, 4, 4), dtype=bool) mask2_vol = np.zeros_like(mask1_vol) mask1_vol[0, 0, 0] = True mask2_vol[1, 0, 0] = True mask1_coords = np.array(np.where(mask1_vol)).T mask2_coords = np.array(np.where(mask2_vol)).T # If there is an affine, we'll use it: affine = np.eye(4) affine[:, 3] = [-1, 100, -20, 1] # Transform the streamlines: x_streamlines = [sl + affine[:3, 3] for sl in streamlines] # After reorientation, this should be the answer: flipped_sl = [streamlines[0], streamlines[1][::-1]] new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=False) npt.assert_equal(new_streamlines, flipped_sl) npt.assert_(new_streamlines is not streamlines) # Test with affine: x_flipped_sl = [s + affine[:3, 3] for s in flipped_sl] new_streamlines = orient_by_rois(x_streamlines, mask1_vol, mask2_vol, in_place=False, affine=affine, as_generator=False) npt.assert_equal(new_streamlines, x_flipped_sl) npt.assert_(new_streamlines is not x_streamlines) # Test providing coord ROIs instead of vol ROIs: new_streamlines = orient_by_rois(x_streamlines, mask1_coords, mask2_coords, in_place=False, affine=affine, as_generator=False) npt.assert_equal(new_streamlines, x_flipped_sl) # Test with as_generator set to True new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, flipped_sl) # Test with as_generator set to True and with the affine new_streamlines = orient_by_rois(x_streamlines, mask1_vol, mask2_vol, in_place=False, affine=affine, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, x_flipped_sl) # Test with generator input: new_streamlines = orient_by_rois(generate_sl(streamlines), mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, flipped_sl) # Generator output cannot take a True `in_place` kwarg: npt.assert_raises(ValueError, orient_by_rois, *[generate_sl(streamlines), mask1_vol, mask2_vol], **dict(in_place=True, affine=None, as_generator=True)) # But you can input a generator and get a non-generator as output: new_streamlines = orient_by_rois(generate_sl(streamlines), mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=False) npt.assert_(not isinstance(new_streamlines, types.GeneratorType)) npt.assert_equal(new_streamlines, flipped_sl) # Modify in-place: new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=True, affine=None, as_generator=False) npt.assert_equal(new_streamlines, flipped_sl) # The two objects are one and the same: npt.assert_(new_streamlines is streamlines)
def test_orient_by_rois(): streamlines = [ np.array([[0, 0., 0], [1, 0., 0.], [2, 0., 0.]]), np.array([[2, 0., 0.], [1, 0., 0], [0, 0, 0.]]) ] # Make two ROIs: mask1_vol = np.zeros((4, 4, 4), dtype=bool) mask2_vol = np.zeros_like(mask1_vol) mask1_vol[0, 0, 0] = True mask2_vol[1, 0, 0] = True mask1_coords = np.array(np.where(mask1_vol)).T mask2_coords = np.array(np.where(mask2_vol)).T # If there is an affine, we'll use it: affine = np.eye(4) affine[:, 3] = [-1, 100, -20, 1] # Transform the streamlines: x_streamlines = [sl + affine[:3, 3] for sl in streamlines] # After reorientation, this should be the answer: flipped_sl = [streamlines[0], streamlines[1][::-1]] new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=False) npt.assert_equal(new_streamlines, flipped_sl) npt.assert_(new_streamlines is not streamlines) # Test with affine: x_flipped_sl = [s + affine[:3, 3] for s in flipped_sl] new_streamlines = orient_by_rois(x_streamlines, mask1_vol, mask2_vol, in_place=False, affine=affine, as_generator=False) npt.assert_equal(new_streamlines, x_flipped_sl) npt.assert_(new_streamlines is not x_streamlines) # Test providing coord ROIs instead of vol ROIs: new_streamlines = orient_by_rois(x_streamlines, mask1_coords, mask2_coords, in_place=False, affine=affine, as_generator=False) npt.assert_equal(new_streamlines, x_flipped_sl) # Test with as_generator set to True new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, flipped_sl) # Test with as_generator set to True and with the affine new_streamlines = orient_by_rois(x_streamlines, mask1_vol, mask2_vol, in_place=False, affine=affine, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, x_flipped_sl) # Test with generator input: new_streamlines = orient_by_rois(generate_sl(streamlines), mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=True) npt.assert_(isinstance(new_streamlines, types.GeneratorType)) ll = list(new_streamlines) npt.assert_equal(ll, flipped_sl) # Generator output cannot take a True `in_place` kwarg: npt.assert_raises(ValueError, orient_by_rois, *[generate_sl(streamlines), mask1_vol, mask2_vol], **dict(in_place=True, affine=None, as_generator=True)) # But you can input a generator and get a non-generator as output: new_streamlines = orient_by_rois(generate_sl(streamlines), mask1_vol, mask2_vol, in_place=False, affine=None, as_generator=False) npt.assert_(not isinstance(new_streamlines, types.GeneratorType)) npt.assert_equal(new_streamlines, flipped_sl) # Modify in-place: new_streamlines = orient_by_rois(streamlines, mask1_vol, mask2_vol, in_place=True, affine=None, as_generator=False) npt.assert_equal(new_streamlines, flipped_sl) # The two objects are one and the same: npt.assert_(new_streamlines is streamlines)
def segment(fdata, fbval, fbvec, streamlines, bundles, reg_template=None, mapping=None, as_generator=True, clip_to_roi=True, **reg_kwargs): """ Segment streamlines into bundles. Parameters ---------- fdata, fbval, fbvec : str Full path to data, bvals, bvecs streamlines : list of 2D arrays Each array is a streamline, shape (3, N). bundles: dict The format is something like:: {'name': {'ROIs':[img, img], 'rules':[True, True]}} reg_template : str or nib.Nifti1Image, optional. Template to use for registration (defaults to the MNI T2) mapping : DiffeomorphicMap object, str or nib.Nifti1Image, optional A mapping between DWI space and a template. Defaults to generate this. as_generator : bool, optional Whether to generate the streamlines here, or return generators. Default: True. clip_to_roi : bool, optional Whether to clip the streamlines between the ROIs """ img, data, gtab, mask = ut.prepare_data(fdata, fbval, fbvec) xform_sl = [ s for s in dtu.move_streamlines(streamlines, np.linalg.inv(img.affine)) ] if reg_template is None: reg_template = dpd.read_mni_template() if mapping is None: mapping = reg.syn_register_dwi(fdata, gtab, template=reg_template, **reg_kwargs) if isinstance(mapping, str) or isinstance(mapping, nib.Nifti1Image): mapping = reg.read_mapping(mapping, img, reg_template) fiber_groups = {} for bundle in bundles: select_sl = xform_sl for ROI, rule in zip(bundles[bundle]['ROIs'], bundles[bundle]['rules']): data = ROI.get_data() warped_ROI = patch_up_roi( mapping.transform_inverse(data, interpolation='nearest')) # This function requires lists as inputs: select_sl = dts.select_by_rois(select_sl, [warped_ROI.astype(bool)], [rule]) # Next, we reorient each streamline according to an ARBITRARY, but # CONSISTENT order. To do this, we use the first ROI for which the rule # is True as the first one to pass through, and the last ROI for which # the rule is True as the last one to pass through: # Indices where the 'rule' is True: idx = np.where(bundles[bundle]['rules']) orient_ROIs = [ bundles[bundle]['ROIs'][idx[0][0]], bundles[bundle]['ROIs'][idx[0][-1]] ] select_sl = dts.orient_by_rois(select_sl, orient_ROIs[0].get_data(), orient_ROIs[1].get_data(), as_generator=True) # XXX Implement clipping to the ROIs # if clip_to_roi: # dts.clip() if as_generator: fiber_groups[bundle] = select_sl else: fiber_groups[bundle] = list(select_sl) return fiber_groups
def segment(fdata, fbval, fbvec, streamlines, bundles, reg_template=None, mapping=None, as_generator=True, **reg_kwargs): """ generate : bool Whether to generate the streamlines here, or return generators. reg_template : template to use for registration (defaults to the MNI T2) bundles: dict The format is something like:: {'name': {'ROIs':[img, img], 'rules':[True, True]}} """ img, data, gtab, mask = ut.prepare_data(fdata, fbval, fbvec) xform_sl = [s for s in dtu.move_streamlines(streamlines, np.linalg.inv(img.affine))] if reg_template is None: reg_template = dpd.read_mni_template() if mapping is None: mapping = reg.syn_register_dwi(fdata, gtab, template=reg_template, **reg_kwargs) if isinstance(mapping, str) or isinstance(mapping, nib.Nifti1Image): mapping = reg.read_mapping(mapping, img, reg_template) fiber_groups = {} for bundle in bundles: select_sl = xform_sl for ROI, rule in zip(bundles[bundle]['ROIs'], bundles[bundle]['rules']): data = ROI.get_data() warped_ROI = patch_up_roi(mapping.transform_inverse( data, interpolation='nearest')) # This function requires lists as inputs: select_sl = dts.select_by_rois(select_sl, [warped_ROI.astype(bool)], [rule]) # Next, we reorient each streamline according to an ARBITRARY, but # CONSISTENT order. To do this, we use the first ROI for which the rule # is True as the first one to pass through, and the last ROI for which # the rule is True as the last one to pass through: # Indices where the 'rule' is True: idx = np.where(bundles[bundle]['rules']) orient_ROIs = [bundles[bundle]['ROIs'][idx[0][0]], bundles[bundle]['ROIs'][idx[0][-1]]] select_sl = dts.orient_by_rois(select_sl, orient_ROIs[0].get_data(), orient_ROIs[1].get_data(), in_place=True) if as_generator: fiber_groups[bundle] = select_sl else: fiber_groups[bundle] = list(select_sl) return fiber_groups