diff --git a/.gitignore b/.gitignore index a21b99bf..ba0c6610 100644 --- a/.gitignore +++ b/.gitignore @@ -40,5 +40,10 @@ coverage.xml *.pyc phantoms/MR_XCAT_qMRI/*.json phantoms/MR_XCAT_qMRI/*.txt +phantoms/brain/data/*.nii.gz +phantoms/brain/ground_truth/*.nii.gz tests/IVIMmodels/unit_tests/models models +temp +.vscode +.env diff --git a/doc/code_contributions_record.csv b/doc/code_contributions_record.csv index a3471709..dd7753c4 100644 --- a/doc/code_contributions_record.csv +++ b/doc/code_contributions_record.csv @@ -29,4 +29,5 @@ IVIM,Fitting,LSQ fitting,Part of the SUPER-IVIM-DC python package - trust region IVIM,Fitting,LSQ fitting,Part of the SUPER-IVIM-DC python package - segmented algorithm,TCML_TechnionIIT,TF2.4_IVIM-MRI_CodeCollection/src/original/TCML_TechnionIIT/SUPER-IVIM-DC,Noam Korngut/Elad Rotman/Onur Afacan Sila Kurugol/Yael Zaffrani-Reznikov/Shira Nemirovsky-Rotman/Simon Warfield/Moti Freiman,TCML Technion IIT,super_ivim_dc.source.Classsic_ivim_fit.IVIM_fit_sls,https://doi.org/10.1007/978-3-031-16434-7_71,TCML_TechnionIIT_lsqSLS IVIM,Fitting,LSQ fitting,Part of the SUPER-IVIM-DC python package - Levenberg Marquart lsq algorithm initialized with segmented fitting,TCML_TechnionIIT,TF2.4_IVIM-MRI_CodeCollection/src/original/TCML_TechnionIIT/SUPER-IVIM-DC,Noam Korngut/Elad Rotman/Onur Afacan Sila Kurugol/Yael Zaffrani-Reznikov/Shira Nemirovsky-Rotman/Simon Warfield/Moti Freiman,TCML Technion IIT,super_ivim_dc.source.Classsic_ivim_fit.IVIM_fit_sls_lm,https://doi.org/10.1007/978-3-031-16434-7_71,TCML_TechnionIIT_lsq_sls_lm IVIM,Fitting,LSQ fitting,Part of the SUPER-IVIM-DC python package - trust region lsq algorithm initialized with segmented fitting,TCML_TechnionIIT,TF2.4_IVIM-MRI_CodeCollection/src/original/TCML_TechnionIIT/SUPER-IVIM-DC,Noam Korngut/Elad Rotman/Onur Afacan Sila Kurugol/Yael Zaffrani-Reznikov/Shira Nemirovsky-Rotman/Simon Warfield/Moti Freiman,TCML Technion IIT,super_ivim_dc.source.Classsic_ivim_fit.IVIM_fit_sls_trf,https://doi.org/10.1007/978-3-031-16434-7_71,TCML_TechnionIIT_lsq_sls_trf -IVIM,Fitting,Segmented linear fitting,Consensus algorithm,TF_reference,TF2.4_IVIM-MRI_CodeCollection/src/original/TF_reference/,Ben Neijndorff/OSIPI taskforce 2.4,OSIPI,segmented_IVIMfit,tba,TF_reference_IVIMfit \ No newline at end of file +IVIM,Fitting,Segmented linear fitting,Consensus algorithm,TF_reference,TF2.4_IVIM-MRI_CodeCollection/src/original/TF_reference/,Ben Neijndorff/OSIPI taskforce 2.4,OSIPI,segmented_IVIMfit,tba,TF_reference_IVIMfit +IVIM,Preprocessing,Full pipeline,Brain pipeline,EP_GU,TF2.4_IVIM-MRI_CodeCollection/src/original/EP_GU,Elina Petersson,University of Gothenburg,brain_preproc,tba, \ No newline at end of file diff --git a/src/original/DK_OGC_AmsterdamUMC/__init__.py b/phantoms/__init__.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/__init__.py rename to phantoms/__init__.py diff --git a/phantoms/brain/ground_truth/ballistic_groundtruth.json b/phantoms/brain/ground_truth/ballistic_groundtruth.json index 6a5a7995..d4709f81 100644 --- a/phantoms/brain/ground_truth/ballistic_groundtruth.json +++ b/phantoms/brain/ground_truth/ballistic_groundtruth.json @@ -1,6 +1,9 @@ { + "tissues": ["WM","GM","CSF"], "D":[1.2e-3,0.98e-3,3e-3], "f":[0.0243,0.0164,0], "vd":[1.71,1.73,0], - "Db":1.75e-3 + "Db":1.75e-3, + "T1":[1.0, 1.5, 3.4], + "T2":[0.046,0.068,0.45] } \ No newline at end of file diff --git a/phantoms/brain/ground_truth/diffusive_groundtruth.json b/phantoms/brain/ground_truth/diffusive_groundtruth.json index 27ac53d6..d6bcda7a 100644 --- a/phantoms/brain/ground_truth/diffusive_groundtruth.json +++ b/phantoms/brain/ground_truth/diffusive_groundtruth.json @@ -1,5 +1,8 @@ { + "tissues": ["WM","GM","CSF"], "D":[0.81e-3,0.86e-3,3e-3], "f":[0.044,0.033,0], - "Dstar":[84e-3,76e-3,0] -} \ No newline at end of file + "Dstar":[84e-3,76e-3,0], + "T1":[1.0, 1.5, 3.4], + "T2":[0.046,0.068,0.45] +} diff --git a/phantoms/brain/sim_brain_phantom.py b/phantoms/brain/sim_brain_phantom.py index d5ba89a5..295f0f6c 100644 --- a/phantoms/brain/sim_brain_phantom.py +++ b/phantoms/brain/sim_brain_phantom.py @@ -6,23 +6,28 @@ from scipy.ndimage import zoom from utilities.data_simulation.Download_data import download_data -if __name__ == "__main__": +DIFFUSIVE_REGIME = 'diffusive' +BALLISTIC_REGIME = 'ballistic' + +def simulate_brain_phantom(regime=DIFFUSIVE_REGIME, snr=100, sim_relaxation=True, TE=60e-3, TR=5, resolution=[3,3,3]): + ''' + Simulation parameters can be set by changing the default values of the function arguments. + The default values are chosen to be suitable for a diffusive regime phantom, but can be changed to simulate a ballistic regime phantom as well. + The simulated image is saved in phantoms/brain/data with the name 'diffusive_sn{snr}.nii.gz' or 'ballistic_sn{snr}.nii.gz' depending on the regime. + The corresponding bvals and cvals (if applicable) are also saved in the same folder. + + regime: 'diffusive' or 'ballistic' to choose the type of phantom to simulate + snr: signal-to-noise ratio of the simulated image + sim_relaxation: whether to simulate T1 and T2 relaxation effects in the signal + TE: echo time in seconds + TR: repetition time in seconds + resolution: voxel size in mm + ''' download_data() - DIFFUSIVE_REGIME = 'diffusive' - BALLISTIC_REGIME = 'ballistic' folder = os.path.dirname(__file__) - ########################### - # Simulation parameters # - regime = DIFFUSIVE_REGIME - snr = 200 - resolution = [3,3,3] - # # - ########################### - - # Ground truth nii = nib.load(os.path.join(os.path.split(os.path.split(folder)[0])[0],'download','Phantoms','brain','ground_truth','hrgt_icbm_2009a_nls_3t.nii.gz')) segmentation = np.squeeze(nii.get_fdata()[...,-1]) @@ -40,20 +45,30 @@ # Calculate signal S = np.zeros(list(np.shape(segmentation))+[b.size]) - + print(ivim_pars) if regime == BALLISTIC_REGIME: Db = ivim_pars["Db"] - for i,(D,f,vd) in enumerate(zip(ivim_pars["D"],ivim_pars["f"],ivim_pars["vd"])): + for i,(D,f,vd,T1,T2) in enumerate(zip(ivim_pars["D"],ivim_pars["f"],ivim_pars["vd"],ivim_pars["T1"],ivim_pars["T2"])): S[segmentation==i+1,:] = S0*((1-f)*np.exp(-b*D)+f*np.exp(-b*Db-c**2*vd**2)) + if sim_relaxation: + S[segmentation==i+1,:] *= np.exp(-TE/T2)*(1-np.exp(-TR/T1)) else: - for i,(D,f,Dstar) in enumerate(zip(ivim_pars["D"],ivim_pars["f"],ivim_pars["Dstar"])): + for i,(D,f,Dstar,T1,T2) in enumerate(zip(ivim_pars["D"],ivim_pars["f"],ivim_pars["Dstar"],ivim_pars["T1"],ivim_pars["T2"])): S[segmentation==i+1,:] = S0*((1-f)*np.exp(-b*D)+f*np.exp(-b*Dstar)) + if sim_relaxation: + S[segmentation==i+1,:] *= np.exp(-TE/T2)*(1-np.exp(-TR/T1)) # Resample to suitable resolution im = zoom(S,np.append(np.diag(nii.affine)[:3]/np.array(resolution),1),order=1) sz = im.shape - # Add noise + # Save image without noise for reference + nii_out = nib.Nifti1Image(im,np.eye(4)) + base_name = os.path.join(folder,'data','{}_reference'.format(regime,snr)) + nib.save(nii_out,base_name+'.nii.gz') + shutil.copyfile(bval_file,base_name+'.bval') + + # Add Rician noise im_noise = np.abs(im + S0/snr*(np.random.randn(sz[0],sz[1],sz[2],sz[3])+1j*np.random.randn(sz[0],sz[1],sz[2],sz[3]))) # Save as image and sequence parameters @@ -62,4 +77,14 @@ nib.save(nii_out,base_name+'.nii.gz') shutil.copyfile(bval_file,base_name+'.bval') if regime == BALLISTIC_REGIME: - shutil.copyfile(cval_file,base_name+'.cval') \ No newline at end of file + shutil.copyfile(cval_file,base_name+'.cval') + + # Resample and save segmentation + segmentation = zoom(segmentation,np.diag(nii.affine)[:3]/np.array(resolution),order=0) + nii_out = nib.Nifti1Image(segmentation,np.eye(4)) + base_name = os.path.join(folder,'data','{}_snr{}_mask'.format(regime,snr)) + nib.save(nii_out,base_name+'.nii.gz') + + +if __name__ == "__main__": + simulate_brain_phantom() diff --git a/pytest.ini b/pytest.ini index 1d85aaef..b3286ddb 100644 --- a/pytest.ini +++ b/pytest.ini @@ -3,6 +3,7 @@ markers = slow: marks tests as slow (deselect with '-m "not slow"') addopts = -m 'not slow' + --ignore-glob=**/wip_*.py testpaths = tests filterwarnings = ignore::Warning diff --git a/requirements.txt b/requirements.txt index 3250d946..d445ba1c 100644 --- a/requirements.txt +++ b/requirements.txt @@ -18,4 +18,7 @@ sphinx_rtd_theme pytest-json-report statsmodels ivimnet -nlopt \ No newline at end of file +nlopt +nipype +itk +#ivim-mri \ No newline at end of file diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/.gitignore b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/.gitignore similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/.gitignore rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/.gitignore diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/IVIM_standard_bcin.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/IVIM_standard_bcin.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/IVIM_standard_bcin.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/IVIM_standard_bcin.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/README.md b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/README.md old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/README.md rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/README.md diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/avgRepeatBvalVols.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/avgRepeatBvalVols.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/avgRepeatBvalVols.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/avgRepeatBvalVols.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/bvalOrderFix.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/bvalOrderFix.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/bvalOrderFix.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/bvalOrderFix.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/dataPrepDWI.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/dataPrepDWI.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/dataPrepDWI.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/dataPrepDWI.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/demo_QAMPER_IVIM.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/demo_QAMPER_IVIM.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/demo_QAMPER_IVIM.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/demo_QAMPER_IVIM.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/getTestData.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/getTestData.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/getTestData.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/getTestData.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/inpaint_nans.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/inpaint_nans.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/inpaint_nans.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/inpaint_nans.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/ivim_modeling_noise.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/ivim_modeling_noise.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/ivim_modeling_noise.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/ivim_modeling_noise.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/outputHNMPAResults.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/outputHNMPAResults.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/outputHNMPAResults.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/outputHNMPAResults.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/qualityFit.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/qualityFit.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/qualityFit.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/qualityFit.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.log b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.log old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.log rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.log diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/returnFeatures.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/write_param_txt.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/write_param_txt.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/write_param_txt.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/qa_fitting/write_param_txt.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/runQAMPERBatch.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/runQAMPERBatch.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/runQAMPERBatch.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/runQAMPERBatch.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/run_QAMPER_IVIM.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/run_QAMPER_IVIM.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/run_QAMPER_IVIM.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/run_QAMPER_IVIM.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/Dir2Arr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/Dir2Arr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/Dir2Arr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/Dir2Arr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/arr2map2.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/arr2map2.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/arr2map2.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/arr2map2.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/deb.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/deb.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/deb.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/deb.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/flipCheck.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/flipCheck.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/flipCheck.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/flipCheck.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/map2arr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/map2arr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/map2arr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/map2arr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/FAQ.pdf b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/FAQ.pdf old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/FAQ.pdf rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/FAQ.pdf diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/NIfTI_tools.pdf b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/NIfTI_tools.pdf old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/NIfTI_tools.pdf rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/NIfTI_tools.pdf diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/UseANALYZE.pdf b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/UseANALYZE.pdf old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/UseANALYZE.pdf rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/UseANALYZE.pdf diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/affine.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/affine.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/affine.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/affine.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bipolar.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bipolar.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bipolar.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bipolar.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bresenham_line3d.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bresenham_line3d.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bresenham_line3d.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/bresenham_line3d.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/clip_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/clip_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/clip_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/clip_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan2.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan2.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan2.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/collapse_nii_scan2.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/examples.txt b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/examples.txt old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/examples.txt rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/examples.txt diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/expand_nii_scan.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/expand_nii_scan.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/expand_nii_scan.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/expand_nii_scan.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/extra_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/extra_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/extra_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/extra_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/flip_lr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/flip_lr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/flip_lr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/flip_lr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/get_nii_frame.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/get_nii_frame.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/get_nii_frame.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/get_nii_frame.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/license.txt b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/license.txt old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/license.txt rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/license.txt diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_ext.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_ext.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_ext.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_ext.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_img.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_img.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_img.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_nii_img.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch0_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch0_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch0_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch0_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_header_only.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_header_only.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_header_only.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_header_only.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_img.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_img.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_img.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/load_untouch_nii_img.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_ana.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_ana.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_ana.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_ana.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/make_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/mat_into_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/mat_into_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/mat_into_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/mat_into_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/pad_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/pad_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/pad_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/pad_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/reslice_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/reslice_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/reslice_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/reslice_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_file_menu.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_file_menu.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_file_menu.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_file_menu.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient_ui.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient_ui.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient_ui.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_orient_ui.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_select_file.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_select_file.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_select_file.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_select_file.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_xhair.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_xhair.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_xhair.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_xhair.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_zoom_menu.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_zoom_menu.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_zoom_menu.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/rri_zoom_menu.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_ext.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_ext.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_ext.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_ext.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch0_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch0_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch0_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch0_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_header_only.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_header_only.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_header_only.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_header_only.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii_hdr.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii_hdr.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii_hdr.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_nii_hdr.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_slice.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_slice.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_slice.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/save_untouch_slice.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/unxform_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/unxform_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/unxform_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/unxform_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/verify_nii_ext.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/verify_nii_ext.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/verify_nii_ext.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/verify_nii_ext.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii_menu.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii_menu.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii_menu.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/view_nii_menu.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/xform_nii.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/xform_nii.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/xform_nii.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nifti_toolbox/xform_nii.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_load.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_load.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_load.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_load.m diff --git a/src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_save.m b/src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_save.m old mode 100755 new mode 100644 similarity index 100% rename from src/original/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_save.m rename to src/original/fitting/ASD_MemorialSloanKettering/MRI-QAMPER_IVIM/utils/nii_save.m diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/__init__.py b/src/original/fitting/ASD_MemorialSloanKettering/__init__.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/__init__.py rename to src/original/fitting/ASD_MemorialSloanKettering/__init__.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_loading/__init__.py b/src/original/fitting/DK_OGC_AmsterdamUMC/__init__.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_loading/__init__.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/__init__.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/__init__.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/__init__.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/__init__.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/__init__.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/__init__.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_loading/__init__.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/__init__.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_loading/__init__.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_loading/load_ivim_subject.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_loading/load_ivim_subject.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_loading/load_ivim_subject.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_loading/load_ivim_subject.py diff --git a/src/original/ETP_SRI/__init__.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/__init__.py similarity index 100% rename from src/original/ETP_SRI/__init__.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/__init__.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/AverageSignalsOfEqualXvals.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/AverageSignalsOfEqualXvals.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/AverageSignalsOfEqualXvals.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/AverageSignalsOfEqualXvals.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/FlattenImageData.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/FlattenImageData.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/FlattenImageData.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/FlattenImageData.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeMaxSignal.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeMaxSignal.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeMaxSignal.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeMaxSignal.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeSignals.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeSignals.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeSignals.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeSignals.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeXvals.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeXvals.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeXvals.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/NormalizeXvals.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalCuration.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalCuration.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalCuration.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalCuration.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalMask.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalMask.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalMask.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SignalMask.py diff --git a/src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SortSignalOnXval.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SortSignalOnXval.py similarity index 100% rename from src/original/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SortSignalOnXval.py rename to src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/SortSignalOnXval.py diff --git a/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/__init__.py b/src/original/fitting/DK_OGC_AmsterdamUMC/utils/data_processing/processors/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/DT_IIITN/__init__.py b/src/original/fitting/DT_IIITN/__init__.py similarity index 100% rename from src/original/DT_IIITN/__init__.py rename to src/original/fitting/DT_IIITN/__init__.py diff --git a/src/original/DT_IIITN/wls_ivim_fitting.py b/src/original/fitting/DT_IIITN/wls_ivim_fitting.py similarity index 100% rename from src/original/DT_IIITN/wls_ivim_fitting.py rename to src/original/fitting/DT_IIITN/wls_ivim_fitting.py diff --git a/src/original/ETP_SRI/LinearFitting.py b/src/original/fitting/ETP_SRI/LinearFitting.py similarity index 100% rename from src/original/ETP_SRI/LinearFitting.py rename to src/original/fitting/ETP_SRI/LinearFitting.py diff --git a/src/original/fitting/ETP_SRI/__init__.py b/src/original/fitting/ETP_SRI/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/fitting/IAR_LundUniversity/__init__.py b/src/original/fitting/IAR_LundUniversity/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_biexp.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_biexp.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_biexp.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_biexp.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_linear.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_linear.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_linear.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_linear.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_modified_mix.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_modified_mix.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_modified_mix.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_modified_mix.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_modified_topopro.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_modified_topopro.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_modified_topopro.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_modified_topopro.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_segmented_2step.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_segmented_2step.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_segmented_2step.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_segmented_2step.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_segmented_3step.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_segmented_3step.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_segmented_3step.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_segmented_3step.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_sivim.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_sivim.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_sivim.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_sivim.py diff --git a/src/original/IAR_LundUniversity/ivim_fit_method_subtracted.py b/src/original/fitting/IAR_LundUniversity/ivim_fit_method_subtracted.py similarity index 100% rename from src/original/IAR_LundUniversity/ivim_fit_method_subtracted.py rename to src/original/fitting/IAR_LundUniversity/ivim_fit_method_subtracted.py diff --git a/src/original/OGC_AUMC_IVIMNET/Example_1_simple_map.py b/src/original/fitting/OGC_AUMC_IVIMNET/Example_1_simple_map.py similarity index 100% rename from src/original/OGC_AUMC_IVIMNET/Example_1_simple_map.py rename to src/original/fitting/OGC_AUMC_IVIMNET/Example_1_simple_map.py diff --git a/src/original/OGC_AUMC_IVIMNET/Example_2_simulations.py b/src/original/fitting/OGC_AUMC_IVIMNET/Example_2_simulations.py similarity index 100% rename from src/original/OGC_AUMC_IVIMNET/Example_2_simulations.py rename to src/original/fitting/OGC_AUMC_IVIMNET/Example_2_simulations.py diff --git a/src/original/OGC_AUMC_IVIMNET/Example_3_volunteer.py b/src/original/fitting/OGC_AUMC_IVIMNET/Example_3_volunteer.py similarity index 100% rename from src/original/OGC_AUMC_IVIMNET/Example_3_volunteer.py rename to src/original/fitting/OGC_AUMC_IVIMNET/Example_3_volunteer.py diff --git a/src/original/fitting/OGC_AUMC_IVIMNET/__init__.py b/src/original/fitting/OGC_AUMC_IVIMNET/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/OGC_AUMC_IVIMNET/hyperparams.py b/src/original/fitting/OGC_AUMC_IVIMNET/hyperparams.py similarity index 100% rename from src/original/OGC_AUMC_IVIMNET/hyperparams.py rename to src/original/fitting/OGC_AUMC_IVIMNET/hyperparams.py diff --git a/src/original/OGC_AmsterdamUMC/LSQ_fitting.py b/src/original/fitting/OGC_AmsterdamUMC/LSQ_fitting.py similarity index 100% rename from src/original/OGC_AmsterdamUMC/LSQ_fitting.py rename to src/original/fitting/OGC_AmsterdamUMC/LSQ_fitting.py diff --git a/src/original/fitting/OGC_AmsterdamUMC/__init__.py b/src/original/fitting/OGC_AmsterdamUMC/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/OJ_GU/IVIM_bayes.m b/src/original/fitting/OJ_GU/IVIM_bayes.m similarity index 100% rename from src/original/OJ_GU/IVIM_bayes.m rename to src/original/fitting/OJ_GU/IVIM_bayes.m diff --git a/src/original/OJ_GU/IVIM_seg.m b/src/original/fitting/OJ_GU/IVIM_seg.m similarity index 100% rename from src/original/OJ_GU/IVIM_seg.m rename to src/original/fitting/OJ_GU/IVIM_seg.m diff --git a/src/original/fitting/OJ_GU/__init__.py b/src/original/fitting/OJ_GU/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/OJ_GU/info.json b/src/original/fitting/OJ_GU/info.json similarity index 100% rename from src/original/OJ_GU/info.json rename to src/original/fitting/OJ_GU/info.json diff --git a/src/original/OJ_GU/ivim_seg.py b/src/original/fitting/OJ_GU/ivim_seg.py similarity index 100% rename from src/original/OJ_GU/ivim_seg.py rename to src/original/fitting/OJ_GU/ivim_seg.py diff --git a/src/original/fitting/PV_MUMC/__init__.py b/src/original/fitting/PV_MUMC/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/PV_MUMC/triexp_fitting_algorithms.py b/src/original/fitting/PV_MUMC/triexp_fitting_algorithms.py similarity index 100% rename from src/original/PV_MUMC/triexp_fitting_algorithms.py rename to src/original/fitting/PV_MUMC/triexp_fitting_algorithms.py diff --git a/src/original/PV_MUMC/two_step_IVIM_fit.py b/src/original/fitting/PV_MUMC/two_step_IVIM_fit.py similarity index 100% rename from src/original/PV_MUMC/two_step_IVIM_fit.py rename to src/original/fitting/PV_MUMC/two_step_IVIM_fit.py diff --git a/src/original/PvH_KB_NKI/DWI_Examples.py b/src/original/fitting/PvH_KB_NKI/DWI_Examples.py similarity index 100% rename from src/original/PvH_KB_NKI/DWI_Examples.py rename to src/original/fitting/PvH_KB_NKI/DWI_Examples.py diff --git a/src/original/PvH_KB_NKI/DWI_functions_standalone.py b/src/original/fitting/PvH_KB_NKI/DWI_functions_standalone.py similarity index 100% rename from src/original/PvH_KB_NKI/DWI_functions_standalone.py rename to src/original/fitting/PvH_KB_NKI/DWI_functions_standalone.py diff --git a/src/original/fitting/PvH_KB_NKI/__init__.py b/src/original/fitting/PvH_KB_NKI/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/TCML_TechnionIIT/SUPER-IVIM-DC/README.md b/src/original/fitting/TCML_TechnionIIT/SUPER-IVIM-DC/README.md similarity index 100% rename from src/original/TCML_TechnionIIT/SUPER-IVIM-DC/README.md rename to src/original/fitting/TCML_TechnionIIT/SUPER-IVIM-DC/README.md diff --git a/src/original/TCML_TechnionIIT/SUPER-IVIM-DC/sample.ipynb b/src/original/fitting/TCML_TechnionIIT/SUPER-IVIM-DC/sample.ipynb similarity index 100% rename from src/original/TCML_TechnionIIT/SUPER-IVIM-DC/sample.ipynb rename to src/original/fitting/TCML_TechnionIIT/SUPER-IVIM-DC/sample.ipynb diff --git a/src/original/fitting/TCML_TechnionIIT/__init__.py b/src/original/fitting/TCML_TechnionIIT/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/fitting/TF_reference/__init__.py b/src/original/fitting/TF_reference/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/TF_reference/segmented_IVIMfit.py b/src/original/fitting/TF_reference/segmented_IVIMfit.py similarity index 100% rename from src/original/TF_reference/segmented_IVIMfit.py rename to src/original/fitting/TF_reference/segmented_IVIMfit.py diff --git a/src/original/fitting/__init__.py b/src/original/fitting/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/preprocessing/EP_GU/__init__.py b/src/original/preprocessing/EP_GU/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/preprocessing/EP_GU/brain_pipeline.py b/src/original/preprocessing/EP_GU/brain_pipeline.py new file mode 100644 index 00000000..3fd68987 --- /dev/null +++ b/src/original/preprocessing/EP_GU/brain_pipeline.py @@ -0,0 +1,184 @@ +''' +Preprocessing of brain IVIM data +Requirements: +- ivim +- fsl +- freesurfer +- itk +- itk-elastix +''' +#%% +import numpy as np +import nibabel as nib +import subprocess, os +from nipype.interfaces import fsl +import itk +from ivim.io.base import read_bval, write_bval +from ivim.preproc.base import extract, combine, average +from ivim.preproc import signal_drift + + +def denoise_wrap(im_file): + ''' Denoising ''' + im_file_denoised = im_file.replace('.nii.gz','-pca.nii.gz') + noise_level = im_file.replace('.nii.gz','-noise_level.nii.gz') + print('Denoising...') + subprocess.run(['dwidenoise', '-noise', noise_level, im_file, im_file_denoised]) + subprocess.run(['cp',im_file.replace('.nii.gz','.bval'),im_file_denoised.replace('.nii.gz','.bval')]) + subprocess.run(['cp',im_file.replace('.nii.gz','.bvec'),im_file_denoised.replace('.nii.gz','.bvec')]) + return im_file_denoised + +def degibbs_wrap(im_file): + ''' Gibbs ringing artifact removal ''' + im_file_degibbs = im_file.replace('.nii.gz','-gib.nii.gz') + print('Degibbsing...') + subprocess.run(['mrdegibbs', im_file, im_file_degibbs]) + subprocess.run(['cp',im_file.replace('.nii.gz','.bval'),im_file_degibbs.replace('.nii.gz','.bval')]) + subprocess.run(['cp',im_file.replace('.nii.gz','.bvec'),im_file_degibbs.replace('.nii.gz','.bvec')]) + return im_file_degibbs + +def extract_volume(in_file, t_index): + ''' + Extracts a 3D volume at time index t_index from a 4D image. + Returns the path to the temporary file. + ''' + out_file = in_file.replace('.nii.gz',f'-tmp{t_index}.nii.gz') + subprocess.run(['fslroi',in_file,out_file,str(t_index),'1']) + return out_file + +def register_3D_to_ref(in_file, ref_idx, out_file,method='rigid'): + ''' + Registers a 3D image to a reference image using ITK Elastix. + ''' + PixelType = itk.F + Dimension3D = 3 + Image3DType = itk.Image[PixelType, Dimension3D] + + # Built-in default parameter map seems to work well for brain + parameter_object = itk.ParameterObject.New() + parameter_object.AddParameterMap(parameter_object.GetDefaultParameterMap(method)) + + # Load reference image + tmp_ref = extract_volume(in_file, ref_idx) + ref_itk = itk.imread(tmp_ref, pixel_type=PixelType) + + # Loop through all volumes and register to reference + n_vols = nib.load(in_file).shape[3] + registered_vols = [] + for t in range(n_vols): + if t == ref_idx: + registered_vols.append(tmp_ref) # No need to register reference to itself + continue + + # Load moving image + tmp_moving = extract_volume(in_file, t) + moving_itk = itk.imread(tmp_moving, pixel_type=PixelType) + + print(f'Registering volume {t} to reference volume {ref_idx}...') + elastix = itk.ElastixRegistrationMethod.New(ref_itk, moving_itk) + # elastix.SetFixedImage(ref_itk) + # elastix.SetMovingImage(moving_itk) + elastix.SetParameterObject(parameter_object) + elastix.Update() + result = elastix.GetOutput() + tmp_out = out_file.replace('.nii.gz',f'-tmp{t}.nii.gz') + itk.imwrite(result, tmp_out) + os.remove(tmp_moving) # Clean up temp moving image + registered_vols.append(tmp_out) + + out_file = in_file.replace('.nii.gz','-rigid.nii.gz') + # Stack back to 4D + subprocess.run(['fslmerge','-t',out_file]+registered_vols) + + # Clean up + os.remove(tmp_ref) # Clean up temp reference image + for t in range(1,n_vols): + os.remove(out_file.replace('-rigid.nii.gz',f'-reg-tmp{t}.nii.gz')) # Clean up temp registered images + return out_file + +def topup_wrap(im_file,bval_file, b0rev_file, b0rev_bval_file): + ''' Susceptibility distortion correction ''' + print('Running topup...') + im_file_unwarp = im_file.replace('.nii.gz','-unwarp.nii.gz') + + # Prepare b0:s for topup + extract(im_file=im_file, bval_file=bval_file, outbase=im_file.replace('.nii.gz','-b0'),b_ex=0) # we dont perform averaging since it seems preferable to not do it + combine(dwi_files=[im_file.replace('.nii.gz','-b0.nii.gz'),b0rev_file], + bval_files=[im_file.replace('.nii.gz','-b0.bval'),b0rev_bval_file], + outbase=im_file.replace('.nii.gz','-b0-b0rev')) + b = read_bval(im_file.replace('.nii.gz','-b0.bval')) + brev = read_bval(b0rev_bval_file) + interbase = im_file.replace('.nii.gz','-b0-b0rev') + acqp_file = interbase + '_acqparams.txt' + with open(acqp_file,'w') as f: + for _ in range(np.sum(b==0)): + f.write('0 1 0 0.050\n') + for _ in range(np.sum(brev==0)): + f.write('0 -1 0 0.050\n') + + topup_cmd = f'topup --imain={im_file.replace(".nii.gz","-b0-b0rev.nii.gz")} --datain={acqp_file} --config=b02b0.cnf --subsamp=1 --out={interbase} --verbose' + os.system(topup_cmd) + + applytopup_cmd = f'applytopup --imain={im_file} --datain={acqp_file} --inindex=1 --topup={interbase} --out={im_file_unwarp} --method=jac --verbose' + os.system(applytopup_cmd) + subprocess.run(['cp',im_file.replace('.nii.gz','.bval'),im_file_unwarp.replace('.nii.gz','.bval')]) + + return im_file_unwarp + +def brain_preproc(im_file: str, bval_file: str, b0rev_file: str, b0rev_bval_file: str, temp_folder: str): + + # Denoising + im_file_denoised = denoise_wrap(im_file) + + # Degibbsing + im_file_degibbs = degibbs_wrap(im_file_denoised) + + # Registration to b0 + im_file_reg = register_3D_to_ref(im_file_degibbs, ref_idx=0, out_file=im_file_degibbs.replace('.nii.gz','-reg.nii.gz')) + + # Suseptibility distortion correction + im_file_unwarp = topup_wrap(im_file_reg, bval_file, b0rev_file, b0rev_bval_file) + + # Brain extraction + brain_mask = im_file_unwarp.replace('.nii.gz','-brain-mask.nii.gz') + extract(im_file_unwarp, im_file_unwarp.replace('.nii.gz','.bval'), outbase=im_file_unwarp.replace('.nii.gz','-b0'), b_ex=0) + average(im_file_unwarp.replace('.nii.gz','-b0.nii.gz'), im_file_unwarp.replace('.nii.gz','-b0.bval'), im_file_unwarp.replace('.nii.gz','-b0-avr')) + subprocess.run(['mri_synthstrip', '-i', im_file_unwarp.replace('.nii.gz','-b0-avr.nii.gz'), '-o', im_file_unwarp.replace('.nii.gz', '-brain.nii.gz'), '-m', im_file_unwarp.replace('.nii.gz', '-brain-mask.nii.gz')]) + os.remove(im_file_unwarp.replace('.nii.gz','-b0.nii.gz')) + os.remove(im_file_unwarp.replace('.nii.gz','-b0.bval')) + os.remove(im_file_unwarp.replace('.nii.gz','-b0-avr.nii.gz')) + + # Signal drift correction + signal_drift.spatiotemporal(im_file = im_file_unwarp, + bval_file = im_file_unwarp.replace('.nii.gz','.bval'), + outbase = im_file_unwarp.replace('.nii.gz','-sigdri'), + roi_file = brain_mask) + subprocess.run(['cp',im_file_unwarp.replace('.nii.gz','.bval'),im_file_unwarp.replace('.nii.gz','-sigdri_corr.bval')]) +#%% +# im_file = os.getcwd()+'/temp/diffusive_snr200.nii.gz' +# bval_file = os.getcwd()+'/temp/diffusive_snr200.bval' +# b0rev_file = os.getcwd()+'/temp/diffusive_snr200_b0.nii.gz' +# b0rev_bval_file = os.getcwd()+'/temp/diffusive_snr200_b0.bval' + +# im_file_denoised = denoise_wrap(im_file) +# im_file_degibbs = degibbs_wrap(im_file_denoised) +# im_file_reg = register_3D_to_ref(im_file_degibbs, ref_idx=0, out_file=im_file_degibbs.replace('.nii.gz','-reg.nii.gz')) +# im_file_unwarp = topup_wrap(im_file_reg, bval_file, b0rev_file, b0rev_bval_file) + +# Brain extraction +# brain_mask = im_file_unwarp.replace('.nii.gz','-brain-mask.nii.gz') +# extract(im_file_unwarp, bval_file, outbase=im_file_unwarp.replace('.nii.gz','-b0'), b_ex=0) +# average(im_file_unwarp.replace('.nii.gz','-b0.nii.gz'), im_file_unwarp.replace('.nii.gz','-b0.bval'), im_file_unwarp.replace('.nii.gz','-b0-avr')) +# subprocess.run(['mri_synthstrip', '-i', im_file_unwarp.replace('.nii.gz','-b0-avr.nii.gz'), '-o', im_file_unwarp.replace('.nii.gz', '-brain.nii.gz'), '-m', im_file_unwarp.replace('.nii.gz', '-brain-mask.nii.gz')]) +# os.remove(im_file_unwarp.replace('.nii.gz','-b0.nii.gz')) +# os.remove(im_file_unwarp.replace('.nii.gz','-b0.bval')) +# os.remove(im_file_unwarp.replace('.nii.gz','-b0-avr.nii.gz')) + +# # Signal drift correction +# signal_drift.spatiotemporal(im_file = im_file_unwarp, +# bval_file = bval_file, +# outbase = im_file_unwarp.replace('.nii.gz','-sigdri'), +# roi_file = brain_mask) +# subprocess.run(['cp',im_file_unwarp.replace('.nii.gz','.bval'),im_file_unwarp.replace('.nii.gz','-sigdri_corr.bval')]) + +# %% diff --git a/src/original/preprocessing/EP_GU/info.json b/src/original/preprocessing/EP_GU/info.json new file mode 100644 index 00000000..3e937823 --- /dev/null +++ b/src/original/preprocessing/EP_GU/info.json @@ -0,0 +1,4 @@ +{ + "developers": "Oscar Jalnefjord", + "institutions": ["University of Gothenburg, Gothenburg, Sweden", "Sahlgrenska University Hospital, Gothenburg, Sweden"] +} \ No newline at end of file diff --git a/src/original/preprocessing/EP_GU/outlier_removal.py b/src/original/preprocessing/EP_GU/outlier_removal.py new file mode 100644 index 00000000..6ee7c108 --- /dev/null +++ b/src/original/preprocessing/EP_GU/outlier_removal.py @@ -0,0 +1,165 @@ +""" Methods for outlier removal. +Reproduced with permission from Oscar Jalngefjord: https://github.com/oscarjalnefjord/ivim/tree/outlier by Elina Petersson +""" + +import numpy as np +import nibabel as nib +import numpy.typing as npt +import matplotlib.pyplot as plt +from scipy.optimize import minimize +from scipy.stats import norm + +NO_REGIME = 'no' +DIFFUSIVE_REGIME = 'diffusive' +BALLISTIC_REGIME = 'ballistic' +Db = 1.75e-3 # mm2/s, see Ahlgren et al 2016 NMR in Biomedicine + +def roi_based(im_file: str, bval_file: str, roi_file: str, outbase: str, regime:str , fig: bool = False, cval_file: str | None = None): + """ + Identify outliers by fit to ROI average. + + Arguments: + im_file: path to nifti image file + bval_file: path to .bval file + roi_file: path to nifti file defining a region-of-interest (ROI) in which the correction is calculated and applied + outbase: basis for output filenames, i.e. filename without file extension to which .nii.gz, .bval, etc. is added + regime: IVIM regime to model: no (= sIVIM), diffusive (long encoding time) or ballistic (short encoding time) + fig: (optional) if True, a diagnostic figure is output + cval_file: (optional) path to .cval file + """ + + check_regime(regime) + Y = nib.load(im_file).get_fdata() + if roi_file is not None: + roi = nib.load(roi_file).get_fdata().astype(bool) + else: + roi = np.full(Y.shape[:-1], True) + Y = Y[roi,:] + b = np.atleast_1d(np.loadtxt(bval_file)) + if regime == BALLISTIC_REGIME: + c = np.atleast_1d(np.loadtxt(cval_file)) + + y_avg = np.median(Y, axis=0) + + if regime == NO_REGIME: + def model(x, idx): + return sIVIM(b[idx], x[0], x[1], x[2]) + x0 = [1e-3, 0.1, np.max(y_avg)] + bounds = ((0, 3e-3), (0, 1), (0, 2*np.max(y_avg))) + elif regime == BALLISTIC_REGIME: + def model(x, idx): + return ballistic(b[idx], c[idx], x[0], x[1], x[2], x[3]) + x0 = [1e-3, 0.1, 2, np.max(y_avg)] + bounds = ((0, 3e-3), (0, 1), (0, 5), (0, 2*np.max(y_avg))) + else: # diffusive + def model(x, idx): + return diffusive(b[idx], x[0], x[1], x[2], x[3]) + x0 = [1e-3, 0.1, 10e-3, np.max(y_avg)] + bounds = ((0, 3e-3), (0, 1), (0, 1), (0, 2*np.max(y_avg))) + + + has_outliers = True + idx = np.full_like(b, True, dtype=bool) + while has_outliers: + def fun(x): + return np.sum(np.abs(model(x, idx)-y_avg[idx])) + + x = minimize(fun, x0, bounds=bounds).x + res = np.squeeze(model(x, idx)) - y_avg[idx] + iqr = (np.quantile(res, 0.75) - np.quantile(res, 0.25)) + tmp = np.full_like(b, False, dtype=bool) + tmp[idx] = np.abs(res) < 3*iqr + if np.all(tmp == idx): + has_outliers = False + else: + idx = tmp + + if fig: + fig, ax = plt.subplots(1, 1) + b_plot = np.linspace(np.min(b), np.max(b)) + if regime == NO_REGIME: + y = np.squeeze(sIVIM(b_plot, x[0], x[1], x[2])) + + elif regime == BALLISTIC_REGIME: + c_plot = b_plot * (c/b)[c>0][np.argmax(b[c>0])] + y = np.squeeze(ballistic(b_plot, c_plot, x[0], x[1], x[2], x[3])) + if np.any((b>0)&(c==0)): + ax.plot(b_plot, np.squeeze(ballistic(b_plot, np.zeros_like(b_plot), x[0], x[1], x[2], x[3]))) + else: + y = np.squeeze(diffusive(b_plot, x[0], x[1], x[2], x[3])) + ax.plot(b_plot, y) + ax.plot(b, y_avg, 'ko') + ax.plot(b[~idx], y_avg[~idx], 'rx') + ax.set_xlabel(r'b [s/mm$^2$]') + ax.set_ylabel('Signal [a.u]') + fig.savefig(outbase+'.png') + plt.close(fig) + + sz = roi.shape + + if Y[:,idx].ndim > 1: + im_new = np.full(list(sz) + [Y[:,idx].shape[1]], np.nan) + im_new[roi, :] = Y[:,idx] + else: + im_new = np.full(sz, np.nan) + im_new[roi] = Y[:,idx] + nib.save(nib.Nifti1Image(im_new, nib.load(im_file).affine, nib.load(im_file).header), outbase+'.nii.gz') + np.savetxt(outbase+'.bval', b[idx], fmt='%.1f', newline=' ') + if regime == BALLISTIC_REGIME: + np.savetxt(outbase+'.cval', c[idx], fmt='%.1f', newline=' ') + + + +def at_least_1d(pars: list) -> list: + """ Check that each parameter is atleast one dimension in shape. """ + for i, par in enumerate(pars): + pars[i] = np.atleast_1d(par) + return pars + +def check_regime(regime: str) -> None: + """ Check that the regime is valid. """ + if regime not in [NO_REGIME, DIFFUSIVE_REGIME, BALLISTIC_REGIME]: + raise ValueError(f'Invalid regime "{regime}". Valid regimes are "{NO_REGIME}", "{DIFFUSIVE_REGIME}" and "{BALLISTIC_REGIME}".') + +def monoexp(b: npt.NDArray[np.float64], D: npt.NDArray[np.float64]) -> npt.NDArray[np.float64]: + """ + Return the monoexponential e^(-b*D). + """ + + [b, D] = at_least_1d([b, D]) + S = np.exp(-np.outer(D, b)) + return np.reshape(S, list(D.shape) + [b.size]) # reshape as np.outer flattens D is ndim > 1 + +def kurtosis(b: npt.NDArray[np.float64], D: npt.NDArray[np.float64], K: npt.NDArray[np.float64]) -> npt.NDArray[np.float64]: + """ + Return the kurtosis signal representation. + """ + + [b, D, K] = at_least_1d([b, D, K]) + Slin = monoexp(b, D) + Squad = np.exp(np.reshape(np.outer(D, b)**2, list(D.shape) + [b.size]) * K[..., np.newaxis]/6) + return Slin * Squad + +def sIVIM(b: npt.NDArray[np.float64], D: npt.NDArray[np.float64], f: npt.NDArray[np.float64], S0: npt.NDArray[np.float64] = 1, K: npt.NDArray[np.float64] = 0) -> npt.NDArray[np.float64]: + """ + Return MR signal based on the simplified IVIM (sIVIM) model. + """ + + [b, D, f, S0] = at_least_1d([b, D, f, S0]) + return S0[..., np.newaxis] * ((1-f[..., np.newaxis]) * kurtosis(b, D, K) + np.reshape(np.outer(f, b==0), list(f.shape) + [b.size])) + +def ballistic(b: npt.NDArray[np.float64], c: npt.NDArray[np.float64], D: npt.NDArray[np.float64], f: npt.NDArray[np.float64], vd: npt.NDArray[np.float64], S0: npt.NDArray[np.float64] = 1, K: npt.NDArray[np.float64] = 0) -> npt.NDArray[np.float64]: + """ + Return MR signal based on the ballistic IVIM model. + """ + + [b, c, D, f, vd, S0] = at_least_1d([b, c, D, f, vd, S0]) + return S0[..., np.newaxis] * ((1-f[..., np.newaxis])*kurtosis(b, D, K) + f[..., np.newaxis]*monoexp(b, Db)*monoexp(c**2, vd**2)) + +def diffusive(b: npt.NDArray[np.float64], D: npt.NDArray[np.float64], f: npt.NDArray[np.float64], Dstar: npt.NDArray[np.float64], S0: npt.NDArray[np.float64] = 1, K: npt.NDArray[np.float64] = 0) -> npt.NDArray[np.float64]: + """ + Return MR signal based on the diffusive IVIM model. + """ + + [b, D, f, Dstar, S0] = at_least_1d([b, D, f, Dstar, S0]) + return S0[..., np.newaxis] * ((1-f[..., np.newaxis])*kurtosis(b, D, K) + f[..., np.newaxis]*monoexp(b, Dstar)) \ No newline at end of file diff --git a/src/original/preprocessing/MG_LU/TOPED_fsl_commands.py b/src/original/preprocessing/MG_LU/TOPED_fsl_commands.py new file mode 100644 index 00000000..28a330fe --- /dev/null +++ b/src/original/preprocessing/MG_LU/TOPED_fsl_commands.py @@ -0,0 +1,308 @@ +import os +import re +import shutil +import subprocess +from typing import Optional, Tuple + + +class TOPED: + def __init__(self, distribution: str, user: str, linux_workdir: str): + """ Specify WSL distribution, user, and working directory for FSL. + Parameters: + distribution : str The WSL distribution where FSL is installed (e.g., "Ubuntu"). + user : str The Linux username to run commands as. + linux_workdir : str The directory in the Linux filesystem to use for temporary files. + """ + + if not os.path.exists(linux_workdir): + #raise ValueError(f"Linux working directory not found: {linux_workdir}") + print(f"Linux working directory not found, creating: {linux_workdir}") + os.makedirs(linux_workdir) + + self.distribution = distribution + self.user = user + self.linux_workdir = linux_workdir + + # CORE COMMAND FUNCTION + def run_command(self, command: str, workdir: str): + """ Run a generic FSL command through WSL. + Parameters: + command : str The FSL command to execute. + workdir : str The working directory in the Linux filesystem where the command should be executed. + """ + # print the full command in the IDE output when running the fsl_runner. + print(f" command: {command}") + + full_cmd = f"source ~/.profile; source ~/.bashrc; {command}" + return subprocess.run( + ['wsl', '-d', self.distribution, '-u', self.user, '-e', 'bash', '-c', full_cmd], + cwd=workdir, + check=True, + capture_output=True, + text=True + ) + + # TOPUP + def run_topup( + self, + b0_path: str, + acq_parameter_path: str, + config_file_path: Optional[str] = None, + nthr: Optional[int] = None, + logout: Optional[str] = None, + dfout: Optional[str] = None, + jacout: Optional[str] = None, + patient_id: Optional[str] = None, + output_dir: Optional[str] = None + ) -> str: + """ Run FSL TOPUP on a stack of b0 images. + Parameters: + b0_path : str The path to the b0 image to process with TOPUP. + acq_parameter_path : str Path to the acquisition parameters file. + config_file_path : str, optional Path to the TOPUP configuration file, by default None, which uses the default FSL config b02b0.cnf. + nthr : int, optional Number of threads to use, by default None (uses default_threads) + Returns: + whatever specified in the TOPUP command output (dfout, iout, jacout) + Corrected image, fieldmap, and Jacobian determinant paths are generated in the Linux working directory. + """ + workdir = self.get_patient_workdir(patient_id) + + if not os.path.exists(b0_path): + raise ValueError("b0_path invalid") + if not os.path.exists(acq_parameter_path): + raise ValueError("acq_parameter_path invalid") + + output_dir = output_dir or os.path.dirname(b0_path) + + # Copy inputs + b0_name = self.copy_to_wsl(b0_path, workdir) + b0_basename, _ = self.split_nifti_gz(b0_name) + + acqparam = self.copy_to_wsl(acq_parameter_path, workdir) + if config_file_path: + config_filename = self.copy_to_wsl(config_file_path, workdir) + config_arg = f"--config={config_filename} " + else: + # FSL default config + config_arg = "--config=b02b0.cnf " + + # Build command + cmd = ( + f"topup " + f"--imain={b0_name} " + f"--datain={acqparam} " + f"--out={b0_basename} " + f"--iout={self.get_corrected_name(b0_basename)} " + ) + + if logout is not None: cmd += f"--logout={self.get_log_name(b0_basename)} " + if dfout is not None: cmd += f"--dfout={self.get_warpfig_name(b0_basename)} " + if jacout is not None: cmd += f"--jacout={self.get_jacobian_name(b0_basename)} " + if nthr is not None: cmd += f"--nthr={nthr} " + cmd += config_arg + + # Run + self.run_command(cmd, workdir) + + # Copy corrected image back + self.ensure_dir(output_dir) + corrected_filename = self.get_corrected_name(b0_basename, ext=True) + self.copy_from_wsl(corrected_filename, output_dir, workdir) + + # Return topup base for Eddy + return b0_basename + + # Eddy + def run_eddy( + self, + dwi_path: str, + mask_path: str, + acq_parameter_path: str, + index_path: str, + bvecs_path: str, + bvals_path: str, + topup_base: str, + slspec_path: Optional[str] = None, + b_range: Optional[int] = None, + flm: Optional[str] = None, + slm: Optional[str] = None, + niter: Optional[int] = None, + fwhm: Optional[str] = None, + resamp: Optional[str] = None, + fep: Optional[bool] = None, + repol: Optional[bool] = None, + estimate_move_by_susceptibility: Optional[bool] = None, + mporder: Optional[int] = None, + patient_id: Optional[str] = None, + output_dir: Optional[str] = None, + json_path: Optional[str] = None, + interp: Optional[str] = None, + nvoxhp: Optional[int] = None, + ff: Optional[float] = None, + dont_sep_offs_move: Optional[bool] = None, + dont_peas: Optional[bool] = None, + ol_nstd: Optional[float] = None, + ol_nvox: Optional[int] = None, + ol_type: Optional[str] = None, + ol_ss: Optional[str] = None, + ol_pos: Optional[bool] = None, + ol_sqr: Optional[bool] = None, + s2v_niter: Optional[int] = None, + s2v_lambda: Optional[float] = None, + s2v_interp: Optional[str] = None, + mbs_niter: Optional[int] = None, + mbs_lambda: Optional[float] = None, + mbs_ksp: Optional[float] = None, + cnr_maps: Optional[bool] = None, + residuals: Optional[bool] = None, + data_is_shelled: Optional[bool] = None, + nthr: Optional[int] = None + ) -> str: + + """ Run FSL Eddy. + Parameters: + dwi_path : str Path to the input DWI image. This is the stack to be corrected by Eddy & TOPUP. + mask_path : str Path to the mask image. + acqparams_path : str Path to acquisition parameters file + index_path : str Path to index file + bvecs_path : str Path to bvecs file + bvals_path : str Path to bvals file + topup_base : str Base name used for topup output. is is automatically set by TOUP in the linux working directory and is used as input for Eddy. + output_dir : str Output directory + bunch of optional Eddy flags (set to None to use FSL defaults). + Returns: + (Eddy + TOPUP) Corrected DWI image (path to output image) + """ + + workdir = self.get_patient_workdir(patient_id) + + for p in [dwi_path, mask_path, acq_parameter_path, index_path, bvecs_path, bvals_path]: + if not os.path.exists(p): + raise ValueError(f"Missing compulsory file: {p}") + + output_dir = output_dir or os.path.dirname(dwi_path) + + # Copy inputs + dwi_name = self.copy_to_wsl(dwi_path, workdir) + dwi_basename, _ = self.split_nifti_gz(dwi_name) + + mask = self.copy_to_wsl(mask_path, workdir) + acqp = self.copy_to_wsl(acq_parameter_path, workdir) + index = self.copy_to_wsl(index_path, workdir) + bvecs = self.copy_to_wsl(bvecs_path, workdir) + bvals = self.copy_to_wsl(bvals_path, workdir) + + slspec = self.copy_to_wsl(slspec_path, workdir) if slspec_path else None + json_file = self.copy_to_wsl(json_path, workdir) if json_path else None + + # Build command + cmd = ( + f"eddy " + f"--imain={dwi_name} " + f"--mask={mask} " + f"--acqp={acqp} " + f"--index={index} " + f"--bvecs={bvecs} " + f"--bvals={bvals} " + f"--topup={topup_base} " + f"--out={self.get_corrected_name_eddy(dwi_basename)} " + ) + + # Optional params + if slspec: cmd += f"--slspec={slspec} " + if json_file: cmd += f"--json={json_file} " + if b_range is not None: cmd += f"--b_range={b_range} " + + if flm is not None: cmd += f"--flm={flm} " + if slm is not None: cmd += f"--slm={slm} " + if fwhm is not None: cmd += f"--fwhm={fwhm} " + if niter is not None: cmd += f"--niter={niter} " + if interp is not None: cmd += f"--interp={interp} " + if resamp is not None: cmd += f"--resamp={resamp} " + if fep: cmd += f"--fep " + if nvoxhp is not None: cmd += f"--nvoxhp={nvoxhp} " + if ff is not None: cmd += f"--ff={ff} " + if dont_sep_offs_move: cmd += f"--dont_sep_offs_move " + if dont_peas: cmd += f"--dont_peas " + + if repol: cmd += f"--repol " + if ol_nstd is not None: cmd += f"--ol_nstd={ol_nstd} " + if ol_nvox is not None: cmd += f"--ol_nvox={ol_nvox} " + if ol_type is not None: cmd += f"--ol_type={ol_type} " + if ol_ss is not None: cmd += f"--ol_ss={ol_ss} " + if ol_pos: cmd += f"--ol_pos " + if ol_sqr: cmd += f"--ol_sqr " + + if mporder is not None: cmd += f"--mporder={mporder} " + if s2v_niter is not None: cmd += f"--s2v_niter={s2v_niter} " + if s2v_lambda is not None: cmd += f"--s2v_lambda={s2v_lambda} " + if s2v_interp is not None: cmd += f"--s2v_interp={s2v_interp} " + + if estimate_move_by_susceptibility: cmd += f"--estimate_move_by_susceptibility " + if mbs_niter is not None: cmd += f"--mbs_niter={mbs_niter} " + if mbs_lambda is not None: cmd += f"--mbs_lambda={mbs_lambda} " + if mbs_ksp is not None: cmd += f"--mbs_ksp={mbs_ksp} " + + if cnr_maps: cmd += f"--cnr_maps " + if residuals: cmd += f"--residuals " + if data_is_shelled: cmd += f"--data_is_shelled " + if nthr is not None: cmd += f"--nthr={nthr} " + + + # Run + self.run_command(cmd, workdir) + + # Copy output back + self.ensure_dir(output_dir) + output_filename = self.get_corrected_name_eddy(dwi_basename, ext=True) + self.copy_from_wsl(output_filename, output_dir, workdir) + + return os.path.join(output_dir, output_filename) + + + # FILE HANDLING between windows and wsl + def copy_to_wsl(self, path: str, workdir: str) -> str: + filename = os.path.basename(path) + dst = os.path.join(workdir, filename) + shutil.copy(path, dst) + return filename + + def copy_from_wsl(self, filename: str, output_dir: str, workdir: str): + src = os.path.join(workdir, filename) + dst = os.path.join(output_dir, filename) + if not os.path.exists(src): + raise FileNotFoundError(f"Expected output not found: {src}") + shutil.copy(src, dst) + + + # HELPERS - filenames and folders etc. + def split_nifti_gz(self, filename: str) -> Tuple[str, str]: + match = re.match(r"^(.*)(\.nii\.gz)$", filename) + return match.group(1), match.group(2) if match else os.path.splitext(filename) + + def get_warpfig_name(self, base: str): + return f"{base}_warpfig" + + def get_jacobian_name(self, base: str): + return f"{base}_jacobian" + + def get_log_name(self, base: str): + return f"{base}_log" + + def get_corrected_name(self, base: str, ext=False): + return f"{base}_corrected.nii.gz" if ext else f"{base}_corrected" + + def get_corrected_name_eddy(self, base: str, ext=False): + return f"{base}_EddyCorrected.nii.gz" if ext else f"{base}_EddyCorrected" + + def ensure_dir(self, path: str): + if not os.path.exists(path): + os.makedirs(path) + + def get_patient_workdir(self, patient_id: Optional[str]) -> str: + if not patient_id: + return self.linux_workdir + path = os.path.join(self.linux_workdir, patient_id) + if not os.path.exists(path): + os.makedirs(path) + return path \ No newline at end of file diff --git a/src/original/preprocessing/MG_LU/TOPED_fsl_runner.py b/src/original/preprocessing/MG_LU/TOPED_fsl_runner.py new file mode 100644 index 00000000..80100f86 --- /dev/null +++ b/src/original/preprocessing/MG_LU/TOPED_fsl_runner.py @@ -0,0 +1,375 @@ +import os +from typing import Optional +from TOPED_fsl_commands import TOPED # script containing subprocess commands + +""" +About this script: +The script is run in Windows and expects files located in windows directories. + +This script runs all linux commands as a subprocess using the TOPED class in TOPED_fsl_commands.py. + The input data is read from your specified windows directory 'main_dir' and the final output is saved in the same directory. + All processing is done in a specified linux working directory. All files for each patient are saved there and then copied back to the respective folders in the windows directory. +To run the script you will need to specify the parameters in the configuration section below. +Input files for topup and and eddy are identified through keywords specified in the IDENTIFIERS dictionary. + for each input type (e.g. b0, dwi stack, mask, acqp, bvecs, bvals, index), specify a keyword that is contained in the respective file names in your dataset. + This should be unique, i.e. if the keyword for the topup imain input is "b0", the script looks for files containing "b0" in the name and takes that as input. If there are multiple files containing "b0", an error is raised. + The assumed directory strucure is seen below. The script looks for the input files in the 'patient' folders first, then in the common folder if not found in the patient folder. + The structure of the main directory will be copied into the Linux working directory (i.e. the same folders and files will be generated). + +Requirements: +- Python packages (os, re, typing, subprocess, shutil) +- FSL installed with an WSL distro. user needs to be configured. Make sure FSL can be run from the command line in WSL. + + +Supported file inputs: + Topup: + - b0 image (4D file containing multiple b0 volumes). nii.gz (compulsory) + - acqparams.txt (PE directions) (compulsory) + - configuration file (if not specified the default FSL config b02b0.cnf is used) .cnf (optional) + Eddy: + - dwi image (4D stack contaning whatever should be topup+eddy corrected). nii.gz (compulsory) + - mask (typically brain mask, but i dont do brain so its whatever i guess). nii.gz (compulsory) + - acqparams (assumed to be the same as for topup). (compulsory) + - index (to match the dwi stack volumes to the acqparams lines). (compulsory) + - bvecs (as generated by e.g. dcm2niix). make sure they match the full stack. (compulsory) + - bvals (as generated by e.g. dcm2niix). make sure they match the full stack. (compulsory) + - slspec (optional). + - JSON (optional) +""" + +# main_directory +# ├── patient_1 +# │ ├── pt1_b0.nii.gz +# │ ├── pt1_dwi_stack.nii.gz +# │ ├── pt1_mask.nii.gz +# │ └── ... (other patient-specific files, e.g. pt1_jsonfile.json) +# ├── patient_2 +# │ ├── pt2_b0.nii.gz +# │ ├── pt2_dwi_stack.nii.gz +# │ ├── pt2_mask.nii.gz +# │ └── ... (other patient-specific files) +# └── common_files (optional) +# ├── acqparams.txt +# ├── bvecs.txt +# ├── bvals.txt +# ├── index.txt +# ├── slspec.txt +# └── config.cnf + +# names of folders are arbitrary. +# The names of these folders are copied into the linux working directory and are used to identify the respective entries. +# a 'common_files' folder is optional. The purpose is is you e.g. have the same config file or acqparams/bvecs/bvals/index/slspec files for all patients. + +# ======================================================================================================================================================= +"""CONFIGURATION - Adjust these parameters according to your data""" # change things in this section! + +#main directory in WINDOWS containing patient folders and common folder. +MAIN_DIR = r"C:\path\to\your\main_dir" # replace with path to your main_dir. + +# folder inside main_dir that contains files which are common for all patients (e.g. acqparams, bvecs, bvals, index, slspec). +COMMON_FOLDER_NAME = "common_files" # replace with your path, or set to None if there is no common folder. +# The script looks in the patient folders first. if it does not find the required files there, it looks in the common folder. + + +# Filename identifiers - Change the RHS here according to your own file naming conventions!!! +# The script will look for files containing these keywords in the patient folders first (then in the common folder). +IDENTIFIERS = { + "b0": "b0.nii.gz", # e.g. topup --imain. assumed to contain str 'b0' in the filename. + # the name of the b0 file determines the names of generated output files. + # a b0 file named 'patient1_ddmmyyyy_b0.nii.gz' will generate output files which all have the prefix 'patient1_ddmmyyyy'. + "dwi": "stack.nii.gz", # e.g. eddy --imain. DWI stack assumed to contain 'stack' in the filename. Should have the same prefix as the b0 file, e.g. 'patient1_ddmmyyyy_stack.nii.gz' to match with 'patient1_ddmmyyyy_b0.nii.gz'. + "mask": "mask", # eddy --mask. contains 'mask' in the filename. + "bvec": "bvec", + "bval": "bval", + "index": "index", # index for eddy + "acqp": "acq", # acqparams for topup and eddy. + "slspec": "slspec", # optional slice spec for eddy. + "json": "json", # optional json file for eddy. + "config": ".cnf" # optional config file for topup. If not found, the FSL default config b02b0.cnf will be used. +} + +# FSL PARAMETERS - adjust as needed. +TOPUP_PARAMS = { + "nthr": 14, # --nthr to run topup. + "jacout": None, # Default False. + "logout": None, # Default False. + "dfout": None, # Default False. + "output_dir": None # all files are saved in the linux working directory by default (None). The corrected files are copied back into main_dir in windows. + # remaining Topup parameters are set with the config file. You can specify a config file for each patient or a common one in the common folder by placing the .cnf file in the directory. +} + + +EDDY_PARAMS = { + "b_range": None, # None defaults to 50. + "flm": None, # ('linear', 'quadratic', 'cubic'). None defaults to 'quadratic' + "slm": None, # ('none', 'linear', 'quadratic'). None defaults to 'none'. + "fwhm": 10, # Default: 0 mm. Set to 10 for testing. + "niter": 1, # Default: 5. Set to 1 for testing. + "interp": None, # ('spline', 'trilinear'). None defaults to 'spline'. + "resamp": None, # ('jac', 'lsr'). None defaults to 'jac'. + "fep": None, # True/False. None defaults to False. + "nvoxhp": None, # None defaults to 1000. + "ff": None, # [0,10]. None defaults to 10. + "dont_sep_offs_move": None, # True/False. None defaults to False. + "dont_peas": None, # True/False. None defaults to False. + + "repol": None, # True/False. None defaults to False. set to True to enable outlier replacement. + "ol_nstd": None, # When repol=True; None defaults to 4. + "ol_nvox": None, # When repol=True; None defaults to 250. + "ol_type": None, # When repol=True; ('sw', 'gw', 'both'). None defaults to 'sw'. + "ol_ss": None, # When repol=True; ('sw', 'pooled'). None defaults to 'sw'. + "ol_pos": None, # When repol=True; True/False. None defaults to False. + "ol_sqr": None, # When repol=True; True/False. None defaults to False. + + "mporder": None, # Default 0. + "s2v_niter": None, # When mporder>0; None defaults to 5. + "s2v_lambda": None, # When mporder>0; None defaults to 1. + "s2v_interp": None, # When mporder>0; ('trilinear', 'spline'). None defaults to 'trilinear'. + + "estimate_move_by_susceptibility": None, # True/Flase. None defaults to False. + "mbs_niter": None, # When estimate_move_by_susceptibility=True; None defaults to 10. + "mbs_lambda": None, # When estimate_move_by_susceptibility=True; None defaults to 10. + "mbs_ksp": None, # When estimate_move_by_susceptibility=True; None defaults to 10. + + "cnr_maps": None, # True/False. None defaults to False. + "residuals": None, # True/False. None defaults to False. + "data_is_shelled": None,# True/False. None defaults to False. + "nthr": None, # --nthr to run eddy. only relevant for CPU! + + "output_dir": None # all files are saved in the linux working directory by default (None). The corrected files are copied back into original dir in windows. +} + +# WSL commands are run through your distro and in whatever directory you specify as your linux_workdir. +fsl = TOPED( + + distribution="Ubuntu-22.04", # your WSL distribution name. you can find it by running 'wsl -l -v' in powershell. + user="username", # replace with your WSL user. + linux_workdir=r"\\wsl.localhost\Ubuntu-22.04\home\user\yourfolder" # replace with a path to a folder in your WSL distribution. + # yourfolder will be created if it does not exist. + # All output files will be saved here. Corrected files from TOPUP and Eddy will be copied back to the patient folders in windows. + # linux_workdir will be organised into folders matching your main_dir structure, i.e. for each patient folder in main_dir, a corresponding folder is created in linux_workdir and all processing for that patient is done in that folder. +) + + + + + +# ======================================================================================================================================================= +"""RUNNING LOOP THOUGH FOLDERS IN MAIN_DIR, WITH PARAMTERS SPECIFIED ABOVE""" +# ALL lops are run with the parameters as specified in the configuration section above. parameters are global for the run. +# be careful if/when changing this section below (needs to match with TOPED_fsl_commands.py). + + +# HELPER functions to find input files based in IDENTIFIERS dict. +def find_file(folder, keyword) -> Optional[str]: + matches = [f for f in os.listdir(folder) if keyword.lower() in f.lower()] + if len(matches) == 0: + return None + if len(matches) > 1: + raise RuntimeError(f"Multiple files found for '{keyword}' in {folder}") + return os.path.join(folder, matches[0]) + +# function for finding cnf files. +def find_cnf_file(folder): + matches = [f for f in os.listdir(folder) if f.lower().endswith(".cnf")] + if len(matches) == 0: + return None + if len(matches) > 1: + raise RuntimeError(f"Multiple .cnf files found in {folder}! clean this shit up") + return os.path.join(folder, matches[0]) +# function for finding json files. +def find_json_file(folder): + matches = [f for f in os.listdir(folder) if f.lower().endswith(".json")] + if len(matches) == 0: + return None + if len(matches) > 1: + raise RuntimeError(f"Multiple .json files found in {folder}!") + return os.path.join(folder, matches[0]) + + +# searches for the file in the patient folder first, then in the common folder if not found in the patient folder. +def resolve_file(patient_dir, common_dir, key): + local = find_file(patient_dir, IDENTIFIERS[key]) + if local: + return local + if common_dir: + return find_file(common_dir, IDENTIFIERS[key]) + return None + + +# main loops start HERE - runs TOPUP and Eddy for each patient folder in main_dir +common_dir = None +if COMMON_FOLDER_NAME: + _common_path = os.path.join(MAIN_DIR, COMMON_FOLDER_NAME) + if os.path.isdir(_common_path): + common_dir = _common_path + else: + print("note: no common folder found -> checking compulsory files in remaining folders...") + +# Input file check - check all of main_dir, do the files exist for all patients? +# this is so that you wont leeave this overnight and come back to some shit error that could have been prevented. + +print("\n File check: Checking if all required files are found...") +file_check = True + +for patient in os.listdir(MAIN_DIR): + patient_dir = os.path.join(MAIN_DIR, patient) + if not os.path.isdir(patient_dir) or patient == COMMON_FOLDER_NAME: + continue + + issues = [] + + # Locate files using same logic as the main loop + b0_path = find_file(patient_dir, IDENTIFIERS["b0"]) + dwi_path = find_file(patient_dir, IDENTIFIERS["dwi"]) + mask_path = find_file(patient_dir, IDENTIFIERS["mask"]) + acqp_path = resolve_file(patient_dir, common_dir, "acqp") + bvecs_path = resolve_file(patient_dir, common_dir, "bvec") + bvals_path = resolve_file(patient_dir, common_dir, "bval") + index_path = resolve_file(patient_dir, common_dir, "index") + + # TOPUP compulsory inputs + if not b0_path: issues.append("TOPUP: cannot find b0 file") + if not acqp_path: issues.append("TOPUP: cannot find acquisition parameters file") + + # EDDY compulsory (only warn if b0 exists, i.e. TOPUP would run) + if b0_path: + if not dwi_path: issues.append("EDDY: cannot find 4D dwi file") + if not mask_path: issues.append("EDDY: cannot find mask file") + if not bvecs_path: issues.append("EDDY: cannot find bvecs file") + if not bvals_path: issues.append("EDDY: cannot find bvals file") + if not index_path: issues.append("EDDY: cannot find index file") + + if issues: + print(f" FAIL {patient}:") + for issue in issues: + print(f" - {issue}") + file_check = False + else: + print(f" OK {patient}") + +if not file_check: + print("\n WARNING!!!!!!!!! File check failed. Some files cannot be found. You may want to abort and fix the issues. " \ + "\n Consider renaming your files to contain the specified keyword or adjust the IDENTIFIERS dict accordingly. " \ + "\n TOPUP/Eddy will run only for the 'OK' cases.") +else: + print("\n File check passed — all patients have all compulsory inputs.") + + +for patient in os.listdir(MAIN_DIR): + # searches ALL folders in main_dir (except for specified common_folder). -> Attempts to run topup+eddy on all folders in main_dir. + patient_dir = os.path.join(MAIN_DIR, patient) + if not os.path.isdir(patient_dir) or patient == COMMON_FOLDER_NAME: + continue + print(f"\n \nProcessing folder: {patient}--------------------------------------------------------------") + patient_id = patient # this is the name of the folder both in windows and in linux workdir. + + try: + # Locate compulsory files - these files should be in the 'patient' directory, not in common. + b0_path = find_file(patient_dir, IDENTIFIERS["b0"]) + dwi_path = find_file(patient_dir, IDENTIFIERS["dwi"]) + mask_path = find_file(patient_dir, IDENTIFIERS["mask"]) + # these can be in both common and patient dir. + acqp_path = resolve_file(patient_dir, common_dir, "acqp") + bvecs_path = resolve_file(patient_dir, common_dir, "bvec") + bvals_path = resolve_file(patient_dir, common_dir, "bval") + index_path = resolve_file(patient_dir, common_dir, "index") + slspec_path = resolve_file(patient_dir, common_dir, "slspec") + config_path = find_cnf_file(patient_dir) + if not config_path and common_dir: + config_path = find_cnf_file(common_dir) + json_path = find_json_file(patient_dir) + if not json_path and common_dir: + json_path = find_json_file(common_dir) + + # Check TOPUP inputs + if not b0_path: + print(f" o_O No b0 found in {patient} → Cannot run TOPUP. skipping dataset. Rename your b0 file to contain the specified keyword or adjust the IDENTIFIERS dict accordingly.") + continue + if not acqp_path: + raise RuntimeError(" Missing acquisition parameters (acqp). Please add file or update IDENTIFIERS dict.") + + print(f" → Running TOPUP :)") + # RUN TOPUP + topup_base = fsl.run_topup( + b0_path=b0_path, + acq_parameter_path=acqp_path, + config_file_path=config_path, + nthr=TOPUP_PARAMS["nthr"], + logout=TOPUP_PARAMS["logout"], + jacout=TOPUP_PARAMS["jacout"], + dfout=TOPUP_PARAMS["dfout"], + patient_id=patient, + output_dir=TOPUP_PARAMS["output_dir"] or patient_dir + ) + + # Check EDDY inputs + missing_eddy = [] + if not dwi_path: missing_eddy.append("dwi") + if not mask_path: missing_eddy.append("mask") + if not bvecs_path: missing_eddy.append("bvecs") + if not bvals_path: missing_eddy.append("bvals") + if not index_path: missing_eddy.append("index") + + if missing_eddy: + print(f" o_O Eddy missing compulsory parameters: {missing_eddy} → Cannot run EDDY. Rename your files to contain the respective keywords or adjust the IDENTIFIERS dict accordingly.") + continue +# + print(f" → Running Eddy :)") + + # RUN EDDY + fsl.run_eddy( + dwi_path=dwi_path, + mask_path=mask_path, + acq_parameter_path=acqp_path, + index_path=index_path, + bvecs_path=bvecs_path, + bvals_path=bvals_path, + patient_id=patient, + topup_base=topup_base, + + slspec_path=slspec_path, + json_path=json_path, + b_range=EDDY_PARAMS["b_range"], + + flm=EDDY_PARAMS["flm"], + slm=EDDY_PARAMS["slm"], + fwhm=EDDY_PARAMS["fwhm"], + niter=EDDY_PARAMS["niter"], + interp=EDDY_PARAMS["interp"], + resamp=EDDY_PARAMS["resamp"], + fep=EDDY_PARAMS["fep"], + nvoxhp=EDDY_PARAMS["nvoxhp"], + ff=EDDY_PARAMS["ff"], + dont_sep_offs_move=EDDY_PARAMS["dont_sep_offs_move"], + dont_peas=EDDY_PARAMS["dont_peas"], + + repol=EDDY_PARAMS["repol"], + ol_nstd=EDDY_PARAMS["ol_nstd"], + ol_nvox=EDDY_PARAMS["ol_nvox"], + ol_type=EDDY_PARAMS["ol_type"], + ol_ss=EDDY_PARAMS["ol_ss"], + ol_pos=EDDY_PARAMS["ol_pos"], + ol_sqr=EDDY_PARAMS["ol_sqr"], + mporder=EDDY_PARAMS["mporder"], + s2v_niter=EDDY_PARAMS["s2v_niter"], + s2v_lambda=EDDY_PARAMS["s2v_lambda"], + s2v_interp=EDDY_PARAMS["s2v_interp"], + + estimate_move_by_susceptibility=EDDY_PARAMS["estimate_move_by_susceptibility"], + mbs_niter=EDDY_PARAMS["mbs_niter"], + mbs_lambda=EDDY_PARAMS["mbs_lambda"], + mbs_ksp=EDDY_PARAMS["mbs_ksp"], + + cnr_maps=EDDY_PARAMS["cnr_maps"], + residuals=EDDY_PARAMS["residuals"], + data_is_shelled=EDDY_PARAMS["data_is_shelled"], + + + output_dir=EDDY_PARAMS["output_dir"] or patient_dir + ) + + print(f"\n Done. Check your output for {patient} :)") + + except Exception as e: + print(f"ERROR in {patient}: {str(e)}") \ No newline at end of file diff --git a/src/original/preprocessing/MG_LU/__init__.py b/src/original/preprocessing/MG_LU/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/original/preprocessing/__init__.py b/src/original/preprocessing/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/src/standardized wip/IAR_LU_linear.py b/src/standardized wip/IAR_LU_linear.py index 7ff310d0..928024b8 100644 --- a/src/standardized wip/IAR_LU_linear.py +++ b/src/standardized wip/IAR_LU_linear.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_linear import IvimModelLinear +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_linear import IvimModelLinear class IAR_LU_linear(OsipiBase): diff --git a/src/standardized/DT_IIITN_WLS.py b/src/standardized/DT_IIITN_WLS.py index 4925dbed..97f1fb9a 100644 --- a/src/standardized/DT_IIITN_WLS.py +++ b/src/standardized/DT_IIITN_WLS.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.DT_IIITN.wls_ivim_fitting import wls_ivim_fit +from src.original.fitting.DT_IIITN.wls_ivim_fitting import wls_ivim_fit import numpy as np diff --git a/src/standardized/ETP_SRI_LinearFitting.py b/src/standardized/ETP_SRI_LinearFitting.py index 46d97c4c..f963c014 100644 --- a/src/standardized/ETP_SRI_LinearFitting.py +++ b/src/standardized/ETP_SRI_LinearFitting.py @@ -1,6 +1,6 @@ import numpy as np from src.wrappers.OsipiBase import OsipiBase -from src.original.ETP_SRI.LinearFitting import LinearFit +from src.original.fitting.ETP_SRI.LinearFitting import LinearFit import warnings warnings.simplefilter('once', UserWarning) diff --git a/src/standardized/IAR_LU_biexp.py b/src/standardized/IAR_LU_biexp.py index e36e5879..e362bf1a 100644 --- a/src/standardized/IAR_LU_biexp.py +++ b/src/standardized/IAR_LU_biexp.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_biexp import IvimModelBiExp +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_biexp import IvimModelBiExp class IAR_LU_biexp(OsipiBase): diff --git a/src/standardized/IAR_LU_modified_mix.py b/src/standardized/IAR_LU_modified_mix.py index 3580f8ba..48aef405 100644 --- a/src/standardized/IAR_LU_modified_mix.py +++ b/src/standardized/IAR_LU_modified_mix.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_modified_mix import IvimModelVP +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_modified_mix import IvimModelVP class IAR_LU_modified_mix(OsipiBase): diff --git a/src/standardized/IAR_LU_modified_topopro.py b/src/standardized/IAR_LU_modified_topopro.py index 58e6323d..d86b6779 100644 --- a/src/standardized/IAR_LU_modified_topopro.py +++ b/src/standardized/IAR_LU_modified_topopro.py @@ -2,7 +2,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_modified_topopro import IvimModelTopoPro +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_modified_topopro import IvimModelTopoPro class IAR_LU_modified_topopro(OsipiBase): diff --git a/src/standardized/IAR_LU_segmented_2step.py b/src/standardized/IAR_LU_segmented_2step.py index 9d1d4149..dbbec2c9 100644 --- a/src/standardized/IAR_LU_segmented_2step.py +++ b/src/standardized/IAR_LU_segmented_2step.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_segmented_2step import IvimModelSegmented2Step +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_segmented_2step import IvimModelSegmented2Step class IAR_LU_segmented_2step(OsipiBase): diff --git a/src/standardized/IAR_LU_segmented_3step.py b/src/standardized/IAR_LU_segmented_3step.py index 28ae1ab8..5a03bee6 100644 --- a/src/standardized/IAR_LU_segmented_3step.py +++ b/src/standardized/IAR_LU_segmented_3step.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_segmented_3step import IvimModelSegmented3Step +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_segmented_3step import IvimModelSegmented3Step class IAR_LU_segmented_3step(OsipiBase): diff --git a/src/standardized/IAR_LU_subtracted.py b/src/standardized/IAR_LU_subtracted.py index d0548cb4..c2b6fd3b 100644 --- a/src/standardized/IAR_LU_subtracted.py +++ b/src/standardized/IAR_LU_subtracted.py @@ -1,7 +1,7 @@ import numpy as np from dipy.core.gradients import gradient_table from src.wrappers.OsipiBase import OsipiBase -from src.original.IAR_LundUniversity.ivim_fit_method_subtracted import IvimModelSubtracted +from src.original.fitting.IAR_LundUniversity.ivim_fit_method_subtracted import IvimModelSubtracted class IAR_LU_subtracted(OsipiBase): diff --git a/src/standardized/OGC_AmsterdamUMC_Bayesian_biexp.py b/src/standardized/OGC_AmsterdamUMC_Bayesian_biexp.py index a4e68e7e..2de8cbf7 100644 --- a/src/standardized/OGC_AmsterdamUMC_Bayesian_biexp.py +++ b/src/standardized/OGC_AmsterdamUMC_Bayesian_biexp.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.OGC_AmsterdamUMC.LSQ_fitting import flat_neg_log_prior, fit_bayesian, empirical_neg_log_prior, fit_segmented, fit_bayesian_array, fit_segmented_array +from src.original.fitting.OGC_AmsterdamUMC.LSQ_fitting import flat_neg_log_prior, fit_bayesian, empirical_neg_log_prior, fit_segmented, fit_bayesian_array, fit_segmented_array import warnings import numpy as np diff --git a/src/standardized/OGC_AmsterdamUMC_biexp.py b/src/standardized/OGC_AmsterdamUMC_biexp.py index bf5aac57..80e5a8e0 100644 --- a/src/standardized/OGC_AmsterdamUMC_biexp.py +++ b/src/standardized/OGC_AmsterdamUMC_biexp.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.OGC_AmsterdamUMC.LSQ_fitting import fit_least_squares, fit_least_squares_array +from src.original.fitting.OGC_AmsterdamUMC.LSQ_fitting import fit_least_squares, fit_least_squares_array import numpy as np class OGC_AmsterdamUMC_biexp(OsipiBase): diff --git a/src/standardized/OGC_AmsterdamUMC_biexp_segmented.py b/src/standardized/OGC_AmsterdamUMC_biexp_segmented.py index c3ac076b..6d687feb 100644 --- a/src/standardized/OGC_AmsterdamUMC_biexp_segmented.py +++ b/src/standardized/OGC_AmsterdamUMC_biexp_segmented.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.OGC_AmsterdamUMC.LSQ_fitting import fit_segmented, fit_segmented_array +from src.original.fitting.OGC_AmsterdamUMC.LSQ_fitting import fit_segmented, fit_segmented_array import warnings import numpy as np diff --git a/src/standardized/OJ_GU_seg.py b/src/standardized/OJ_GU_seg.py index 74ec7eda..9b8cbf2f 100644 --- a/src/standardized/OJ_GU_seg.py +++ b/src/standardized/OJ_GU_seg.py @@ -1,6 +1,6 @@ import numpy as np from src.wrappers.OsipiBase import OsipiBase -from src.original.OJ_GU.ivim_seg import seg +from src.original.fitting.OJ_GU.ivim_seg import seg class OJ_GU_seg(OsipiBase): """ diff --git a/src/standardized/PV_MUMC_biexp.py b/src/standardized/PV_MUMC_biexp.py index 3331e9a1..fa854cda 100644 --- a/src/standardized/PV_MUMC_biexp.py +++ b/src/standardized/PV_MUMC_biexp.py @@ -1,6 +1,6 @@ import numpy as np from src.wrappers.OsipiBase import OsipiBase -from src.original.PV_MUMC.two_step_IVIM_fit import fit_least_squares +from src.original.fitting.PV_MUMC.two_step_IVIM_fit import fit_least_squares class PV_MUMC_biexp(OsipiBase): diff --git a/src/standardized/PvH_KB_NKI_IVIMfit.py b/src/standardized/PvH_KB_NKI_IVIMfit.py index febeeaac..a574a94e 100644 --- a/src/standardized/PvH_KB_NKI_IVIMfit.py +++ b/src/standardized/PvH_KB_NKI_IVIMfit.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.PvH_KB_NKI.DWI_functions_standalone import generate_IVIMmaps_standalone, generate_ADC_standalone +from src.original.fitting.PvH_KB_NKI.DWI_functions_standalone import generate_IVIMmaps_standalone, generate_ADC_standalone import numpy as np import warnings warnings.simplefilter('once', UserWarning) diff --git a/src/standardized/TF_reference_IVIMfit.py b/src/standardized/TF_reference_IVIMfit.py index eee58f38..f72062d5 100644 --- a/src/standardized/TF_reference_IVIMfit.py +++ b/src/standardized/TF_reference_IVIMfit.py @@ -1,5 +1,5 @@ from src.wrappers.OsipiBase import OsipiBase -from src.original.TF_reference.segmented_IVIMfit import segmented_IVIM_fit +from src.original.fitting.TF_reference.segmented_IVIMfit import segmented_IVIM_fit import warnings import numpy as np diff --git a/src/wrappers/ivim_fit.py b/src/wrappers/ivim_fit.py index fe1f9dc6..268afe66 100644 --- a/src/wrappers/ivim_fit.py +++ b/src/wrappers/ivim_fit.py @@ -7,7 +7,7 @@ import numpy as np # from utils.data_simulation.GenerateData import GenerateData -from src.original.ETP_SRI.LinearFitting import LinearFit +from src.original.fitting.ETP_SRI.LinearFitting import LinearFit author_lookup = { 'ETP_SRI': LinearFit diff --git a/tests/IVIMpreproc/unit_tests/__init__.py b/tests/IVIMpreproc/unit_tests/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/tests/IVIMpreproc/unit_tests/wip_degibbs.py b/tests/IVIMpreproc/unit_tests/wip_degibbs.py new file mode 100644 index 00000000..4287ca86 --- /dev/null +++ b/tests/IVIMpreproc/unit_tests/wip_degibbs.py @@ -0,0 +1 @@ +# \ No newline at end of file diff --git a/tests/IVIMpreproc/unit_tests/wip_denoise.py b/tests/IVIMpreproc/unit_tests/wip_denoise.py new file mode 100644 index 00000000..f198a263 --- /dev/null +++ b/tests/IVIMpreproc/unit_tests/wip_denoise.py @@ -0,0 +1,63 @@ +''' +1. Load brain phantom +2. Add Rician noise +3. Denoise using denoise algorithm +4. Check that sum of squared residuals decreased after denoising +''' +import os + +import numpy as np +from phantoms.brain.sim_brain_phantom import simulate_brain_phantom +import nibabel as nib +import matplotlib.pyplot as plt +from src.original.preprocessing.EP_GU.brain_pipeline import denoise_wrap + + +def test_denoise_wrap(): + # Simulate phantom with noise + snr = 50 + simulate_brain_phantom(snr = snr) + + # Denoising + im_file = 'phantoms/brain/data/diffusive_snr{}.nii.gz'.format(snr) + im_file_denoised = denoise_wrap(im_file) + S_denoised = nib.load(im_file_denoised).get_fdata() + + # Compute sum of squared residuals before denoising + mask = nib.load(os.path.join('phantoms','brain','data','diffusive_snr{}_mask.nii.gz'.format(snr))).get_fdata() + ref_file = 'phantoms/brain/data/diffusive_reference.nii.gz' + S = nib.load(im_file).get_fdata() + S_ref = nib.load(ref_file).get_fdata() + ssr_before = np.sum((S[mask!=0,:]-S_ref[mask!=0,:])**2) + ssr_after = np.sum((S_denoised[mask!=0,:]-S_ref[mask!=0,:])**2) + + + + # print('SSR before denoising: {}'.format(ssr_before)) + # print('SSR after denoising: {}'.format(ssr_after)) + + # plt.subplot(1,3,1) + # plt.imshow(np.rot90(S_ref[:,:,30,10]),cmap='gray') + # plt.title('Reference') + # plt.xticks([]) + # plt.yticks([]) + # plt.subplot(1,3,2) + # plt.imshow(np.rot90(S[:,:,30,10]),cmap='gray') + # plt.title('Noisy') + # plt.xticks([]) + # plt.yticks([]) + # plt.subplot(1,3,3) + # plt.imshow(np.rot90(S_denoised[:,:,30,10]),cmap='gray') + # plt.title('Denoised') + # plt.xticks([]) + # plt.yticks([]) + # plt.show() + + # Check that sum of squared residuals decreased after denoising + if ssr_after < ssr_before: + assert True + else: + assert False + + +