def test_multib0_dsi(): data, gtab = dsi_voxels() # Create a new data-set with a b0 measurement: new_data = np.concatenate([data, data[..., 0, None]], -1) new_bvecs = np.concatenate([gtab.bvecs, np.zeros((1, 3))]) new_bvals = np.concatenate([gtab.bvals, [0]]) new_gtab = gradient_table(new_bvals, new_bvecs) ds = DiffusionSpectrumModel(new_gtab) sphere = get_sphere('repulsion724') dsfit = ds.fit(new_data) pdf = dsfit.pdf() dsfit.odf(sphere) assert_equal(new_data.shape[:-1] + (17, 17, 17), pdf.shape) assert_equal(np.alltrue(np.isreal(pdf)), True) # And again, with one more b0 measurement (two in total): new_data = np.concatenate([data, data[..., 0, None]], -1) new_bvecs = np.concatenate([gtab.bvecs, np.zeros((1, 3))]) new_bvals = np.concatenate([gtab.bvals, [0]]) new_gtab = gradient_table(new_bvals, new_bvecs) ds = DiffusionSpectrumModel(new_gtab) dsfit = ds.fit(new_data) pdf = dsfit.pdf() dsfit.odf(sphere) assert_equal(new_data.shape[:-1] + (17, 17, 17), pdf.shape) assert_equal(np.alltrue(np.isreal(pdf)), True)
def visualize_pdf(pdf, gtab=None): signal = pdf s = signal.shape grid_s = math.ceil((signal.shape[-1])**(1 / 3)) signal = signal.reshape(*s[:-1], grid_s, grid_s, grid_s) sphere = get_sphere('repulsion724') if gtab: dsmodel = DiffusionSpectrumModel(gtab) signal_xq = np.fft.fftn(signal, axes=[-3, -2, -1]) dsfit = dsmodel.fit(signal_xq.reshape(*s[:2], -1)) odfs = dsfit.odf(sphere) else: signal = signal.reshape(-1, grid_s, grid_s, grid_s) odfs = np.stack([ get_odf(signal[vid], sphere) for vid in range(signal.shape[0]) ]).reshape(*s[:-1], -1) if len(odfs.shape) == 3: odfs = odfs[:, :, np.newaxis] # visualize r = window.Scene() sfu = actor.odf_slicer(odfs, sphere=sphere, colormap='plasma', scale=0.5) sfu.display(z=0) r.add(sfu) window.show(r)
def odf(self, sphere, gtab_dsi=None, mean=None, voxel_size=None, image_origin=None, spatial_idx=None, spatial_shape=None): if gtab_dsi is None: btable = np.loadtxt(get_data('dsi4169btable')) gtab_dsi = gradient_table(btable[:, 0], btable[:, 1:], big_delta=self.model.gtab.big_delta, small_delta=self.model.gtab.small_delta) pred = self.predict(gtab_dsi, mean=mean, voxel_size=voxel_size, image_origin=image_origin, spatial_idx=spatial_idx, spatial_shape=spatial_shape, compute_var=False) dsi_model = DiffusionSpectrumModel(gtab_dsi, qgrid_size=25, r_end=50, r_step=0.4, filter_width=np.inf) # dsi_model = DiffusionSpectrumModel(gtab_dsi, filter_width=np.inf) # dsi_model = DiffusionSpectrumDeconvModel(gtab_dsi) odf = dsi_model.fit(pred).odf(sphere) return odf
def test_multivox_dsi(): data, gtab = dsi_voxels() DS = DiffusionSpectrumModel(gtab) DSfit = DS.fit(data) PDF = DSfit.pdf() assert_equal(data.shape[:-1] + (17, 17, 17), PDF.shape) assert_equal(np.alltrue(np.isreal(PDF)), True)
def test_multivox_dsi(): data, gtab = dsi_voxels() DS = DiffusionSpectrumModel(gtab) get_sphere('symmetric724') DSfit = DS.fit(data) PDF = DSfit.pdf() assert_equal(data.shape[:-1] + (17, 17, 17), PDF.shape) assert_equal(np.alltrue(np.isreal(PDF)), True)
def test_multivox_dsi(): data, gtab = dsi_voxels() DS = DiffusionSpectrumModel(gtab, "standard") sphere = get_sphere("symmetric724") DS.direction_finder.config(sphere=sphere, min_separation_angle=25, relative_peak_threshold=0.35) DSfit = DS.fit(data) PDF = DSfit.pdf() assert_equal(data.shape[:-1] + (16, 16, 16), PDF.shape) assert_equal(np.alltrue(np.isreal(PDF)), True)
def test_dsi_metrics(): btable = np.loadtxt(get_fnames('dsi4169btable')) gtab = gradient_table(btable[:, 0], btable[:, 1:]) data, golden_directions = SticksAndBall(gtab, d=0.0015, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) dsmodel = DiffusionSpectrumModel(gtab, qgrid_size=21, filter_width=4500) rtop_signal_norm = dsmodel.fit(data).rtop_signal() dsmodel.fit(data).rtop_pdf() rtop_pdf = dsmodel.fit(data).rtop_pdf(normalized=False) assert_almost_equal(rtop_signal_norm, rtop_pdf, 6) dsmodel = DiffusionSpectrumModel(gtab, qgrid_size=21, filter_width=4500) mevals = np.array(([0.0015, 0.0003, 0.0003], [0.0015, 0.0003, 0.0003])) S_0, sticks_0 = MultiTensor(gtab, mevals, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) S_1, sticks_0 = MultiTensor(gtab, mevals * 2.0, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) MSD_norm_0 = dsmodel.fit(S_0).msd_discrete(normalized=True) MSD_norm_1 = dsmodel.fit(S_1).msd_discrete(normalized=True) assert_almost_equal(MSD_norm_0, 0.5 * MSD_norm_1, 4)
def dmri_test(): print("Loading slice...") sample_slice, qvecs = load_slice('./test_data/david_data', '3112_BL_data_subject_space.nii.gz') # sinc interpolate Sxq_cc, qvecs_s = interpolate_q_space_sinc(sample_slice, qvecs, 12) gtab = gtable_from_qvecs(qvecs_s) # visualize tensor field using dipy dsmodel = DiffusionSpectrumModel(gtab) dsfit = dsmodel.fit(Sxq_cc) sphere = get_sphere('repulsion724') odfs = dsfit.odf(sphere) vis_2d_field(odfs, sphere)
def test_dsi(): # load repulsion 724 sphere sphere = default_sphere # load icosahedron sphere sphere2 = create_unit_sphere(5) btable = np.loadtxt(get_fnames('dsi515btable')) gtab = gradient_table(btable[:, 0], btable[:, 1:]) data, golden_directions = sticks_and_ball(gtab, d=0.0015, S0=100, angles=[(0, 0), (90, 0)], fractions=[50, 50], snr=None) ds = DiffusionSpectrumModel(gtab) # repulsion724 dsfit = ds.fit(data) odf = dsfit.odf(sphere) directions, _, _ = peak_directions(odf, sphere) assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) # 5 subdivisions dsfit = ds.fit(data) odf2 = dsfit.odf(sphere2) directions, _, _ = peak_directions(odf2, sphere2) assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) assert_equal(dsfit.pdf().shape, 3 * (ds.qgrid_size, )) sb_dummies = sticks_and_ball_dummies(gtab) for sbd in sb_dummies: data, golden_directions = sb_dummies[sbd] odf = ds.fit(data).odf(sphere2) directions, _, _ = peak_directions(odf, sphere2) if len(directions) <= 3: assert_equal(len(directions), len(golden_directions)) if len(directions) > 3: assert_equal(gfa(odf) < 0.1, True) assert_raises(ValueError, DiffusionSpectrumModel, gtab, qgrid_size=16)
def test_dsi(): # load symmetric 724 sphere sphere = get_sphere('symmetric724') # load icosahedron sphere sphere2 = create_unit_sphere(5) btable = np.loadtxt(get_data('dsi515btable')) gtab = gradient_table(btable[:, 0], btable[:, 1:]) data, golden_directions = SticksAndBall(gtab, d=0.0015, S0=100, angles=[(0, 0), (90, 0)], fractions=[50, 50], snr=None) ds = DiffusionSpectrumModel(gtab) # symmetric724 dsfit = ds.fit(data) odf = dsfit.odf(sphere) directions, _, _ = peak_directions(odf, sphere) assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) # 5 subdivisions dsfit = ds.fit(data) odf2 = dsfit.odf(sphere2) directions, _, _ = peak_directions(odf2, sphere2) assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) assert_equal(dsfit.pdf().shape, 3 * (ds.qgrid_size, )) sb_dummies = sticks_and_ball_dummies(gtab) for sbd in sb_dummies: data, golden_directions = sb_dummies[sbd] odf = ds.fit(data).odf(sphere2) directions, _, _ = peak_directions(odf, sphere2) if len(directions) <= 3: assert_equal(len(directions), len(golden_directions)) if len(directions) > 3: assert_equal(gfa(odf) < 0.1, True) assert_raises(ValueError, DiffusionSpectrumModel, gtab, qgrid_size=16)
def test_multib0_dsi(): data, gtab = dsi_voxels() # Create a new data-set with a b0 measurement: new_data = np.concatenate([data, data[..., 0, None]], -1) new_bvecs = np.concatenate([gtab.bvecs, np.zeros((1, 3))]) new_bvals = np.concatenate([gtab.bvals, [0]]) new_gtab = gradient_table(new_bvals, new_bvecs) ds = DiffusionSpectrumModel(new_gtab) dsfit = ds.fit(new_data) pdf = dsfit.pdf() dsfit.odf(default_sphere) assert_equal(new_data.shape[:-1] + (17, 17, 17), pdf.shape) assert_equal(np.alltrue(np.isreal(pdf)), True) # And again, with one more b0 measurement (two in total): new_data = np.concatenate([data, data[..., 0, None]], -1) new_bvecs = np.concatenate([gtab.bvecs, np.zeros((1, 3))]) new_bvals = np.concatenate([gtab.bvals, [0]]) new_gtab = gradient_table(new_bvals, new_bvecs) ds = DiffusionSpectrumModel(new_gtab) dsfit = ds.fit(new_data) pdf = dsfit.pdf() dsfit.odf(default_sphere) assert_equal(new_data.shape[:-1] + (17, 17, 17), pdf.shape) assert_equal(np.alltrue(np.isreal(pdf)), True)
def test_dsi_metrics(): btable = np.loadtxt(get_data('dsi4169btable')) gtab = gradient_table(btable[:, 0], btable[:, 1:]) data, golden_directions = SticksAndBall(gtab, d=0.0015, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) data = data / float(data[0]) dsmodel = DiffusionSpectrumModel(gtab, qgrid_size=21, filter_width=4500) rtop_signal_norm = dsmodel.fit(data).rtop_signal() rtop_pdf_norm = dsmodel.fit(data).rtop_pdf() rtop_pdf = dsmodel.fit(data).rtop_pdf(normalized=False) assert_almost_equal(rtop_signal_norm, rtop_pdf, 10) mevals = np.array(([0.0015, 0.0003, 0.0003], [0.0015, 0.0003, 0.0003])) S_0, sticks_0 = MultiTensor(gtab, mevals, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) S_1, sticks_0 = MultiTensor(gtab, mevals * 2.0, S0=100, angles=[(0, 0), (60, 0)], fractions=[50, 50], snr=None) MSD_norm_0 = dsmodel.fit(S_0).msd_discrete(normalized=True) MSD_norm_1 = dsmodel.fit(S_1).msd_discrete(normalized=True) assert_almost_equal(MSD_norm_0, 0.5 * MSD_norm_1, 4)
def test_dsi(): #load symmetric 724 sphere sphere = get_sphere('symmetric724') #load icosahedron sphere sphere2 = create_unit_sphere(5) btable = np.loadtxt(get_data('dsi515btable')) bvals = btable[:,0] bvecs = btable[:,1:] data, golden_directions = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0)], fractions=[50, 50], snr=None) gtab = gradient_table(bvals, bvecs) ds = DiffusionSpectrumModel(gtab) #symmetric724 ds.direction_finder.config(sphere=sphere, min_separation_angle=25, relative_peak_threshold=.35) dsfit = ds.fit(data) odf = dsfit.odf(sphere) directions = dsfit.directions assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) #5 subdivisions ds.direction_finder.config(sphere=sphere2, min_separation_angle=25, relative_peak_threshold=.35) dsfit = ds.fit(data) odf2 = dsfit.odf(sphere2) directions = dsfit.directions assert_equal(len(directions), 2) assert_almost_equal(angular_similarity(directions, golden_directions), 2, 1) #from dipy.viz._show_odfs import show_odfs #show_odfs(odf[None,None,None,:], (sphere.vertices, sphere.faces)) #show_odfs(odf2[None,None,None,:], (sphere2.vertices, sphere2.faces)) assert_equal(dsfit.pdf.shape, 3 * (ds.qgrid_size, )) sb_dummies=sticks_and_ball_dummies(gtab) for sbd in sb_dummies: data, golden_directions = sb_dummies[sbd] odf = ds.fit(data).odf(sphere2) directions = ds.fit(data).directions #show_odfs(odf[None, None, None, :], (sphere2.vertices, sphere2.faces)) if len(directions) <= 3: assert_equal(len(ds.fit(data).directions), len(golden_directions)) if len(directions) > 3: assert_equal(gfa(ds.fit(data).odf(sphere2)) < 0.1, True)
def test_dsi(): #load odf sphere vertices,faces = sphere_vf_from('symmetric724') edges = unique_edges(faces) half_vertices,half_edges,half_faces=reduce_antipodal(vertices,faces) #load bvals and gradients btable=np.loadtxt(get_data('dsi515btable')) bvals=btable[:,0] bvecs=btable[:,1:] S,stics=SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0),(90,0),(90,90)], fractions=[50,50,0], snr=None) #pdf0,odf0,peaks0=standard_dsi_algorithm(S,bvals,bvecs) S2=S.copy() S2=S2.reshape(1,len(S)) odf_sphere=(vertices,faces) ds=DiffusionSpectrumModel( bvals, bvecs, odf_sphere) dsfit=ds.fit(S) assert_equal((dsfit.peak_values>0).sum(),3) #change thresholds ds.relative_peak_threshold = 0.5 ds.angular_distance_threshold = 30 dsfit = ds.fit(S) assert_equal((dsfit.peak_values>0).sum(),2) #assert_almost_equal(np.sum(ds.pdf(S)-pdf0),0) #assert_almost_equal(np.sum(ds.odf(ds.pdf(S))-odf0),0) assert_almost_equal(dsfit.gfa,np.array([0.5749720469955439])) #1 fiber S,stics=SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0),(90,0),(90,90)], fractions=[100,0,0], snr=None) ds=DiffusionSpectrumModel(bvals,bvecs,odf_sphere) dsfit=ds.fit(S) QA=dsfit.qa assert_equal(np.sum(QA>0),1) #2 fibers S,stics=SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0),(90,0),(90,90)], fractions=[50,50,0], snr=None) ds=DiffusionSpectrumModel(bvals,bvecs,odf_sphere) ds.relative_peak_threshold = 0.5 ds.angular_distance_threshold = 20 dsfit=ds.fit(S) QA=dsfit.qa assert_equal(np.sum(QA>0),2) #Give me 2 directions assert_equal(len(dsfit.get_directions()),2) #3 fibers S,stics=SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0),(90,0),(90,90)], fractions=[33,33,33], snr=None) ds=DiffusionSpectrumModel(bvals,bvecs,odf_sphere) ds.relative_peak_threshold = 0.5 dsfit=ds.fit(S,return_odf=True) QA=dsfit.qa assert_equal(np.sum(QA>0),3) #Give me 3 directions assert_equal(len(dsfit.get_directions()),3) #Recalculate the odf with a different sphere. vertices, faces = sphere_vf_from('symmetric724') odf1=dsfit.odf() print len(odf1) odf2=dsfit.odf((vertices,faces)) print len(odf2) assert_array_almost_equal(odf1,odf2) #isotropic S,stics=SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0),(90,0),(90,90)], fractions=[0,0,0], snr=None) ds=DiffusionSpectrumModel(bvals,bvecs,odf_sphere) dsfit=ds.fit(S) QA=dsfit.qa assert_equal(np.sum(QA>0),0)
img contains a nibabel Nifti1Image object (data) and gtab contains a GradientTable object (gradient information e.g. b-values). For example to read the b-values it is possible to write print(gtab.bvals). Load the raw diffusion data and the affine. """ data = img.get_data() affine = img.affine print('data.shape (%d, %d, %d, %d)' % data.shape) """ Instantiate the Model and apply it to the data. """ dsmodel = DiffusionSpectrumModel(gtab, qgrid_size=35, filter_width=18.5) """ Lets just use one slice only from the data. """ dataslice = data[30:70, 20:80, data.shape[2] / 2] """ Normalize the signal by the b0 """ dataslice = dataslice / (dataslice[..., 0, None]).astype(np.float) """ Calculate the return to origin probability on the signal
elapsed = time.time() - t print(' time %d' %elapsed) # Convert result to dir format t = time.time() print('... convert peaks to dir format') dsidir = prepare_dir(dsipeaks, sphere, 0, 0, 1) name = os.path.join(main_dir,tp,'CMP','scalars','dsideconv_dir.nii.gz') nib.save(nib.Nifti1Image(dsidir, affine), name) elapsed = time.time() - t print(' time %d' %elapsed) # Classic DSI reconstruction t = time.time() print('... perform classic DSI reconstruction') dsmodel_dsi = DiffusionSpectrumModel(gtab) dsifit = dsmodel_dsi.fit(data) odfs = dsifit.odf(sphere) GFA = gfa(odfs) name = os.path.join(main_dir,tp,'CMP','scalars','dsidipy_gfa.nii.gz') nib.save(nib.Nifti1Image(GFA, affine), name) name = os.path.join(main_dir,tp,'CMP','scalars','dsidipy_odf.nii.gz') nib.save(nib.Nifti1Image(odfs, affine), name) elapsed = time.time() - t print(' time %d' %elapsed)
from dipy.align.aniso2iso import resample new_zooms = (2., 2., 2.) data, affine = resample(data, affine, zooms, new_zooms) # print('data.shape (%d, %d, %d, %d)' % data.shape) from dipy.data import get_sphere sphere = get_sphere('symmetric724') from dipy.reconst.dsi import DiffusionSpectrumModel dsmodel = DiffusionSpectrumModel(gtab) dsfit = dsmodel.fit(data) odfs = dsfit.odf(sphere) from dipy.reconst.odf import gfa GFA = gfa(odfs) fodfs = dname + 'odfs_dsi.nii.gz' fgfa = dname + 'gfa_dsi.nii.gz' nib.save(nib.Nifti1Image(odfs, affine), fodfs) nib.save(nib.Nifti1Image(GFA, affine), fgfa)
100, angles=directions, fractions=fractions, snr=None) sphere = get_sphere('symmetric724').subdivide(1) odf_gt = multi_tensor_odf(sphere.vertices, evals, angles=directions, fractions=fractions) """ Perform the reconstructions with standard DSI and DSI with deconvolution. """ dsi_model = DiffusionSpectrumModel(gtab) dsi_odf = dsi_model.fit(signal).odf(sphere) dsid_model = DiffusionSpectrumDeconvModel(gtab) dsid_odf = dsid_model.fit(signal).odf(sphere) """ Finally, we can visualize the ground truth ODF, together with the DSI and DSI with deconvolution ODFs and observe that with the deconvolved method it is easier to resolve the correct fiber directions because the ODF is sharper. """ from dipy.viz import window, actor # Enables/disables interactive visualization
fractions = [50, 50] signal, _ = multi_tensor(gtab, evals, 100, angles=directions, fractions=fractions, snr=None) sphere = get_sphere('symmetric724').subdivide(1) odf_gt = multi_tensor_odf(sphere.vertices, evals, angles=directions, fractions=fractions) """ Perform the reconstructions with standard DSI and DSI with deconvolution. """ dsi_model = DiffusionSpectrumModel(gtab) dsi_odf = dsi_model.fit(signal).odf(sphere) dsid_model = DiffusionSpectrumDeconvModel(gtab) dsid_odf = dsid_model.fit(signal).odf(sphere) """ Finally, we can visualize the ground truth ODF, together with the DSI and DSI with deconvolution ODFs and observe that with the deconvolved method it is easier to resolve the correct fiber directions because the ODF is sharper. """ from dipy.viz import fvtk
data.shape ``(96, 96, 60, 203)`` This dataset has anisotropic voxel sizes, therefore reslicing is necessary. """ affine = img.get_affine() """ Read the voxel size from the image header. """ voxel_size = img.get_header().get_zooms()[:3] """ Instantiate the Model and apply it to the data. """ dsmodel = DiffusionSpectrumModel(gtab) """ Lets just use one slice only from the data. """ dataslice = data[:, :, data.shape[2] / 2] dsfit = dsmodel.fit(dataslice) """ Load an odf reconstruction sphere """ sphere = get_sphere('symmetric724') """ Calculate the ODFs with this specific sphere """
normalize_peaks=False) ddsfit = dds.fit(SS) ddsodf = ddsfit.odf(sphere) ddsdir, _, _ = peak_directions(ddsodf, sphere, .35, 15) print angular_similarity(sticks, ddsdir) grid_size = 35 ds = DiffusionSpectrumModel(gtab_full, qgrid_size=grid_size, r_start=0.2 * (grid_size // 2), r_end=0.7 * (grid_size // 2), r_step=0.02 * (grid_size // 2), filter_width=np.inf, normalize_peaks=False) dsfit = ds.fit(SS) dsodf = dsfit.odf(sphere) dsdir, _, _ = peak_directions(dsodf, sphere, .35, 15) print angular_similarity(sticks, dsdir) show_odfs(gqodf[None, None, None, :], sphere) show_odfs(dsodf[None, None, None, :], sphere) show_odfs(ddsodf[None, None, None, :], sphere)
This dataset has anisotropic voxel sizes, therefore reslicing is necessary. """ affine = img.get_affine() """ Read the voxel size from the image header. """ voxel_size = img.get_header().get_zooms()[:3] """ Instantiate the Model and apply it to the data. """ dsmodel = DiffusionSpectrumModel(gtab) """ Lets just use one slice only from the data. """ dataslice = data[:, :, data.shape[2] / 2] dsfit = dsmodel.fit(dataslice) """ Load an odf reconstruction sphere """ sphere = get_sphere('symmetric724')
import numpy as np from dipy.data import get_sphere from dipy.reconst.dsi import DiffusionSpectrumDeconvModel, DiffusionSpectrumModel from undersample.generate_mask import generate_kq_power_density_mask from undersample.undersample import undersample from undersample.interpolate import interpolate_q_space_sinc from undersample.utils import vis_2d_field, gtable_from_qvecs, load_slice if __name__ == "__main__": print("Loading slice...") sample_slice, qvecs = load_slice('./test_data/T1w/Diffusion') interpolated_gt, _ = interpolate_q_space_sinc(sample_slice, qvecs, 12) print("Generating mask...") mask = generate_kq_power_density_mask(0.5, 0.6, 2, 36, 12, 4) print("Undersampling...") undersampled_slice, q_grid = undersample(sample_slice, mask, qvecs) print("Done undersampling!") print("Reconstructing using DSI") sphere = get_sphere('repulsion724') gtab = gtable_from_qvecs(q_grid) dsmodel = DiffusionSpectrumModel(gtab) dsfit = dsmodel.fit(undersampled_slice.reshape(*undersampled_slice.shape[0:2], -1)) #dsfit = dsmodel.fit(interpolated_gt) odfs = dsfit.odf(sphere) vis_2d_field(odfs, sphere)
def run(context): #################################################### # Get the path to input files and other parameter # #################################################### analysis_data = context.fetch_analysis_data() settings = analysis_data['settings'] postprocessing = settings['postprocessing'] dataset = settings['dataset'] if dataset == "HCPL": dwi_file_handle = context.get_files('input', modality='HARDI')[0] dwi_file_path = dwi_file_handle.download('/root/') bvalues_file_handle = context.get_files( 'input', reg_expression='.*prep.bvalues.hcpl.txt')[0] bvalues_file_path = bvalues_file_handle.download('/root/') bvecs_file_handle = context.get_files( 'input', reg_expression='.*prep.gradients.hcpl.txt')[0] bvecs_file_path = bvecs_file_handle.download('/root/') elif dataset == "DSI": dwi_file_handle = context.get_files('input', modality='DSI')[0] dwi_file_path = dwi_file_handle.download('/root/') bvalues_file_handle = context.get_files( 'input', reg_expression='.*prep.bvalues.txt')[0] bvalues_file_path = bvalues_file_handle.download('/root/') bvecs_file_handle = context.get_files( 'input', reg_expression='.*prep.gradients.txt')[0] bvecs_file_path = bvecs_file_handle.download('/root/') else: context.set_progress(message='Wrong dataset parameter') inject_file_handle = context.get_files( 'input', reg_expression='.*prep.inject.nii.gz')[0] inject_file_path = inject_file_handle.download('/root/') VUMC_ROIs_file_handle = context.get_files( 'input', reg_expression='.*VUMC_ROIs.nii.gz')[0] VUMC_ROIs_file_path = VUMC_ROIs_file_handle.download('/root/') ############################### # _____ _____ _______ __ # # | __ \_ _| __ \ \ / / # # | | | || | | |__) \ \_/ / # # | | | || | | ___/ \ / # # | |__| || |_| | | | # # |_____/_____|_| |_| # # # ############################### ######################################################################################## # _______ _ __ __ _______ _ __ # # |__ __| | | | \/ | |__ __| | | / _| # # | |_ __ __ _ ___| | ___ _| \ / | ___| |_ __ __ _ ___| | _| |_ __ _ ___ ___ # # | | '__/ _` |/ __| |/ / | | | |\/| |/ __| | '__/ _` |/ __| |/ / _/ _` |/ __/ _ \ # # | | | | (_| | (__| <| |_| | | | | (__| | | | (_| | (__| <| || (_| | (_| __/ # # |_|_| \__,_|\___|_|\_\\__, |_| |_|\___|_|_| \__,_|\___|_|\_\_| \__,_|\___\___| # # __/ | # # |___/ # # # # # # IronTract Team # ######################################################################################## ################# # Load the data # ################# dwi_img = nib.load(dwi_file_path) bvals, bvecs = read_bvals_bvecs(bvalues_file_path, bvecs_file_path) gtab = gradient_table(bvals, bvecs) ############################################ # Extract the brain mask from the b0 image # ############################################ _, brain_mask = median_otsu(dwi_img.get_data()[:, :, :, 0], median_radius=2, numpass=1) ################################################################## # Fit the tensor model and compute the fractional anisotropy map # ################################################################## context.set_progress(message='Processing voxel-wise DTI metrics.') tenmodel = TensorModel(gtab) tenfit = tenmodel.fit(dwi_img.get_data(), mask=brain_mask) FA = fractional_anisotropy(tenfit.evals) stopping_criterion = ThresholdStoppingCriterion(FA, 0.2) sphere = get_sphere("repulsion724") seed_mask_img = nib.load(inject_file_path) affine = seed_mask_img.affine seeds = utils.random_seeds_from_mask(seed_mask_img.get_data(), affine, seed_count_per_voxel=True, seeds_count=5000) if dataset == "HCPL": ################################################ # Compute Fiber Orientation Distribution (CSD) # ################################################ context.set_progress(message='Processing voxel-wise FOD estimation.') response, _ = auto_response_ssst(gtab, dwi_img.get_data(), roi_radii=10, fa_thr=0.7) csd_model = ConstrainedSphericalDeconvModel(gtab, response, sh_order=8) csd_fit = csd_model.fit(dwi_img.get_data(), mask=brain_mask) shm = csd_fit.shm_coeff prob_dg = ProbabilisticDirectionGetter.from_shcoeff(shm, max_angle=20., sphere=sphere, pmf_threshold=0.1) elif dataset == "DSI": context.set_progress(message='Processing voxel-wise DSI estimation.') dsmodel = DiffusionSpectrumModel(gtab) dsfit = dsmodel.fit(dwi_img.get_data()) ODFs = dsfit.odf(sphere) prob_dg = ProbabilisticDirectionGetter.from_pmf(ODFs, max_angle=20., sphere=sphere, pmf_threshold=0.01) ########################################### # Compute DIPY Probabilistic Tractography # ########################################### context.set_progress(message='Processing tractography.') streamline_generator = LocalTracking(prob_dg, stopping_criterion, seeds, affine, step_size=.2, max_cross=1) streamlines = Streamlines(streamline_generator) # sft = StatefulTractogram(streamlines, seed_mask_img, Space.RASMM) # streamlines_file_path = "/root/streamlines.trk" # save_trk(sft, streamlines_file_path) ########################################################################### # Compute 3D volumes for the IronTract Challenge. For 'EPFL', we only # # keep streamlines with length > 1mm. We compute the visitation count # # image and apply a small gaussian smoothing. The gaussian smoothing # # is especially usefull to increase voxel coverage of deterministic # # algorithms. The log of the smoothed visitation count map is then # # iteratively thresholded producing 200 volumes/operation points. # # For VUMC, additional streamline filtering is done using anatomical # # priors (keeping only streamlines that intersect with at least one ROI). # ########################################################################### if postprocessing in ["EPFL", "ALL"]: context.set_progress(message='Processing density map (EPFL)') volume_folder = "/root/vol_epfl" output_epfl_zip_file_path = "/root/TrackyMcTrackface_EPFL_example.zip" os.mkdir(volume_folder) lengths = length(streamlines) streamlines = streamlines[lengths > 1] density = utils.density_map(streamlines, affine, seed_mask_img.shape) density = scipy.ndimage.gaussian_filter(density.astype("float32"), 0.5) log_density = np.log10(density + 1) max_density = np.max(log_density) for i, t in enumerate(np.arange(0, max_density, max_density / 200)): nbr = str(i) nbr = nbr.zfill(3) mask = log_density >= t vol_filename = os.path.join(volume_folder, "vol" + nbr + "_t" + str(t) + ".nii.gz") nib.Nifti1Image(mask.astype("int32"), affine, seed_mask_img.header).to_filename(vol_filename) shutil.make_archive(output_epfl_zip_file_path[:-4], 'zip', volume_folder) if postprocessing in ["VUMC", "ALL"]: context.set_progress(message='Processing density map (VUMC)') ROIs_img = nib.load(VUMC_ROIs_file_path) volume_folder = "/root/vol_vumc" output_vumc_zip_file_path = "/root/TrackyMcTrackface_VUMC_example.zip" os.mkdir(volume_folder) lengths = length(streamlines) streamlines = streamlines[lengths > 1] rois = ROIs_img.get_fdata().astype(int) _, grouping = utils.connectivity_matrix(streamlines, affine, rois, inclusive=True, return_mapping=True, mapping_as_streamlines=False) streamlines = streamlines[grouping[(0, 1)]] density = utils.density_map(streamlines, affine, seed_mask_img.shape) density = scipy.ndimage.gaussian_filter(density.astype("float32"), 0.5) log_density = np.log10(density + 1) max_density = np.max(log_density) for i, t in enumerate(np.arange(0, max_density, max_density / 200)): nbr = str(i) nbr = nbr.zfill(3) mask = log_density >= t vol_filename = os.path.join(volume_folder, "vol" + nbr + "_t" + str(t) + ".nii.gz") nib.Nifti1Image(mask.astype("int32"), affine, seed_mask_img.header).to_filename(vol_filename) shutil.make_archive(output_vumc_zip_file_path[:-4], 'zip', volume_folder) ################### # Upload the data # ################### context.set_progress(message='Uploading results...') #context.upload_file(fa_file_path, 'fa.nii.gz') # context.upload_file(fod_file_path, 'fod.nii.gz') # context.upload_file(streamlines_file_path, 'streamlines.trk') if postprocessing in ["EPFL", "ALL"]: context.upload_file(output_epfl_zip_file_path, 'TrackyMcTrackface_' + dataset +'_EPFL.zip') if postprocessing in ["VUMC", "ALL"]: context.upload_file(output_vumc_zip_file_path, 'TrackyMcTrackface_' + dataset +'_VUMC.zip')
def test_dsi(): #load odf sphere vertices, faces = sphere_vf_from('symmetric724') edges = unique_edges(faces) half_vertices, half_edges, half_faces = reduce_antipodal(vertices, faces) #load bvals and gradients btable = np.loadtxt(get_data('dsi515btable')) bvals = btable[:, 0] bvecs = btable[:, 1:] S, stics = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0), (90, 90)], fractions=[50, 50, 0], snr=None) #pdf0,odf0,peaks0=standard_dsi_algorithm(S,bvals,bvecs) S2 = S.copy() S2 = S2.reshape(1, len(S)) odf_sphere = (vertices, faces) ds = DiffusionSpectrumModel(bvals, bvecs, odf_sphere) dsfit = ds.fit(S) assert_equal((dsfit.peak_values > 0).sum(), 3) #change thresholds ds.relative_peak_threshold = 0.5 ds.angular_distance_threshold = 30 dsfit = ds.fit(S) assert_equal((dsfit.peak_values > 0).sum(), 2) #assert_almost_equal(np.sum(ds.pdf(S)-pdf0),0) #assert_almost_equal(np.sum(ds.odf(ds.pdf(S))-odf0),0) assert_almost_equal(dsfit.gfa, np.array([0.5749720469955439])) #1 fiber S, stics = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0), (90, 90)], fractions=[100, 0, 0], snr=None) ds = DiffusionSpectrumModel(bvals, bvecs, odf_sphere) dsfit = ds.fit(S) QA = dsfit.qa assert_equal(np.sum(QA > 0), 1) #2 fibers S, stics = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0), (90, 90)], fractions=[50, 50, 0], snr=None) ds = DiffusionSpectrumModel(bvals, bvecs, odf_sphere) ds.relative_peak_threshold = 0.5 ds.angular_distance_threshold = 20 dsfit = ds.fit(S) QA = dsfit.qa assert_equal(np.sum(QA > 0), 2) #Give me 2 directions assert_equal(len(dsfit.get_directions()), 2) #3 fibers S, stics = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0), (90, 90)], fractions=[33, 33, 33], snr=None) ds = DiffusionSpectrumModel(bvals, bvecs, odf_sphere) ds.relative_peak_threshold = 0.5 dsfit = ds.fit(S, return_odf=True) QA = dsfit.qa assert_equal(np.sum(QA > 0), 3) #Give me 3 directions assert_equal(len(dsfit.get_directions()), 3) #Recalculate the odf with a different sphere. vertices, faces = sphere_vf_from('symmetric724') odf1 = dsfit.odf() print len(odf1) odf2 = dsfit.odf((vertices, faces)) print len(odf2) assert_array_almost_equal(odf1, odf2) #isotropic S, stics = SticksAndBall(bvals, bvecs, d=0.0015, S0=100, angles=[(0, 0), (90, 0), (90, 90)], fractions=[0, 0, 0], snr=None) ds = DiffusionSpectrumModel(bvals, bvecs, odf_sphere) dsfit = ds.fit(S) QA = dsfit.qa assert_equal(np.sum(QA > 0), 0)
Load the raw diffusion data and the affine. """ data, affine = load_nifti(fraw) bvals, bvecs = read_bvals_bvecs(fbval, fbvec) bvecs[1:] = (bvecs[1:] / np.sqrt(np.sum(bvecs[1:] * bvecs[1:], axis=1))[:, None]) gtab = gradient_table(bvals, bvecs) print('data.shape (%d, %d, %d, %d)' % data.shape) """ Instantiate the Model and apply it to the data. """ dsmodel = DiffusionSpectrumModel(gtab, qgrid_size=35, filter_width=18.5) """ Let's just use one slice only from the data. """ dataslice = data[30:70, 20:80, data.shape[2] // 2] """ Normalize the signal by the b0 """ dataslice = dataslice / (dataslice[..., 0, None]).astype(float) """ Calculate the return to origin probability on the signal that corresponds to the integral of the signal. """