Source code for cmind.pipeline.cmind_T1map_preprocess

#!/usr/bin/env python
from __future__ import division, print_function, absolute_import

[docs]def cmind_T1map_preprocess(output_dir,T1EST_nii_folder,T1EST_glob='',ANTS_bias_cmd=None,do_motion_cor=True,generate_figures=True,ForceUpdate=False,verbose=False,logger=None): """T1EST preprocessing prior to fitting T1 values Parameters ---------- output_dir : str directory in which to store the output T1EST_nii_folder : str or list of str or list of tuple folder containing all of the T1EST NIFTI-GZ files or a list of tuples where the first element of the tuple is a filename and the second is the corresponding TI value. If a text file is provided instead it must be formatted withe one comma separated filename and TI value per line. TI values should be specified in ms. T1EST_glob : str, optional if this string is not empty, use this as the file pattern to match within T1EST_nii_folder (e.g. T1EST_glob='*T1EST*.nii.gz'). The filenames will be required to have TI values stored within them as *_TI%d_*. For general filenames, use csv file input as described above under `T1EST_nii_folder`. ANTS_bias_cmd : str, optional path to the ANTs bias correction binary do_motion_cor : bool, optional coregister the images from the different TI times generate_figures : bool, optional if true, generate additional summary images ForceUpdate : bool,optional if True, rerun and overwrite any previously existing results verbose : bool, optional print additional output (to terminal and log) logger : logging.Logger or str, optional logging.Logger object (or string of a filename to log to) Returns ------- T1concat_mcf : str concatenated T1EST images after (optional) motion correction TIvals_file : str text file containing the TI values T1concat_mean_N4 : str output volume containing mean over T1concat_mcf T1concat_mean_N4_brain : str T1concat_mean_N4 after brain extraction T1concat_mean_N4_mask : str mask corresponding to T1concat_mean_N4_brain Notes ----- combines separate 3D T1EST images into a single 4D timeseries optionally coregisters the separate T1EST images as well .. figure:: ../img/IRC04H_06M008_P_1_allTI_uncor_mov.gif :align: center :scale: 100% Coregistered images magnitude images for each of the TI times For the CMIND study, the *T1EST_TI*.nii.gz files for a given subject can be stored in a folder and the files will be found and have the TI values extracted automatically. For more general inputs, see the documentation of the T1EST_nii_folder input. """ import os import glob import shutil import tempfile import warnings import numpy as np import nibabel as nib from cmind.globals import (has_ImageMagick, has_GraphicsMagick, cmind_imageconvert_cmd) from cmind.utils.utils import input2bool from cmind.utils.file_utils import imexist, split_multiple_ext from cmind.utils.nifti_utils import cmind_save_nii_mod_header from cmind.utils.cmind_utils import cmind_reg_report_img, find_optimal_FSL_refvol from cmind.utils.fsl_mcflirt_opt import fsl_mcflirt_opt from cmind.utils.logging_utils import cmind_init_logging, log_cmd, cmind_func_info #convert various strings to boolean generate_figures, ForceUpdate, verbose, do_motion_cor = input2bool([generate_figures, ForceUpdate, verbose, do_motion_cor]) if verbose: cmind_func_info(logger=logger) module_logger=cmind_init_logging(verbose=verbose, logger=logger) module_logger.info("Starting T1 estimation preprocessing") if generate_figures and (not (has_ImageMagick or has_GraphicsMagick)): warnings.warn("generate_figures=True, but has_ImageMagick=False. Images will not be created") if not os.path.isdir(output_dir): os.makedirs(output_dir); ForceUpdate=input2bool(ForceUpdate) generate_figures=input2bool(generate_figures) do_motion_cor=input2bool(do_motion_cor) if not ANTS_bias_cmd: from cmind.globals import cmind_ANTs_dir ANTS_bias_cmd=os.path.join(cmind_ANTs_dir,'N4BiasFieldCorrection') VERBOSE=False fcheck=os.path.join(output_dir,'T1concat_mean_N4_brain.nii.gz') T1concat_mcf=os.path.join(output_dir,'T1concat_mcf.nii.gz') TIvals_file=os.path.join(output_dir,'TIvals.txt') T1concat_mean_N4=os.path.join(output_dir,'T1concat_mean_N4.nii.gz') T1concat_mean_N4_brain=os.path.join(output_dir,'T1concat_mean_N4_brain.nii.gz') T1concat_mean_N4_mask=os.path.join(output_dir,'T1concat_mean_N4_brain_mask.nii.gz') #if(~exist('./T1_map.nii.gz','file') || ForceUpdate) if (not imexist(fcheck,'nifti-1')[0]) or ForceUpdate: if ForceUpdate: #remove old image volumes from prior processing if imexist(os.path.join(output_dir,'T1concat'),'nifti-1')[0] or imexist(os.path.join(output_dir,'T1concat_mcf'),'nifti-1')[0]: log_cmd('imrm ' + os.path.join(output_dir,'T1concat*'), verbose=verbose, logger=module_logger) if generate_figures: working_dir=tempfile.mkdtemp() rm_working_dir=True else: rm_working_dir=False #find the files and TI values if isinstance(T1EST_nii_folder,str): if os.path.isdir(T1EST_nii_folder): #auto-find for CMIND study. unlikely to work for other datasets. # should pass list of (filename, TI) tuples instead for the general case print(T1EST_nii_folder) try: print(type(T1EST_glob)) if not T1EST_glob: files=glob.glob(os.path.join(T1EST_nii_folder,'*T1EST_TI*')); if not files: TIstr='T1ESTTI'; else: TIstr='T1EST_TI'; T1EST_glob='*' + TIstr + '*.nii.gz' else: TIstr='_TI' files=glob.glob(os.path.join(T1EST_nii_folder,T1EST_glob)); print(files) if not files: #convert all .PAR to .nii.gz raise IOError("No T1EST .nii.gz files found") nTI = len(files) TIvals = [] for nn in range(nTI): TIloc=files[nn].find(TIstr)+len(TIstr) if TIstr=='T1ESTTI': TIloc2=files[nn][TIloc::].find('0s')+1; else: #e.g. 'T1EST_TI': TIloc2=files[nn][TIloc::].find('_') TIvals.append(float(files[nn][TIloc:TIloc+TIloc2])) TIvals=np.asarray(TIvals) except: raise Exception("Unable to auto-find the T1EST files in {}".format(T1EST_nii_folder)) elif os.path.exists(T1EST_nii_folder): files=[] TIvals=[] with open(T1EST_nii_folder,'r') as f: for line in f: if line.strip(): f,TI=line.strip().split(',') files.append(f) TIvals.append(TI) nTI = len(files) elif isinstance(T1EST_nii_folder,(list,tuple)): tmp=T1EST_nii_folder[0] if (not isinstance(tmp,(list,tuple))) or (len(tmp)!=2): raise ValueError("Elements of T1EST_nii_folder list must be a list or tuple of length 2") files,TIvals=zip(*T1EST_nii_folder) nTI = len(files) for f in files: if not imexist(f,'nifti-1')[0]: raise IOError("Specified input file, {}, not found".format(f)) else: raise ValueError("T1ESET_nii_folder must be a string, list or tuple") TIvals=np.asarray(TIvals,dtype=np.float32) if TIvals.shape[0]!=np.unique(TIvals).shape[0]: raise IOError("Found multiple T1EST files for the same TI!") si=np.argsort(TIvals) #sort indices TIvals=np.sort(TIvals)/1000.0 #sort into ascending order and convert to seconds files_sorted=[] for idx in range(si.shape[0]): #sort filenames to match ascending TI order files_sorted.append(files[si[idx]]) files = files_sorted; T1={} for nn in range(nTI): tmp_nii=nib.load(files[nn]) if nn==0: #preallocate T1['data'] shape=tmp_nii.get_shape(); imsize=(shape[0], shape[1], shape[2], nTI) T1['data']=np.zeros(imsize,'float32') hdr=tmp_nii.get_header() voxeldims=hdr['pixdim'][1:4]; T1['data'][:,:,:,nn]=tmp_nii.get_data() o=output_dir nii_type=16; #floating point cmind_save_nii_mod_header(tmp_nii,T1['data'],os.path.join(o,'T1concat.nii.gz'),nii_type) log_cmd('$FSLDIR/bin/fslmaths "%s/T1concat" -Tmean "%s/T1concat_mean"' % (o,o), verbose=verbose, logger=module_logger) if do_motion_cor: #if less than 1 voxel width's motion is detected then skip motion correction log_cmd('$FSLDIR/bin/mcflirt -in "%s/T1concat" -out "%s/T1map_motiontest_mcf" -plots -rmsrel -rmsabs -refvol 0 -cost normmi' % (o,o), verbose=verbose, logger=module_logger) #Find the timepoint closest to the mean position my_refvol = find_optimal_FSL_refvol(os.path.join(o,'T1map_motiontest_mcf.par'))[0] #redo the registration using this "optimal" minimal-distance reference volume log_cmd('$FSLDIR/bin/mcflirt -in "%s/T1concat" -out "%s/T1map_motiontest_mcf" -plots -rmsrel -rmsabs -refvol %d -cost normmi' % (o,o,my_refvol), verbose=verbose, logger=module_logger) absmotionpar=np.loadtxt(os.path.join(o,'T1map_motiontest_mcf_abs.rms')) #print "(absmotionpar, voxeldims) = (%s, %s) " % (np.max(absmotionpar), np.min(voxeldims)) if np.max(absmotionpar)<(np.min(voxeldims)/3.0): #if estimated motion is > 1/3 of voxel, use motion correction of the inidividual T1EST volumes do_motion_cor=False; log_cmd('$FSLDIR/bin/imrm "%s"/T1map_motiontest_mcf*' % (o), verbose=verbose, logger=module_logger) #remove any .mat folders created by mcflirt temp_dirs=[os.path.join(output_dir,om) for om in os.listdir(output_dir) if (os.path.isdir(os.path.join(output_dir,om)) and om.find('.mat')!=-1)] #find all subdirectories with .mat in the directory name for d in temp_dirs: shutil.rmtree(d) if (not imexist(os.path.join(o,'T1concat_mean_N4_brain'),'nifti-1')[0]) or ForceUpdate: if do_motion_cor: fsl_mcflirt_opt(os.path.join(o,'T1concat'),'normmi',os.path.join(o,'T1concat_mcf'),verbose=verbose,logger=logger) nii=nib.load(os.path.join(o,'T1concat_mcf.nii.gz')) motionpar=np.genfromtxt(os.path.join(o,'T1concat_mcf.par')); if VERBOSE: from matplotlib import pylab from matplotlib import pyplot pylab.figure(),pylab.plot(motionpar[:,0:3]*180/np.pi),pyplot.title('rotations (deg)') pylab.figure(),pylab.plot(motionpar[:,3:6]),pyplot.title('translations (mm)') T1['data'] = nii.get_data() log_cmd('$FSLDIR/bin/fslmaths "%s/T1concat_mcf" -Tmean "%s/T1concat_mcf_mean"' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/imcp "%s/T1concat_mcf_mean.nii.gz" "%s/T1concat_mean.nii.gz"' % (o,o), verbose=verbose, logger=module_logger) if generate_figures and (has_ImageMagick or has_GraphicsMagick): #generate a summary image of the T1EST registration try: Fig_Dir=os.path.join(o,'T1Est_RegPNGs') if not os.path.exists(Fig_Dir): os.makedirs(Fig_Dir) #Make movie loop & summary image stack from post-registered TI volumes log_cmd('$FSLDIR/bin/imcp "%s"/../T1concat_mcf "%s"/T1concat_mcf' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fslsplit "%s"/T1concat_mcf "%s"/vol' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) rfiles=glob.glob(os.path.join(Fig_Dir,'vol*.nii*')) input_vol1 = os.path.join(Fig_Dir, 'vol0000') fewer=True #only plot 2 slices per axis instead of 4 for nn in range(len(rfiles)): log_cmd('%s -background black -fill white -pointsize 58 +distort SRT 270 label:" %s " "%s"/title.png' % (cmind_imageconvert_cmd,'TI = '+ str(TIvals[nn]),Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/slicer %s -n -s 4 -a "%s"/vol%04d.png' % (rfiles[nn],Fig_Dir,nn), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/pngappend "%s"/title.png + "%s"/vol%04d.png "%s"/vol%04d_wTI.png' % (Fig_Dir,Fig_Dir,nn,Fig_Dir,nn), verbose=verbose, logger=module_logger) if nn==0: log_cmd('cp "%s"/vol%04d_wTI.png "%s"/allTI_img.png' % (Fig_Dir,nn,Fig_Dir), verbose=verbose, logger=module_logger) else: log_cmd('$FSLDIR/bin/pngappend "%s"/allTI_img.png - "%s"/vol%04d_wTI.png "%s"/allTI_img.png' % (Fig_Dir,Fig_Dir,nn,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('%s "%s"/vol%04d.png "%s"/vol%04d.gif' % (cmind_imageconvert_cmd,Fig_Dir,nn,Fig_Dir,nn), verbose=verbose, logger=module_logger) os.remove(os.path.join(Fig_Dir,'title.png')) log_cmd('$FSLDIR/bin/whirlgif -o "%s"/allTI_mov.gif -loop "%s"/vol????.gif' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('rm "%s"/vol*.gif "%s"/vol*.png' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('mv "%s"/allTI_img.png "%s"' % (Fig_Dir,output_dir), verbose=verbose, logger=module_logger) log_cmd('mv "%s"/allTI_mov.gif "%s"' % (Fig_Dir,output_dir), verbose=verbose, logger=module_logger) #Make registration overlay image all_pngs="" for nn in range(1,len(rfiles)): input_vol2 = os.path.join(Fig_Dir, split_multiple_ext(rfiles[nn])[0]); output_file = os.path.join(Fig_Dir, 'vol%04d' % nn + '_reg.png'); if nn==len(rfiles)-1: all_pngs = all_pngs + output_file else: if nn%2==1: all_pngs = all_pngs + output_file + ' + 80 ' else: all_pngs = all_pngs + output_file + ' - ' if not os.path.exists(output_file): cmind_reg_report_img(input_vol1,input_vol2, output_file, working_dir,fewer) log_cmd('$FSLDIR/bin/pngappend %s "%s"/T1EST_register.png' % (all_pngs,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('mv "%s"/T1EST_register.png "%s"' % (Fig_Dir,output_dir), verbose=verbose, logger=module_logger) shutil.rmtree(Fig_Dir) except: warnings.warn("Failed to create images") if do_motion_cor: #generate motion summary images log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1concat_mcf.par -t "MCFLIRT estimated rotations (radians)" -u 1 --start=1 --finish=3 -a x,y,z -w 640 -h 144 -o "%s"/T1map_rot.png' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1concat_mcf.par -t "MCFLIRT estimated translations (mm)" -u 1 --start=4 --finish=6 -a x,y,z -w 640 -h 144 -o "%s"/T1map_trans.png' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1concat_mcf_abs.rms,"%s"/T1concat_mcf_rel.rms -t "MCFLIRT estimated mean displacement (mm)" -u 1 -w 640 -h 144 -a absolute,relative -o "%s"/T1map_disp.png' % (o,o,o), verbose=verbose, logger=module_logger) else: #generate motion summary images log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1map_motiontest_mcf.par -t "MCFLIRT estimated rotations (radians)" -u 1 --start=1 --finish=3 -a x,y,z -w 640 -h 144 -o "%s"/T1map_rot.png' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1map_motiontest_mcf.par -t "MCFLIRT estimated translations (mm)" -u 1 --start=4 --finish=6 -a x,y,z -w 640 -h 144 -o "%s"/T1map_trans.png' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fsl_tsplot -i "%s"/T1map_motiontest_mcf_abs.rms,T1map_motiontest_mcf_rel.rms -t "MCFLIRT estimated mean displacement (mm)" -u 1 -w 640 -h 144 -a absolute,relative -o "%s"/T1map_disp.png' % (o,o,o), verbose=verbose, logger=module_logger) else: nii=nib.load(os.path.join(o,'T1concat.nii.gz')); T1['data'] = nii.get_data() #T1.data=double(T1.data.img); log_cmd('$FSLDIR/bin/fslmaths "%s"/T1concat -Tmean "%s"/T1concat_mean' % (o,o), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/imcp "%s/T1concat" "%s/T1concat_mcf"' % (o,o), verbose=verbose, logger=module_logger) if generate_figures and (has_ImageMagick or has_GraphicsMagick): #generate a summary image of the T1EST registration try: #TODO: cleanup some of the duplicate code here #Make movie loop from pre-registered TI volumes Fig_Dir=os.path.join(o,'T1Est_RegPNGs') if not os.path.exists(Fig_Dir): os.makedirs(Fig_Dir) log_cmd('$FSLDIR/bin/imcp "%s"/T1concat "%s"/T1concat' % (o,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/fslsplit "%s"/T1concat "%s"/uncor' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) uncor_files=glob.glob(os.path.join(Fig_Dir,'uncor*.nii*')) fewer=True #only plot 2 slices per axis instead of 4 for nn in range(len(uncor_files)): log_cmd('$FSLDIR/bin/slicer %s -n -s 4 -a "%s"/uncor%04d.png' % (uncor_files[nn],Fig_Dir,nn), verbose=verbose, logger=module_logger) log_cmd('%s "%s"/uncor%04d.png "%s"/uncor%04d.gif' % (cmind_imageconvert_cmd,Fig_Dir,nn,Fig_Dir,nn), verbose=verbose, logger=module_logger) log_cmd('$FSLDIR/bin/whirlgif -o "%s"/allTI_uncor_mov.gif -loop "%s"/uncor????.gif' % (Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('rm "%s"/uncor*.gif "%s"/uncor*.png "%s"/uncor*.nii.gz' % (Fig_Dir,Fig_Dir,Fig_Dir), verbose=verbose, logger=module_logger) log_cmd('mv "%s"/allTI_uncor_mov.gif "%s"' % (Fig_Dir,output_dir), verbose=verbose, logger=module_logger) shutil.rmtree(Fig_Dir) except: warnings.warn("Failed to generate images") log_cmd('%s -d 3 -i "%s/T1concat_mean.nii.gz" -o ["%s/T1concat_mean_N4.nii.gz","%s/N4BiasT1concat.nii.gz"] -s 1 -b 200 -c [100x100x100x100, 1e-05]' % (ANTS_bias_cmd,o,o,o), verbose=verbose, logger=module_logger) np.savetxt(TIvals_file,TIvals) log_cmd('$FSLDIR/bin/imrm "%s/T1concat_mean"' % o, verbose=verbose, logger=logger) log_cmd('$FSLDIR/bin/bet "%s"/T1concat_mean_N4 "%s"/T1concat_mean_N4_brain -f 0.3 -g 0 -R -m' % (o,o), verbose=verbose, logger=module_logger) #make sure temporary working directory has been removed if rm_working_dir and os.path.exists(working_dir): shutil.rmtree(working_dir) #print any filename outputs for capture by LONI print("T1concat_mcf:{}".format(T1concat_mcf)) print("TIvals_file:{}".format(TIvals_file)) print("T1concat_mean_N4:{}".format(T1concat_mean_N4)) print("T1concat_mean_N4_brain:{}".format(T1concat_mean_N4_brain)) print("T1concat_mean_N4_mask:{}".format(T1concat_mean_N4_mask)) return (T1concat_mcf, TIvals_file, T1concat_mean_N4, T1concat_mean_N4_brain, T1concat_mean_N4_mask)
def _testme(): #output_dir='/media/Data1/CMIND_Other/Matlab_Output/06M008/P_copy/T1map/' #T1EST_nii_folder='/media/Data1/CMIND_Other/Matlab_Output/06M008/P_copy/' import os, tempfile from os.path import join as pjoin from cmind.utils.logging_utils import cmind_logger from cmind.globals import cmind_example_dir,cmind_example_output_dir,cmind_ANTs_dir output_dir=pjoin(cmind_example_output_dir,'P','T1map') T1EST_nii_folder_created=False test_cases=['fromdir','fromlist','fromfile'] for test_case in test_cases: if test_case=='fromdir': #infer from filenames in directory T1EST_nii_folder=cmind_example_dir elif test_case=='fromlist': #test specify explicitly T1EST_nii_folder=[(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI1000_SENSE_13_1.nii.gz'),1000), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI100_SENSE_14_1.nii.gz'),100), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI1500_SENSE_17_1.nii.gz'),1500), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI2000_SENSE_11_1.nii.gz'),2000), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI200_SENSE_9_1.nii.gz'),200), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI300_SENSE_16_1.nii.gz'),300), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI400_SENSE_12_1.nii.gz'),400), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI500_SENSE_18_1.nii.gz'),500), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI750_SENSE_10_1.nii.gz'),750), (pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI3000_SENSE_15_1.nii.gz'),3000), ] elif test_case=='fromfile': #test read from file T1EST_nii_folder=tempfile.mktemp() T1EST_nii_folder_created=True print(T1EST_nii_folder) f=open(T1EST_nii_folder,'w') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI1000_SENSE_13_1.nii.gz')+',1000\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI100_SENSE_14_1.nii.gz')+',100\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI1500_SENSE_17_1.nii.gz')+',1500\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI2000_SENSE_11_1.nii.gz')+',2000\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI200_SENSE_9_1.nii.gz')+',200\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI300_SENSE_16_1.nii.gz')+',300\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI400_SENSE_12_1.nii.gz')+',400\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI500_SENSE_18_1.nii.gz')+',500\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI750_SENSE_10_1.nii.gz')+',750\n') f.write(pjoin(cmind_example_dir,'IRC04H_06M008_P_1_WIP_T1EST_TI3000_SENSE_15_1.nii.gz')+',3000\n') f.write('\n\n') f.close() else: raise ValueError("Unknown test case") T1EST_glob='' ANTS_bias_cmd=pjoin(cmind_ANTs_dir,'N4BiasFieldCorrection') do_motion_cor=True generate_figures=True ForceUpdate=True; verbose=True logger=cmind_logger(log_level_console='INFO',logfile=os.path.join(tempfile.gettempdir(),'cmind_log.txt'),log_level_file='DEBUG',file_mode='w') if verbose: func=cmind_timer(cmind_T1map_preprocess,logger=logger) else: func=cmind_T1map_preprocess func(output_dir,T1EST_nii_folder,T1EST_glob=T1EST_glob,ANTS_bias_cmd=ANTS_bias_cmd,do_motion_cor=do_motion_cor,generate_figures=generate_figures,ForceUpdate=ForceUpdate,verbose=verbose,logger=logger) if T1EST_nii_folder_created: os.remove(T1EST_nii_folder) if __name__=='__main__': import sys, argparse from cmind.utils.utils import _parser_to_loni from cmind.utils.decorators import cmind_timer if len(sys.argv) == 2 and sys.argv[1]=='test': _testme() else: parser = argparse.ArgumentParser(description="T1EST preprocessing prior to fitting T1 values", epilog="") #-h, --help exist by default #example of a positional argument parser.add_argument("-o","--output_dir",required=True, help="directory in which to store the output") parser.add_argument("-i","--T1EST_nii_folder",required=True, help="folder containing all of the T1EST NIFTI-GZ files or a list of the individual files") parser.add_argument("-a","-ants","--ANTS_bias_cmd", help="path to the ANTs bias correction binary") parser.add_argument("--T1EST_glob", type=str, default='', help="if this string is not empty, use this as the file pattern to match within T1EST_nii_folder (e.g. T1EST_glob='*T1EST*.nii.gz')") parser.add_argument("-mc","--do_motion_cor", type=str, default='true', help="coregister the images from the different TI times") parser.add_argument("-gf","--generate_figures",type=str,default="True", help="if true, generate additional summary images") parser.add_argument("-u","--ForceUpdate",type=str,default="False", help="if True, rerun and overwrite any previously existing results") parser.add_argument("-v","-debug","--verbose", help="print additional output (to terminal and log)", action="store_true") parser.add_argument("-log","--logfile", dest='logger', type=str, default="", help="logging.Logger object (or string of a filename to log to)") #if first command line argument is 'loni_bash', print bash template instead of proceeding _parser_to_loni(parser, sys.argv, __file__) #kludge to auto-generate case/esac and usage statements for the corresponding LONI shell scripts args=parser.parse_args() output_dir=args.output_dir T1EST_nii_folder=args.T1EST_nii_folder T1EST_glob=args.T1EST_glob ANTS_bias_cmd=args.ANTS_bias_cmd do_motion_cor=args.do_motion_cor generate_figures=args.generate_figures ForceUpdate=args.ForceUpdate verbose=args.verbose logger=args.logger if verbose: cmind_T1map_preprocess=cmind_timer(cmind_T1map_preprocess,logger=logger) cmind_T1map_preprocess(output_dir,T1EST_nii_folder,T1EST_glob=T1EST_glob,ANTS_bias_cmd=ANTS_bias_cmd,do_motion_cor=do_motion_cor,generate_figures=generate_figures,ForceUpdate=ForceUpdate,verbose=verbose,logger=logger)