def iterative_propagator(sp): """ Propagate all the atlas of the multi-atlas on the target according to the spot instance data. :param sp: instance of the class Spot. :return: for each subjec sj of the multi atlas we have the final segmentation and warped, ready to be stacked: 'final_{0}_over_{1}_segm.nii.gz'.format(sj, sp.target_name) and 'final_{0}_over_{1}_warp.nii.gz'.format(sj, sp.target_name) """ pfo_tmp = sp.scaffoldings_pfo # -- AFFINE -- affine_propagator(sp) # -- NON RIGID -- num_nrigid_modalities = len(sp.propagation_options['N_rigid_modalities']) if num_nrigid_modalities > 0: # -- call non-rigid propagation: non_rigid_propagator(sp) resulting_segmentations_pfi_list = [jph(pfo_tmp, 'segm_moving_nrigid_warp_{0}_on_target_{1}.nii.gz').format(sj, sp.target_name) for sj in sp.atlas_list_charts_names] else: resulting_segmentations_pfi_list = [jph(pfo_tmp, 'segm_moving_aff_warp_{0}_on_target_{1}.nii.gz').format(sj, sp.target_name) for sj in sp.atlas_list_charts_names] # -- SMOOTHING RESULTING SEGMENTATION -- if sp.propagation_options['Final_smoothing_factor'] > 0 and sp.propagation_controller['Smooth_results']: for p in resulting_segmentations_pfi_list: assert os.path.exists(p), p p_new = p.replace('.nii.gz', '_SMOL.nii.gz') cmd = 'seg_maths {0} -smol {1} {2}'.format(p, sp.propagation_options['Final_smoothing_factor'], p_new) print_and_run(cmd)
def extract_brain_tissue_in_NI_multi_atlas(): """ From the existing multi-atlas with the parcellation, this method the binary mask for the brain tissue. This is performed for each subject. Multi-atlas considered is the one located at the global variable root_atlas :return: """ for atlas_sj in defs.multi_atlas_subjects: print('Creating brain tissue for subject {} in NI multi atlas '.format(atlas_sj)) pfi_segm = jph(defs.root_atlas, atlas_sj, 'segm', '{}_segm.nii.gz'.format(atlas_sj)) assert os.path.exists(pfi_segm) pfi_brain_tissue = jph(defs.root_atlas, atlas_sj, 'masks', '{}_brain_tissue.nii.gz'.format(atlas_sj)) print_and_run('cp {0} {1}'.format(pfi_segm, pfi_brain_tissue)) cmd = 'seg_maths {0} -bin {0}; ' \ 'seg_maths {0} -dil 1 {0}; ' \ 'seg_maths {0} -fill {0}; ' \ 'seg_maths {0} -ero 1 {0} '.format(pfi_brain_tissue) print_and_run(cmd)
def run_create_flipped_multi_atlas(phases): if phases[1]: # Phase 1) copy the atlas in the folder pfo_atlas_validation_leave_one_out cmd = 'mkdir {}'.format( path_manager.pfo_atlas_validation_leave_one_out) print_and_run(cmd) for d in os.listdir(path_manager.pfo_multi_atlas): if not d.startswith('.') and not d.startswith('z'): cmd = 'cp -r {} {}'.format( jph(path_manager.pfo_multi_atlas, d), path_manager.pfo_atlas_validation_leave_one_out) print cmd print_and_run(cmd) if phases[2]: # Phase 2) Flip the multi-atlas in the same folder. print(path_manager.atlas_subjects) print(path_manager.pfo_atlas_validation_leave_one_out) suffix_atlas = 'flip' dlm = LdM( jph(path_manager.pfo_atlas_validation_leave_one_out, 'labels_descriptor.txt')) flipper(path_manager.pfo_atlas_validation_leave_one_out, path_manager.atlas_subjects, suffix_atlas, dlm)
def get_list_pfi_images_3d_from_list_images_4d(list_pfi_4d_images, tp): list_new = [] for p in list_pfi_4d_images: p_new = p.replace('.nii.gz', '_tp{}.nii.gz'.format(tp)) cmd = 'seg_maths {0} -tp {1} {2}'.format(p, tp, p_new) print_and_run(cmd) list_new.append(p_new) return list_new
def delete_from_path(pfi_file_1, pfi_file_2): assert os.path.exists(pfi_file_1), pfi_file_1 cmd = 'rm -r {}'.format(pfi_file_1) print_and_run(cmd) if os.path.exists(pfi_file_2): cmd = 'rm -r {}'.format(pfi_file_2) print_and_run(cmd)
def merge_two_study_folders(pfo_main_study, pfo_secondary_study): """ Move from secondary study to main study with added suffix. :param pfo_main_study: :param pfo_secondary_study: :param suffix: :return: """ for name_to_be_moved in list(set(os.listdir(pfo_secondary_study)) - {'.DS_Store'}): name_after_move = name_to_be_moved cmd = 'mv {} {}'.format(jph(pfo_secondary_study, name_to_be_moved), jph(pfo_main_study, name_after_move)) print_and_run(cmd) print_and_run('rm -r {}'.format(pfo_secondary_study))
def stack_a_list_of_images_from_list_pfi(list_pfi, pfi_stack): for p in list_pfi: assert os.path.exists(p), p if len(list_pfi) == 1: cmd = 'cp {} {}'.format(list_pfi[0], pfi_stack) print_and_run(cmd) else: print('stack {0} in {1}'.format(list_pfi, pfi_stack)) pfi_first = list_pfi[0] num_images_to_merge = len(list_pfi) - 1 cmd = 'seg_maths {0} -merge {1} 4'.format(pfi_first, num_images_to_merge) for p in list_pfi[1:]: cmd += ' {0} '.format(p) cmd += ' {0} '.format(pfi_stack) print_and_run(cmd)
def adjust_affine_header(pfi_input, pfi_output, theta, trasl=np.array([0, 0, 0])): if theta != 0: # transformations parameters rot_x = np.array([[1, 0, 0, trasl[0]], [0, np.cos(theta), -np.sin(theta), trasl[1]], [0, np.sin(theta), np.cos(theta), trasl[2]], [0, 0, 0, 1]]) # Load input image: im_input = nib.load(pfi_input) # generate new affine transformation (from bicommissural to histological) new_transf = rot_x.dot(im_input.get_affine()) # create output image on the input if im_input.header['sizeof_hdr'] == 348: new_image = nib.Nifti1Image(im_input.get_data(), new_transf, header=im_input.get_header()) # if nifty2 elif im_input.header['sizeof_hdr'] == 540: new_image = nib.Nifti2Image(im_input.get_data(), new_transf, header=im_input.get_header()) else: raise IOError # print intermediate results print('Affine input image: \n') print(im_input.get_affine()) print('Affine after transformation: \n') print(new_image.get_affine()) # sanity check np.testing.assert_almost_equal(np.linalg.det(new_transf), np.linalg.det(im_input.get_affine())) # save output image nib.save(new_image, pfi_output) else: if not pfi_input == pfi_output: print_and_run('cp {0} {1}'.format(pfi_input, pfi_output))
def get_timepoint_by_path(pfi_im_input_4d, timepoint, pfi_output): """ :param pfi_im_input_4d: :param timepoint: :param pfi_output: :return: Handle base case: If the input 4d volume is actually a 3d and timepoint is 0, then just return the same input in the new file. """ im = nib.load(pfi_im_input_4d) shape_im_input = im.shape if timepoint == 0 and len(shape_im_input) == 3: cmd = 'cp {} {}'.format(pfi_im_input_4d, pfi_output) elif len(shape_im_input) == 4 and timepoint < shape_im_input[-1]: cmd = 'seg_maths {} -tp {} {}'.format(pfi_im_input_4d, timepoint, pfi_output) else: raise IOError print_and_run(cmd)
def squeeze_image_from_path(pfi_in, pfi_out, copy_anyway=False): """ copy the image in a new one with the dimension of the data squeezed. :param path_input_image: :param path_output_image: :param copy_anyway: if the image does not need to be squeezed, it is anyway copied in the path_output_image. Option that can be useful in some pipeline """ im = nib.load(pfi_in) print('Input image dimensions: {0}.'.format(str(im.shape))) if 1 in list(im.shape): new_im = set_new_data(im, np.squeeze(im.get_data()[:])) nib.save(new_im, pfi_out) print('New image dimensions: {0}, saved in {1}'.format( str(new_im.shape), str(pfi_out))) else: print('No need to squeeze the input image.') if copy_anyway: cmd = 'cp {0} {1} '.format(pfi_in, pfi_out) print_and_run(cmd) return 'Already squeezed image copied in {0} '.format(pfi_out)
def unzipper_given_pfi_input_and_pfo_output(pfi_in, pfo_out, sj_name, controller): """ Unzipper auxiliary function related to subject name and controller, with path established a priori. Externalised to avoid code repetitions, as called twice. :param pfi_in: path to .zip file input :param pfo_out: path to folder output where to unzip. :param sj_name: usual sj parameter :param controller: controller filetered from previous methods. :return: """ # Create folder structure: if controller['create_tmp_folder_structure']: print_and_run('mkdir -p {}'.format(pfo_out)) # Unzip: if controller['unzip']: cmd = 'tar -xvf {} -C {}'.format(pfi_in, pfo_out) print cmd print_and_run(cmd) # Rename: if controller['rename']: file_found = 0 for p in os.listdir(pfo_out): if '_HVDM_{}_'.format(sj_name) in p or '_{}_'.format( sj_name) in p or '_{}_{}_'.format(sj_name[:3], sj_name[3:]) in p: file_found += 1 pfi_unzipped_old_name = jph(pfo_out, p) pfi_unzipped_new_name = jph(pfo_out, sj_name) cmd = 'mv {} {}'.format(pfi_unzipped_old_name, pfi_unzipped_new_name) print_and_run(cmd) elif p == str(sj_name): # file is already in the correct format file_found += 1 if file_found != 1: raise IOError( 'Unzipped file was saved with a different naming convention. We found {} with no string {} in it. ' 'Manual work required. Check under folder {} (Probably two subjects with the same name? ' 'Probably different covention to save filenames?)'.format( file_found, '_{}_'.format(sj_name)), pfo_out) pfi_ds_store_mac = jph(pfo_out, sj_name, '.DS_Store') if os.path.exists(pfi_ds_store_mac): print_and_run('rm {}'.format(pfi_ds_store_mac))
def converter_given_pfo_input_and_pfo_output(pfo_input_sj, pfo_output, sj_name): """ Converter auxiliary function related to subject name and path to folder to convert and where to convert. Externalised to avoid code repetitions, as called twice. :param pfo_input_sj: input folder to convert :param pfo_output: input folder where to convert :param sj_name: usual sj parameter :return: """ print_and_run('mkdir -p {}'.format(pfo_output)) pfo_output_sj = jph(pfo_output, sj_name) if os.path.exists(pfo_output_sj): cmd = 'rm -r {}'.format(pfo_output_sj) print('Folder {} where to convert the study exists already... ERASED!'. format(pfo_output_sj)) print_and_run(cmd) conv = Bruker2Nifti(pfo_input_sj, pfo_output, study_name=sj_name) conv.correct_slope = True conv.verbose = 1 conv.convert()
def cluster_access_commands(username='******', command='to_cluster'): """ Copy to or from cluster :param username: :param command: can be 'to_cluster' or 'from_cluster' :return: """ root_probabilistic_atlas_cluster = jph(path_manager.pfo_root, 'A_probabilistic_atlas_on_cluster') if command == 'to_cluster': # copy folders Atlas to cluster cmd = 'scp -r {0} {1}:{2}'.format( path_manager.pfo_root_probabilistic_atlas, username, root_probabilistic_atlas_cluster) print_and_run(cmd) elif command == 'from_cluster': cmd = 'scp -r {0}:{1} {2} '.format( username, jph(root_probabilistic_atlas_cluster, 'groupwise_result'), jph(path_manager.pfo_root_probabilistic_atlas, 'groupwise_result')) print_and_run(cmd) else: raise IOError
def see_array(in_array, pfo_tmp='./z_tmp', in_array_segm=None, pfi_label_descriptor=None, block=False): """ Itk-snap based quick array visualiser. :param in_array: numpy array or list of numpy array same dimension (GIGO). :param pfo_tmp: path to file temporary folder. :param in_array_segm: if there is a single array representing a segmentation (in this case all images must have the same shape). :param pfi_label_descriptor: path to file to a label descriptor in ITK-snap standard format. :param block: if want to stop after each show. :return: """ if isinstance(in_array, list): assert len(in_array) > 0 sh = in_array[0].shape for arr in in_array[1:]: assert sh == arr.shape print_and_run('mkdir {}'.format(pfo_tmp)) cmd = 'itksnap -g ' for arr_id, arr in enumerate(in_array): im = nib.Nifti1Image(arr, affine=np.eye(4)) pfi_im = jph(pfo_tmp, 'im_{}.nii.gz'.format(arr_id)) nib.save(im, pfi_im) if arr_id == 1: cmd += ' -o {} '.format(pfi_im) else: cmd += ' {} '.format(pfi_im) elif isinstance(in_array, np.ndarray): print_and_run('mkdir {}'.format(pfo_tmp)) im = nib.Nifti1Image(in_array, affine=np.eye(4)) pfi_im = jph(pfo_tmp, 'im_0.nii.gz') nib.save(im, pfi_im) cmd = 'itksnap -g {}'.format(pfi_im) else: raise IOError if in_array_segm is not None: im_segm = nib.Nifti1Image(in_array_segm, affine=np.eye(4)) pfi_im_segm = jph(pfo_tmp, 'im_segm_0.nii.gz') nib.save(im_segm, pfi_im_segm) cmd += ' -s {} '.format(pfi_im_segm) if pfi_label_descriptor: if os.path.exists(pfi_label_descriptor): cmd += ' -l {} '.format(pfi_im_segm) print_and_run(cmd) if block: _ = raw_input("Press any key to continue.")
def affine_propagator(sp): """ Core of the propagation - affine part :param sp: instance of the class spot containing the parameters required for the cycle. :return: outcome of the affine registration """ if not sp.propagation_controller['Aff_alignment'] and not sp.propagation_controller['Propagate_aff_to_mask'] and \ not sp.propagation_controller['Propagate_aff_to_segm']: print('You asked to not do any affine alignment.') return pfo_tmp = sp.scaffoldings_pfo pfo_target_mod = jph(sp.target_pfo, sp.arch_modalities_name_folder) pfo_target_masks = jph(sp.target_pfo, sp.arch_masks_name_folder) # --- Prepare target affine -> Mono or Multi modal. num_modalities = len(sp.propagation_options['Affine_modalities']) # Creating fixed input after options selections: pfi_target_mod = jph(pfo_tmp, 'target_aff_{}_mod.nii.gz'.format(sp.target_name)) pfi_target_reg_mask = jph( pfo_tmp, 'target_aff_{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[1])) pfi_target_reg_mask_SLIM = jph( pfo_tmp, 'target_aff_{0}_{1}_SLIM.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[2])) # STACK modalities: pfi_target_mod_list = [ jph(pfo_target_mod, '{0}_{1}.nii.gz'.format(sp.target_name, m)) for m in sp.propagation_options['Affine_modalities'] ] utils.stack_a_list_of_images_from_list_pfi(pfi_target_mod_list, pfi_target_mod) # Prepare STACK reg masks: if not sp.propagation_options['Affine_reg_masks']: pfi_target_reg_mask_list = [ jph( pfo_target_masks, '{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[1])) for _ in range(num_modalities) ] else: assert len(sp.propagation_options['Affine_modalities']) == len( sp.propagation_options['Affine_reg_masks']) pfi_target_reg_mask_list = [ jph( pfo_target_masks, '{0}_{1}_{2}.nii.gz'.format(sp.target_name, m, sp.arch_suffix_masks[1])) for m in sp.propagation_options['Affine_reg_masks'] ] # STACK the images in a single outpout. (even if affine mask is required, do it anyway as it may be useful # in the no-rigid step and trials) utils.stack_a_list_of_images_from_list_pfi(pfi_target_reg_mask_list, pfi_target_reg_mask) # if required Prepare the slim mask for the first modalities - Target: if (sp.propagation_options['Affine_slim_reg_mask'] or sp.propagation_options['N_rigid_slim_reg_mask']) and \ (sp.propagation_controller['Get_affine_slim_mask'] or sp.propagation_controller['Get_N_rigid_slim_mask']): pfi_target_brain_mask = jph( pfo_target_masks, '{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[2])) utils.prepare_slim_mask_from_path_to_stack(pfi_target_reg_mask, pfi_target_brain_mask, pfi_target_reg_mask_SLIM) for sj in sp.atlas_list_charts_names: pfo_sj_mod = jph(sp.atlas_pfo, sj, sp.arch_modalities_name_folder) pfo_sj_masks = jph(sp.atlas_pfo, sj, sp.arch_masks_name_folder) pfo_sj_segm = jph(sp.atlas_pfo, sj, sp.arch_segmentations_name_folder) # prepare sj atlas source -> Mono / Multi modal. suffix_reg = '{}_on_target_{}'.format(sj, sp.target_name) # Output: pfi_moving_sj_mod = jph(pfo_tmp, 'moving_aff_{}_mod.nii.gz'.format(sj)) pfi_moving_sj_reg_mask = jph( pfo_tmp, 'moving_aff_{}_{}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) pfi_moving_sj_reg_mask_SLIM = jph( pfo_tmp, 'moving_aff_{0}_{1}_SLIM.nii.gz'.format(sj, sp.arch_suffix_masks[2])) # Modalities: pfi_sj_list_mod = [ jph(pfo_sj_mod, '{0}_{1}.nii.gz'.format(sj, m)) for m in sp.propagation_options['Affine_modalities'] ] utils.stack_a_list_of_images_from_list_pfi(pfi_sj_list_mod, pfi_moving_sj_mod) # Registration masks: # if not sp.propagation_options['Affine_reg_masks']: # pfi_sj_list_reg_masks = [jph(pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) for _ in range(num_modalities)] # else: # pfi_sj_list_reg_masks = [jph(pfo_sj_masks, '{0}_{1}_{2}.nii.gz'.format(sj, mod, sp.arch_suffix_masks[1])) for mod in sp.propagation_options['Affine_reg_masks']] # This version template there is only one reg mask for each modality. pfi_sj_list_reg_masks = [ jph(pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) for _ in range(num_modalities) ] utils.stack_a_list_of_images_from_list_pfi(pfi_sj_list_reg_masks, pfi_moving_sj_reg_mask) # if required Prepare the slim mask for the first modalities - SUBJECT: if (sp.propagation_options['Affine_slim_reg_mask'] or sp.propagation_options['N_rigid_slim_reg_mask']) and \ (sp.propagation_controller['Get_affine_slim_mask'] or sp.propagation_controller['Get_N_rigid_slim_mask']): pfi_sj_brain_mask = jph( pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[2])) utils.prepare_slim_mask_from_path_to_stack( pfi_moving_sj_reg_mask, pfi_sj_brain_mask, pfi_moving_sj_reg_mask_SLIM) if sp.propagation_controller['Aff_alignment']: print('Affine alignment, subject {}'.format(sj)) for p in [ pfi_target_mod, pfi_target_reg_mask, pfi_moving_sj_mod, pfi_moving_sj_reg_mask ]: assert os.path.exists(p), p # OUTPUT: pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) pfi_moving_sj_on_target_aff_warp = jph( pfo_tmp, 'moving_aff_warp_{}_mod.nii.gz'.format(suffix_reg)) # Command: if sp.propagation_options['Affine_slim_reg_mask']: cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -fmask {3} -aff {4} -res {5} -omp {6} {7}'.format( pfi_target_mod, pfi_target_reg_mask_SLIM, pfi_moving_sj_mod, pfi_moving_sj_reg_mask_SLIM, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_warp, sp.num_cores_run, sp.propagation_options['Affine_parameters']) else: cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -fmask {3} -aff {4} -res {5} -omp {6} {7}'.format( pfi_target_mod, pfi_target_reg_mask, pfi_moving_sj_mod, pfi_moving_sj_reg_mask, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_warp, sp.num_cores_run, sp.propagation_options['Affine_parameters']) # Run print_and_run(cmd) if sp.propagation_controller['Propagate_aff_to_mask']: print('Affine alignment, mask propagation subject {}'.format(sj)) # -> AFFINE transformation: pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans # -> ROI mask pfi_moving_sj_roi_mask = jph( pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[0])) assert os.path.exists( pfi_moving_sj_roi_mask), pfi_moving_sj_roi_mask pfi_moving_sj_on_target_aff_roi_mask_warp = jph( pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format(suffix_reg, sp.arch_suffix_masks[0])) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_target_mod, pfi_moving_sj_roi_mask, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_roi_mask_warp) print_and_run(cmd) # -> REG masks list_modalities = list( set(sp.propagation_options['Affine_reg_masks']) & set(sp.propagation_options['N_rigid_reg_masks'])) if not list_modalities: pfi_moving_sj_reg_mask_mod = jph( pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) assert os.path.exists( pfi_moving_sj_reg_mask_mod), pfi_moving_sj_reg_mask_mod pfi_moving_sj_on_target_aff_reg_mask_warp = jph( pfo_tmp, 'moving_aff_warp_{0}_{1}.nii.gz'.format( suffix_reg, sp.arch_suffix_masks[1])) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_target_mod, pfi_moving_sj_reg_mask, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_reg_mask_warp) print_and_run(cmd) else: # for mod in list_modalities: # pfi_moving_sj_reg_mask_mod = jph(pfo_sj_masks, '{0}_{1}_{2}.nii.gz'.format(sj, mod, sp.arch_suffix_masks[1])) # assert os.path.exists(pfi_moving_sj_reg_mask_mod), pfi_moving_sj_reg_mask_mod # pfi_moving_sj_on_target_aff_reg_mask_warp = jph(pfo_tmp, 'moving_aff_warp_{0}_{1}_{2}.nii.gz'.format(sj, mod, sp.arch_suffix_masks[1])) # cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( # pfi_target_mod, pfi_moving_sj_reg_mask, # pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_reg_mask_warp) # print_and_run(cmd) # This version template there is only one reg mask for each modality. pfi_moving_sj_reg_mask_mod = jph( pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) assert os.path.exists( pfi_moving_sj_reg_mask_mod), pfi_moving_sj_reg_mask_mod pfi_moving_sj_on_target_aff_reg_mask_warp = jph( pfo_tmp, 'moving_aff_warp_{0}_{1}.nii.gz'.format( suffix_reg, sp.arch_suffix_masks[1])) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_target_mod, pfi_moving_sj_reg_mask, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_reg_mask_warp) print_and_run(cmd) # -> BRAIN masks if any. SLIM mask for the non-rigid step will be reconstructed in the non-rigid step. if sp.propagation_options[ 'Affine_slim_reg_mask'] or sp.propagation_options[ 'N_rigid_slim_reg_mask']: pfi_moving_sj_brain_mask = jph( pfo_sj_masks, '{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[2])) assert os.path.exists( pfi_moving_sj_brain_mask), pfi_moving_sj_brain_mask pfi_moving_sj_on_target_aff_brain_mask_warp = jph( pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format( suffix_reg, sp.arch_suffix_masks[2])) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_target_mod, pfi_moving_sj_roi_mask, pfi_moving_sj_on_target_aff_trans, pfi_moving_sj_on_target_aff_brain_mask_warp) print_and_run(cmd) if sp.propagation_controller['Propagate_aff_to_segm']: # -> AFFINE transformation: print( 'Affine alignment, segmentation propagation subject {}'.format( sj)) pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans # -> Segmentation pfi_segm_sj = jph( pfo_sj_segm, '{0}_{1}.nii.gz'.format(sj, sp.atlas_segmentation_suffix)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans pfi_segm_sj_on_target_aff = jph( pfo_tmp, 'segm_moving_aff_warp_{}.nii.gz'.format(suffix_reg)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_target_mod, pfi_segm_sj, pfi_moving_sj_on_target_aff_trans, pfi_segm_sj_on_target_aff) print_and_run(cmd)
def process_T2_map_per_subject(sj, controller): print('\nProcessing T2 map {} started.\n'.format(sj)) # parameters file sanity check: if sj not in list_all_subjects(pfo_subjects_parameters): raise IOError('Subject parameters not known. Subject {}'.format(sj)) sj_parameters = pickle.load(open(jph(pfo_subjects_parameters, sj), 'r')) study = sj_parameters['study'] category = sj_parameters['category'] pfo_input_sj_MSME = jph(root_study_rabbits, '02_nifti', study, category, sj, sj + '_MSME') pfo_output_sj = jph(root_study_rabbits, 'A_data', study, category, sj) pfo_mod = jph(pfo_output_sj, 'mod') # input sanity check: if not os.path.exists(pfo_input_sj_MSME): print('MSME modality not given in the input folder after Nifti conversion. Bypass methods involving MSME') return if not os.path.exists(pfo_output_sj): raise IOError('Output folder MSME does not exist.') if not os.path.exists(pfo_mod): raise IOError('Output folder MSME does not exist.') # -- Generate intermediate and output folder pfo_tmp = jph(pfo_output_sj, 'z_tmp', 'z_T2map') print_and_run('mkdir -p {}'.format(pfo_tmp)) suffix = ['', 'inS0'] if controller['get_acquisition_echo_time']: pfi_visu_pars = jph(pfo_input_sj_MSME, sj + '_MSME_visu_pars.npy') assert check_path_validity(pfi_visu_pars) pfi_echo_times = jph(pfo_tmp, sj + '_echo_times.txt') visu_pars_dict = np.load(pfi_visu_pars) np.savetxt(fname=pfi_echo_times, X=visu_pars_dict.item().get('VisuAcqEchoTime'), fmt='%10.2f', newline=' ') if controller['process_each_MSME_input']: pfi_echo_times = jph(pfo_tmp, '{}_echo_times.txt'.format(sj)) assert os.path.exists(pfi_echo_times) TE = np.loadtxt(pfi_echo_times) echo_delta = TE[2] - TE[1] # original for s in suffix: pfi_original_MSME = jph(pfo_mod, '{}_MSME{}.nii.gz'.format(sj, s)) check_path_validity(pfi_original_MSME) pfi_T2map = jph(pfo_tmp, '{}_T2map{}.nii.gz'.format(sj, s)) cmd1 = root_fit_apps + 'fit_qt2 -source {0} -TE {1} -t2map {2}'.format(pfi_original_MSME, echo_delta, pfi_T2map) print cmd1 print_and_run(cmd1) if controller['correct_origin']: # some versions of niftyfit for fit_qt2 are dividing by 0 in the origin. for s in suffix: pfi_T2map = jph(pfo_tmp, sj + '_T2map{}.nii.gz'.format(s)) check_path_validity(pfi_T2map) pfi_T2map_corrected = jph(pfo_tmp, sj + '_corrected_T2map{}.nii.gz'.format(s)) # clean upper outliers (Mean + 2 * StandardDeviation) ... They are more than outliers! im_s = nib.load(pfi_T2map) places_not_outliers = im_s.get_data() < 1000 # np.mean(im_s.get_data()) + 2 * np.std(im_s.get_data()) im_s.get_data()[:] = places_not_outliers * im_s.get_data() im_corrected = set_new_data(im_s, places_not_outliers * im_s.get_data()) nib.save(im_corrected, pfi_T2map_corrected) if controller['save_results']: # Save the bias field corrected '', and '_up' in the name _T2map and _T2map_up for s in suffix: pfi_source = jph(pfo_tmp, sj + '_corrected_T2map{}.nii.gz'.format(s)) pfi_destination = jph(pfo_mod, sj + '_T2map.nii.gz') cmd = 'cp {0} {1}'.format(pfi_source, pfi_destination) print_and_run(cmd)
def extract_brain_tissue_from_multi_atlas_list_stereotaxic(target_name, multi_atlas_list, pfo_tmp, pfi_output_brain_mask, options): """ :param target_name: :param multi_atlas_list: :param pfo_tmp: :param pfi_output_brain_mask: :param options: :return: """ # controller: affine_only = True nrig_options = ' -be 0.98 -jl 0.5 ' steps = {'register' : True, 'propagate' : True, 'stack' : True, 'fuse' : True} assert os.path.exists(pfo_tmp) # parameters target: sj_parameters = pickle.load(open(jph(defs.pfo_subjects_parameters, target_name), 'r')) study = sj_parameters['study'] category = sj_parameters['category'] # input target: root_target_sj = jph(defs.root_study_rabbits, 'A_data', study, category, target_name) pfi_target_sj_T1 = jph(root_target_sj, 'stereotaxic', 'mod', '{}_T1.nii.gz'.format(target_name)) pfi_target_sj_reg_mask = jph(root_target_sj, 'stereotaxic', 'masks', '{}_T1_reg_mask.nii.gz'.format(target_name)) assert os.path.exists(pfi_target_sj_T1), pfi_target_sj_T1 assert os.path.exists(pfi_target_sj_reg_mask), pfi_target_sj_reg_mask # list of final intermediate output: list_pfi_brain_mask_registered_on_target = [] list_pfi_T1_registered_on_target = [] for atlas_sj in multi_atlas_list: # input selected atlas_sj if atlas_sj in defs.multi_atlas_subjects: root_atlas_sj = jph(defs.root_atlas, atlas_sj) pfi_atlas_sj_T1 = jph(root_atlas_sj, 'mod', '{}_T1.nii.gz'.format(atlas_sj)) pfi_atlas_sj_reg_mask = jph(root_atlas_sj, 'masks', '{}_reg_mask.nii.gz'.format(atlas_sj)) pfi_atlas_sj_brain_mask = jph(root_atlas_sj, 'masks', '{}_brain_mask.nii.gz'.format(atlas_sj)) elif atlas_sj in defs.multi_atlas_BT_subjects: root_atlas_name_BT = jph(defs.root_atlas_BT, atlas_sj) pfi_atlas_sj_T1 = jph(root_atlas_name_BT, '{}_T1.nii.gz'.format(atlas_sj)) pfi_atlas_sj_reg_mask = jph(root_atlas_name_BT, '{}_reg_mask.nii.gz'.format(atlas_sj)) pfi_atlas_sj_brain_mask = jph(root_atlas_name_BT, '{}_brain_mask.nii.gz'.format(atlas_sj)) else: raise IOError('Subject {} is not in a known or provided multi-atlas.'.format(atlas_sj)) assert os.path.exists(pfi_atlas_sj_T1), pfi_atlas_sj_T1 assert os.path.exists(pfi_atlas_sj_reg_mask), pfi_atlas_sj_reg_mask assert os.path.exists(pfi_atlas_sj_brain_mask), pfi_atlas_sj_brain_mask # intermediate output: AFFINE pfi_affine_transformation_ref_on_subject = jph(pfo_tmp, 'target{}_floating{}_aff_transformation.txt'.format(target_name, atlas_sj)) pfi_affine_warped_ref_on_subject = jph(pfo_tmp, 'target{}_floating{}_aff_warped.nii.gz'.format(target_name, atlas_sj)) # AFFINE step cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -fmask {3} -aff {4} -res {5} -omp {6} -speeeeed '.format( pfi_target_sj_T1, pfi_target_sj_reg_mask, pfi_atlas_sj_T1, pfi_atlas_sj_reg_mask, pfi_affine_transformation_ref_on_subject, pfi_affine_warped_ref_on_subject, defs.num_cores_run) if steps['register']: print_and_run(cmd) pfi_final_transformation = pfi_affine_transformation_ref_on_subject # intermediate output: NON-RIGID pfi_nrig_cpp_ref_on_subject = jph(pfo_tmp, 'target{}_floating{}_nrigid_cpp.nii.gz'.format(target_name, atlas_sj)) pfi_nrig_warped_ref_on_subject = jph(pfo_tmp, 'target{}_floating{}_nrigid_warped.nii.gz'.format(target_name, atlas_sj)) # NON-RIGID step if not affine_only: cmd = 'reg_f3d -ref {0} -rmask {1} -flo {2} -fmask {3} -aff {4} -cpp {5} -res {6} {7} -omp {8}'.format( pfi_target_sj_T1, pfi_target_sj_reg_mask, pfi_atlas_sj_T1, pfi_atlas_sj_reg_mask, pfi_affine_transformation_ref_on_subject, pfi_nrig_cpp_ref_on_subject, pfi_nrig_warped_ref_on_subject, nrig_options, defs.num_cores_run) if steps['register']: print_and_run(cmd) pfi_final_transformation = pfi_nrig_cpp_ref_on_subject print('- Propagate registration to brain tissue mask, subject {0} over the target {1}'.format( atlas_sj, target_name)) # Output brain tissue after affine trasformation, must include the atlas_sj name in the naming. pfi_brain_tissue_from_multi_atlas_sj = jph(pfo_tmp, 'target{0}_floating{1}_final_warped_brain_mask.nii.gz'.format( target_name, atlas_sj)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_target_sj_T1, pfi_atlas_sj_brain_mask, pfi_final_transformation, pfi_brain_tissue_from_multi_atlas_sj) if steps['propagate']: print_and_run(cmd) # Append path to output files ot the respective lists. list_pfi_brain_mask_registered_on_target.append(pfi_brain_tissue_from_multi_atlas_sj) if affine_only: list_pfi_T1_registered_on_target.append(pfi_affine_warped_ref_on_subject) else: list_pfi_T1_registered_on_target.append(pfi_nrig_warped_ref_on_subject) print('\n- Create stack of the brain masks warped over the target {} and merge with MV. '.format(target_name)) pfi_stack_brain_mask = jph(pfo_tmp, 'a_stack_brain_tissues_target{0}_multiAtlas{1}.nii.gz'.format( target_name, options['method'])) pfi_stack_T1 = jph(pfo_tmp, 'a_stack_T1_target{0}_multiAtlas{1}.nii.gz'.format( target_name, options['method'])) if steps['stack']: # Create stack of warped brain mask nis_app = nis.App() nis_app.manipulate_shape.stack_list_pfi_images(list_pfi_brain_mask_registered_on_target, pfi_stack_brain_mask) del nis_app # Create stack of warped T1 nis_app = nis.App() nis_app.manipulate_shape.stack_list_pfi_images(list_pfi_T1_registered_on_target, pfi_stack_T1) del nis_app if steps['fuse']: print('\n\n-Labels Fusion') # merge the roi masks in one (Majority voting for now): cmd = 'seg_LabFusion -in {0} -out {1} -MV '.format(pfi_stack_brain_mask, pfi_output_brain_mask) # cmd = 'seg_LabFusion -in {0} -STEPS 3 5 {1} {2} -out {3}'.format(pfi_stack_brain_mask, pfi_target_sj_T1, # pfi_stack_T1, pfi_output_brain_mask) print_and_run(cmd)
def create_brain_tissue_multi_atlas(sj_list, controller): for sj in sj_list: print('Adding subject {} to brain tissue multi atlas. \n'.format(sj)) sj_parameters = pickle.load(open(jph(defs.pfo_subjects_parameters, sj), 'r')) study = sj_parameters['study'] category = sj_parameters['category'] root_sj = jph(defs.root_study_rabbits, 'A_data', study, category, sj) assert os.path.exists(root_sj) # input data: pfi_T1_sj = jph(root_sj, 'mod', '{}_T1.nii.gz'.format(sj)) pfi_T1_segm = jph(root_sj, 'segm', '{}_T1_segm.nii.gz'.format(sj)) # copy to destination (BT = brain tissue multi atlas): root_sj_BT = jph(defs.root_atlas_BT, sj) if controller['Delete_first']: print_and_run('rm -r {}'.format(root_sj_BT), short_path_output=False) print_and_run('mkdir -p {}'.format(root_sj_BT)) pfi_T1_sj_BT = jph(root_sj_BT, '{}_T1.nii.gz'.format(sj)) pfi_brain_tissue_sj_BT = jph(root_sj_BT, '{}_brain_tissue.nii.gz'.format(sj)) print_and_run('cp {0} {1}'.format(pfi_T1_sj, pfi_T1_sj_BT)) print_and_run('cp {0} {1}'.format(pfi_T1_segm, pfi_brain_tissue_sj_BT)) # Elaborate data in destination: # -- from segmentation to brain tissue: cmd = 'seg_maths {0} -bin {0}; ' \ 'seg_maths {0} -dil 1 {0}; ' \ 'seg_maths {0} -fill {0}; ' \ 'seg_maths {0} -ero 1 {0} '.format(pfi_brain_tissue_sj_BT) print_and_run(cmd) # -- from brain tissue to roi mask (dilated of the brain tissue): pfi_roi_mask_BT = jph(root_sj_BT, '{}_roi_mask.nii.gz'.format(sj)) cmd1 = 'cp {} {}'.format(pfi_brain_tissue_sj_BT, pfi_roi_mask_BT) print_and_run(cmd1) cmd2 = 'seg_maths {0} -dil 3 {0}'.format(pfi_roi_mask_BT) print_and_run(cmd2)
def test_print_and_run_create_file_safety_on(): cmd = 'touch {}'.format(jph(test_dir, 'z_tmp_test', 'tmp.txt')) output_msg = print_and_run(cmd, safety_on=True) assert not os.path.exists(jph(test_dir, 'z_tmp_test', 'tmp.txt')) assert output_msg == 'touch tmp.txt'
def binarise_and_adjust_mask_from_segmentation_path(pfi_segm_input, pfi_mask_output, pfo_temp, subject_name, labels_to_exclude=(), dil_factor=1, ero_factor=1): """ Sequence of topological operation to pass from the manual segmentation to a single binary mask covering the brain tissue and excluding the skull. :param pfi_segm_input: :param pfi_mask_output: :param pfo_temp: :param subject_name: :param labels_to_exclude: :param dil_factor: dilation factor before erosion :param ero_factor: erosion factor after dilation :return: """ pfi_intermediate = jph(pfo_temp, '{}_tmp_binarisation.nii.gz'.format(subject_name)) print_and_run('cp {} {}'.format(pfi_segm_input, pfi_intermediate)) if len(labels_to_exclude) > 0: im_segm = nib.load(pfi_intermediate) array_segm_new_data = relabeller(im_segm.get_data(), list_old_labels=labels_to_exclude, list_new_labels=[ 0, ] * len(labels_to_exclude)) im_segm_new = set_new_data(im_segm, array_segm_new_data) nib.save(im_segm_new, pfi_intermediate) print_and_run('seg_maths {0} -bin {0}'.format(pfi_intermediate)) # fill and dil the binarised segmentation print_and_run('seg_maths {0} -fill {1}'.format(pfi_intermediate, pfi_intermediate)) print_and_run('seg_maths {0} -dil {1} {0}'.format(pfi_intermediate, dil_factor)) print_and_run('seg_maths {0} -ero {1} {0}'.format(pfi_intermediate, ero_factor)) # print_and_run('seg_maths {0} -fill {0}'.format(pfi_intermediate)) print_and_run('seg_maths {0} -fill {1}'.format(pfi_intermediate, pfi_mask_output))
def orient2std(pfi_in, pfi_out, keep_translation=True): """ As different modalities are not oriented in the same space when converted and as fslorient2std affects only the s-form and not the q-form. 1) apply fslorient2std 2) set translational part to zero 3) use nibabel to set the s-form as the q-form :param pfi_in: :param pfi_out: :param keep_translation: if False translation is set to zero. :return: """ # assert os.path.exists(pfi_in) # pfi_intermediate = os.path.join(os.path.dirname(pfi_out), 'zz_tmp_' + os.path.basename(pfi_in)) # # 1 -- # cmd0 = 'fslreorient2std {0} {1}'.format(pfi_in, pfi_intermediate) # print_and_run(cmd0) # # 2 -- # set_translational_part_to_zero(pfi_intermediate, pfi_intermediate) # # 3 -- # im = nib.load(pfi_intermediate) # im.set_sform(im.get_qform()) # nib.save(im, pfi_out) # os.system('rm {}'.format(pfi_intermediate)) # New version pfi_intermediate = os.path.join(os.path.dirname(pfi_out), 'zz_tmp_' + os.path.basename(pfi_in)) # 1 -- cmd0 = 'fslreorient2std {0} {1}'.format(pfi_in, pfi_intermediate) print_and_run(cmd0) # for rounding problems re-do the computation of the diagonal elements. see subject 3404 # set the translational part to zero in this part as well. im_input = nib.load(pfi_intermediate) aff = np.copy(im_input.affine) new_aff = np.eye(4) for c in range(3): new_aff[c, c] = np.linalg.norm(aff[:, c]) if keep_translation: new_aff[:-1, 3] = aff[:-1, 3] # create output image on the input if im_input.header['sizeof_hdr'] == 348: new_image = nib.Nifti1Image(im_input.get_data(), new_aff, header=im_input.header) # if nifty2 elif im_input.header['sizeof_hdr'] == 540: new_image = nib.Nifti2Image(im_input.get_data(), new_aff, header=im_input.header) else: raise IOError # print intermediate results print 'Affine input image: \n' print im_input.affine print 'Affine after transformation: \n' print new_image.affine # save output image nib.save(new_image, pfi_out) os.system('rm {}'.format(pfi_intermediate))
def spot_a_list_of_rabbits(subjects_list): for sj_target in subjects_list: print( '\nAutomatic segmentation with SPOT-A-NeonatalRabbit - subject {} started.\n' .format(sj_target)) sj_parameters = pickle.load( open(jph(pfo_subjects_parameters, sj_target), 'r')) study = sj_parameters['study'] category = sj_parameters['category'] pfo_target = jph(root_study_rabbits, 'A_data', study, category, sj_target, 'stereotaxic') # Parameter tag z-SPOT_<TAG> if study == 'W8': parameters_tag = 'P3' multi_atlas_subjects_list = multi_atlas_W8_subjects pfo_sj_atlas = jph(root_study_rabbits, 'A_MultiAtlas_W8', sj_target) root_multi_atlas = root_atlas_W8 elif study == 'ACS' or study == 'PTB' or study == 'TestStudy': parameters_tag = 'P2' multi_atlas_subjects_list = multi_atlas_subjects pfo_sj_atlas = jph(root_study_rabbits, 'A_MultiAtlas', sj_target) root_multi_atlas = root_atlas else: raise IOError( 'Study for subject {} not feasible.'.format(sj_target)) # parameters_tag = 'P2' if sj_parameters['in_atlas']: # SPOT only the rabbits not already in the atlas. print( 'Subject {} already in atlas. No automatic segmentation needed' .format(sj_target)) pfi_T1_segm_from_atlas = jph(pfo_sj_atlas, 'segm', '{}_segm.nii.gz'.format(sj_target)) assert os.path.exists(pfi_T1_segm_from_atlas) cmd0 = 'mkdir -p {}'.format(jph(pfo_target, 'segm')) cmd1 = 'cp {} {}'.format( pfi_T1_segm_from_atlas, jph(pfo_target, 'segm', '{}_segm.nii.gz'.format(sj_target))) print_and_run(cmd0) print_and_run(cmd1) return # --- initialise the class spot: spot_sj = SpotDS(atlas_pfo=root_multi_atlas, target_pfo=pfo_target, target_name=sj_target, parameters_tag=parameters_tag) """ Parameters tag -> correspondence: 'P1' -> Mono modal T1 + BFC on T1. 'P2' -> Multi modal T1 affine only. """ # Template parameters: spot_sj.atlas_name = 'MANRround3' # Multi Atlas Newborn Rabbit spot_sj.atlas_list_charts_names = multi_atlas_subjects_list spot_sj.atlas_list_suffix_modalities = ['T1', 'S0', 'V1', 'MD', 'FA'] spot_sj.atlas_list_suffix_masks = [ 'roi_mask', 'roi_reg_mask', 'brain_mask' ] spot_sj.atlas_segmentation_suffix = 'segm' # Architecture names - default 'automatic'. spot_sj.arch_automatic_segmentations_name_folder = sj_parameters[ 'names_architecture']['final_segm_strx'] # --- target parameters spot_sj.target_list_suffix_modalities = ['T1', 'S0', 'V1', 'MD', 'FA'] spot_sj.target_name = sj_target # --- Utils spot_sj.bfc_corrector_cmd = bfc_corrector_cmd spot_sj.num_cores_run = num_cores_run if sj_parameters['options_brain_mask']['method'] is None: use_slim_mask = False else: use_slim_mask = True if sj_parameters['category'] == 'ex_vivo' or sj_parameters[ 'category'] == 'ex_vivo01' or sj_parameters[ 'category'] == 'ex_vivo02': # --- Propagator option spot_sj.atlas_reference_chart_name = '1305' spot_sj.propagation_options['Affine_modalities'] = ('T1', 'FA') spot_sj.propagation_options['Affine_reg_masks'] = ( 'T1', 'S0') # if (), there is a single mask for all modalities spot_sj.propagation_options['Affine_parameters'] = ' -speeeeed ' spot_sj.propagation_options['Affine_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_modalities'] = ( ) # ('T1', 'FA') # if empty, no non-rigid step. spot_sj.propagation_options['N_rigid_reg_masks'] = ( ) #('T1', 'S0') # if [], same mask for all modalities spot_sj.propagation_options[ 'N_rigid_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_mod_diff_bfc'] = ( 'T1', ) # empty list no diff bfc. - PUT A COMMA IF ONLY ONE SUBJECT!! spot_sj.propagation_options[ 'N_rigid_parameters'] = ' -be 0.9 -ln 6 -lp 1 -smooR 0.07 -smooF 0.07 ' spot_sj.propagation_options['N_rigid_same_mask_moving'] = False spot_sj.propagation_options[ 'N_reg_mask_target'] = 0 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options[ 'N_reg_mask_moving'] = 1 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options['Final_smoothing_factor'] = 0 elif sj_parameters['category'] == 'in_vivo': # --- Propagator option spot_sj.atlas_reference_chart_name = '1305' spot_sj.propagation_options['Affine_modalities'] = ('T1', ) spot_sj.propagation_options['Affine_reg_masks'] = ( 'T1', ) # if (), there is a single mask for all modalities spot_sj.propagation_options['Affine_parameters'] = ' -speeeeed ' spot_sj.propagation_options['Affine_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_modalities'] = ( ) # if empty, no non-rigid step. - first attempt with only an affine step. spot_sj.propagation_options['N_rigid_reg_masks'] = ( ) # if [], same mask for all modalities spot_sj.propagation_options[ 'N_rigid_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_mod_diff_bfc'] = ( ) # empty list no diff bfc. - PUT A COMMA IF ONLY ONE SUBJECT!! spot_sj.propagation_options[ 'N_rigid_parameters'] = ' -be 0.9 -ln 6 -lp 1 -smooR 0.07 -smooF 0.07 ' spot_sj.propagation_options['N_rigid_same_mask_moving'] = False spot_sj.propagation_options[ 'N_reg_mask_target'] = 0 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options[ 'N_reg_mask_moving'] = 1 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options['Final_smoothing_factor'] = 1 elif sj_parameters['category'] == 'first_trial' or sj_parameters[ 'category'] == 'second_trial' or sj_parameters[ 'category'] == 'third_trial': # --- Propagator option spot_sj.atlas_reference_chart_name = '12503' spot_sj.propagation_options['Affine_modalities'] = ('T1', 'FA') spot_sj.propagation_options['Affine_reg_masks'] = ( 'T1', 'S0') # if (), there is a single mask for all modalities spot_sj.propagation_options['Affine_parameters'] = ' -speeeeed ' spot_sj.propagation_options['Affine_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_modalities'] = ( 'T1', ) # if empty, no non-rigid step. spot_sj.propagation_options['N_rigid_reg_masks'] = ( 'T1', ) # if [], same mask for all modalities spot_sj.propagation_options[ 'N_rigid_slim_reg_mask'] = use_slim_mask spot_sj.propagation_options['N_rigid_mod_diff_bfc'] = ( ) # empty list no diff bfc. - PUT A COMMA EVEN IF ONLY ONE SUBJECT!! spot_sj.propagation_options[ 'N_rigid_parameters'] = ' -be 0.8 -vel -smooR 0.07 -smooF 0.07 ' spot_sj.propagation_options['N_rigid_same_mask_moving'] = False spot_sj.propagation_options[ 'N_reg_mask_target'] = 0 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options[ 'N_reg_mask_moving'] = 1 # 0 roi_mask, 1 reg_mask spot_sj.propagation_options['Final_smoothing_factor'] = 0 else: raise IOError( 'Given subject category not recognised for subject {} and category {}.' .format(sj_target, sj_parameters['category'])) # --- Propagator controller spot_sj.propagation_controller['Aff_alignment'] = True spot_sj.propagation_controller['Propagate_aff_to_segm'] = True spot_sj.propagation_controller['Propagate_aff_to_mask'] = True spot_sj.propagation_controller['Get_N_rigid_slim_mask'] = True spot_sj.propagation_controller['Get_differential_BFC'] = True spot_sj.propagation_controller['N_rigid_alignment'] = True spot_sj.propagation_controller['Propagate_n_rigid'] = True spot_sj.propagation_controller['Smooth_results'] = True spot_sj.propagation_controller['Stack_warps_and_segms'] = True # --- Fuser option spot_sj.fuser_options['Fusion_methods'] = [ 'MV', 'STAPLE', 'STEPS', ] # ['STAPLE', 'STEPS', ] # 'STAPLE', 'STEPS' spot_sj.fuser_options['STAPLE_params'] = OrderedDict([('pr1', None)]) spot_sj.fuser_options['STEPS_params'] = OrderedDict([ ('pr{0}.{1}'.format(k, n), [k, n, 4]) for n in [9] for k in [5, 11] ]) # --- Fuser controller spot_sj.fuser_controller['Fuse'] = True spot_sj.fuser_controller['Save_results'] = True spot_sj.spot_on_target_initialise() t = time.time() spot_sj.propagate() spot_sj.fuse() elapsed = time.time() - t print('Time to spot subject {} is : {}'.format(sj_target, elapsed))
def fuser(sp): print('Apply the nifty-seg fusion method {}'.format(sp.target_pfo)) pfo_tmp = sp.scaffoldings_pfo assert os.path.exists(pfo_tmp) if sp.fuser_controller['Fuse']: print('- Fuse {} '.format(sp.target_name)) # file-names and file-paths of the resulting stacks: fin_stack_segm = '{0}_stack_warp_segm_{1}.nii.gz'.format( sp.target_name, sp.parameters_tag) fin_stack_warp = '{0}_stack_warp_mod_{1}.nii.gz'.format( sp.target_name, sp.parameters_tag) pfi_4d_stack_warp_segm = jph(pfo_tmp, fin_stack_segm) pfi_4d_stack_warp_mod = jph(pfo_tmp, fin_stack_warp) assert os.path.exists(pfi_4d_stack_warp_segm) assert os.path.exists(pfi_4d_stack_warp_mod) # ------------ MV ------------ pfi_output_MV = jph( pfo_tmp, 'result_{0}_MV_{1}.nii.gz'.format(sp.target_name, sp.parameters_tag)) if 'MV' in sp.fuser_options['Fusion_methods']: cmd_mv = 'seg_LabFusion -in {0} -out {1} -MV'.format( pfi_4d_stack_warp_segm, pfi_output_MV) print_and_run(cmd_mv, short_path_output=False) assert check_path_validity(pfi_output_MV, timeout=5000, interval=5) # -------- STAPLE ------------ if 'STAPLE' in sp.fuser_options['Fusion_methods']: for key_staple in sp.fuser_options['STAPLE_params'].keys(): pfi_output_STAPLE = jph( pfo_tmp, 'result_{0}_STAPLE_{1}_{2}.nii.gz'.format( sp.target_name, key_staple, sp.parameters_tag)) beta = sp.fuser_options['STAPLE_params'][key_staple] if beta is None: cmd_staple = 'seg_LabFusion -in {0} -STAPLE -out {1}'.format( pfi_4d_stack_warp_segm, pfi_output_STAPLE) else: cmd_staple = 'seg_LabFusion -in {0} -STAPLE -out {1} -MRF_beta {2}'.format( pfi_4d_stack_warp_segm, pfi_output_STAPLE, beta) print_and_run(cmd_staple, short_path_output=False) assert check_path_validity(pfi_output_STAPLE, timeout=5000, interval=5) # ------------ STEPS ------------ if 'STEPS' in sp.fuser_options['Fusion_methods']: # select the path to target: if len(sp.propagation_options['N_rigid_modalities']) > 0: if len(sp.propagation_options['N_rigid_mod_diff_bfc']) > 0: pfi_target = jph( pfo_tmp, 'target_nrigid_{}_mod_BFC.nii.gz'.format( sp.target_name)) else: pfi_target = jph( pfo_tmp, 'target_nrigid_{}_mod.nii.gz'.format(sp.target_name)) else: pfi_target = sp.propagation_options[ 'N_rigid_modalities'] = jph( pfo_tmp, 'target_aff_{}_mod.nii.gz'.format(sp.target_name)) assert os.path.exists(pfi_target) for key_steps in sp.fuser_options['STEPS_params'].keys(): pfi_output_STEPS = jph( pfo_tmp, 'result_{0}_STEPS_{1}_{2}.nii.gz'.format( sp.target_name, key_steps, sp.parameters_tag)) k, n, beta = sp.fuser_options['STEPS_params'][key_steps] if beta is None: cmd_steps = 'seg_LabFusion -in {0} -out {1} -STEPS {2} {3} {4} {5} -prop_update'.format( pfi_4d_stack_warp_segm, pfi_output_STEPS, k, n, pfi_target, pfi_4d_stack_warp_mod) else: cmd_steps = 'seg_LabFusion -in {0} -out {1} -STEPS {2} {3} {4} {5} -MRF_beta {5} -prop_update '.\ format(pfi_4d_stack_warp_segm, pfi_output_STEPS, k, n, pfi_target, pfi_4d_stack_warp_mod, str(beta)) print_and_run(cmd_steps, short_path_output=False) assert check_path_validity(pfi_output_STEPS, timeout=1000, interval=10) if sp.fuser_controller['Save_results']: print('- save result for target subject {}'.format(sp.target_name)) pfo_automatic_segmentations_results = jph( sp.target_pfo, sp.arch_segmentations_name_folder, sp.arch_automatic_segmentations_name_folder) cmd0 = 'mkdir -p {}'.format( jph(sp.target_pfo, sp.arch_segmentations_name_folder)) cmd1 = 'mkdir -p {}'.format(pfo_automatic_segmentations_results) print_and_run(cmd0) print_and_run(cmd1) for filename in os.listdir(pfo_tmp): if filename.startswith('result_'): cmd = 'cp {0} {1}'.format( jph(pfo_tmp, filename), jph(pfo_automatic_segmentations_results, filename.replace('result_', ''))) print_and_run(cmd)
def non_rigid_propagator(sp): """ Core of the propagation - non-rigid part :param sp: instance of the class Spot. :return: outcome of the non-rigid registration """ pfo_tmp = sp.scaffoldings_pfo pfo_target_mod = jph(sp.target_pfo, sp.arch_modalities_name_folder) pfo_target_masks = jph(sp.target_pfo, sp.arch_masks_name_folder) # --- Prepare target non-rigid -> Mono or Multi modal. num_modalities = len(sp.propagation_options['N_rigid_modalities']) # Creating fixed input after options selections: pfi_target_mod = jph(pfo_tmp, 'target_nrigid_{}_mod.nii.gz'.format(sp.target_name)) pfi_target_reg_mask = jph( pfo_tmp, 'target_nrigid_{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[1])) pfi_target_reg_mask_SLIM = jph( pfo_tmp, 'target_nrigid_{0}_{1}_SLIM.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[2])) # STACK modalities: pfi_target_mod_list = [ jph(pfo_target_mod, '{0}_{1}.nii.gz'.format(sp.target_name, m)) for m in sp.propagation_options['N_rigid_modalities'] ] utils.stack_a_list_of_images_from_list_pfi(pfi_target_mod_list, pfi_target_mod) # Prepare STACK reg masks: if not sp.propagation_options['N_rigid_reg_masks']: pfi_target_reg_mask_list = [ jph( pfo_target_masks, '{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[1])) for _ in range(num_modalities) ] else: assert len(sp.propagation_options['N_rigid_modalities']) == len( sp.propagation_options['N_rigid_reg_masks']) pfi_target_reg_mask_list = [ jph( pfo_target_masks, '{0}_{1}_{2}.nii.gz'.format(sp.target_name, m, sp.arch_suffix_masks[1])) for m in sp.propagation_options['N_rigid_reg_masks'] ] # STACK utils.stack_a_list_of_images_from_list_pfi(pfi_target_reg_mask_list, pfi_target_reg_mask) # If required Prepare the slim mask for the first modalities - Target: if sp.propagation_options[ 'N_rigid_slim_reg_mask'] and sp.propagation_controller[ 'Get_N_rigid_slim_mask']: pfi_target_brain_mask = jph( pfo_target_masks, '{0}_{1}.nii.gz'.format(sp.target_name, sp.arch_suffix_masks[2])) utils.prepare_slim_mask_from_path_to_stack(pfi_target_reg_mask, pfi_target_brain_mask, pfi_target_reg_mask_SLIM) for sj in sp.atlas_list_charts_names: # --- input subject folders pfo_sj_mod = jph(sp.atlas_pfo, sj, sp.arch_modalities_name_folder) pfo_sj_masks = jph(sp.atlas_pfo, sj, sp.arch_masks_name_folder) # ---- prepare sj atlas source -> Mono / Multi modal. suffix_reg = '{}_on_target_{}'.format(sj, sp.target_name) moving_suffix_mask = sp.arch_suffix_masks[ sp.propagation_options['N_reg_mask_moving']] # Output: pfi_moving_nrigid_sj_mod = jph( pfo_tmp, 'moving_nrigid_{}_mod.nii.gz'.format(suffix_reg)) pfi_moving_nrigid_sj_reg_mask = jph( pfo_tmp, 'moving_nrigid_{}_{}.nii.gz'.format(suffix_reg, moving_suffix_mask)) pfi_moving_nrigid_sj_reg_mask_SLIM = jph( pfo_tmp, 'moving_nrigid_{0}_{1}_SLIM.nii.gz'.format( sj, sp.arch_suffix_masks[2])) # Modalities: # -- warp not yet warped sj modalities if any. if cmp(sp.propagation_options['N_rigid_modalities'], sp.propagation_options['Affine_modalities']): # > stack the modalities: pfi_target_mod_list = [ jph(pfo_sj_mod, '{0}_{1}.nii.gz'.format(sj, m)) for m in sp.propagation_options['N_rigid_modalities'] ] utils.stack_a_list_of_images_from_list_pfi( pfi_target_mod_list, pfi_moving_nrigid_sj_mod) # > warp the stacked modalities pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans cmd = 'reg_resample -ref {0} -flo {0} -trans {1} -res {0} '.format( pfi_moving_nrigid_sj_mod, pfi_moving_sj_on_target_aff_trans) print_and_run(cmd) else: # > copy the warped mod from affine registration: pfi_moving_sj_on_target_aff_warp = jph( pfo_tmp, 'moving_aff_warp_{}_mod.nii.gz'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_warp) cmd = 'cp {} {}'.format(pfi_moving_sj_on_target_aff_warp, pfi_moving_nrigid_sj_mod) print_and_run(cmd) # Masks: if cmp(sp.propagation_options['N_rigid_reg_masks'], sp.propagation_options['Affine_reg_masks']): # > stack the masks: pfi_target_masks_list = [ jph( pfo_sj_masks, '{0}_{1}_{2}.nii.gz'.format(sj, m, sp.arch_suffix_masks[1])) for m in sp.propagation_options['N_rigid_reg_masks'] ] for p in pfi_target_masks_list: assert os.path.exists(p), p utils.stack_a_list_of_images_from_list_pfi( pfi_target_masks_list, pfi_moving_nrigid_sj_reg_mask) # > warp the stacked masks: pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans cmd = 'reg_resample -ref {0} -flo {0} -trans {1} -res {0} '.format( pfi_moving_nrigid_sj_reg_mask, pfi_moving_sj_on_target_aff_trans) print_and_run(cmd) if sp.propagation_options['N_rigid_slim_reg_mask']: # > stack the masks: pfi_target_masks_list_SLIM = [ jph( pfo_sj_masks, '{0}_{1}_{2}.nii.gz'.format(sj, m, sp.arch_suffix_masks[2])) for m in sp.propagation_options['N_rigid_reg_masks'] ] utils.stack_a_list_of_images_from_list_pfi( pfi_target_masks_list_SLIM, pfi_moving_nrigid_sj_reg_mask_SLIM) # > warp the stacked masks: pfi_moving_sj_on_target_aff_trans = jph( pfo_tmp, 'aff_trans_{}.txt'.format(suffix_reg)) assert os.path.exists(pfi_moving_sj_on_target_aff_trans ), pfi_moving_sj_on_target_aff_trans cmd = 'reg_resample -ref {0} -flo {0} -trans {1} -res {0} '.format( pfi_moving_nrigid_sj_reg_mask_SLIM, pfi_moving_sj_on_target_aff_trans) print_and_run(cmd) else: # Just copy the masks warped in the previous step. pfi_moving_sj_on_target_aff_warp_mask = jph( pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format(suffix_reg, moving_suffix_mask)) assert os.path.exists(pfi_moving_sj_on_target_aff_warp_mask) cmd = 'cp {} {}'.format(pfi_moving_sj_on_target_aff_warp_mask, pfi_moving_nrigid_sj_reg_mask) print_and_run(cmd) if sp.propagation_options['N_rigid_slim_reg_mask']: pfi_moving_sj_on_target_aff_warp_mask_SLIM = jph( pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format( suffix_reg, moving_suffix_mask)) assert os.path.exists( pfi_moving_sj_on_target_aff_warp_mask_SLIM) cmd = 'cp {} {}'.format( pfi_moving_sj_on_target_aff_warp_mask_SLIM, pfi_moving_nrigid_sj_reg_mask_SLIM) print_and_run(cmd) # Masks: are all already warped form the affine step - create the stack # if not sp.propagation_options['N_rigid_reg_masks']: # pfi_sj_list_reg_masks = [jph(pfo_tmp, 'moving_aff_warp_{0}_{1}.nii.gz'.format(sj, sp.arch_suffix_masks[1])) for _ in range(num_modalities)] # else: # pfi_sj_list_reg_masks = [jph(pfo_tmp, 'moving_aff_warp_{0}_{1}_{2}.nii.gz'.format(sj, mod, sp.arch_suffix_masks[1])) for mod in sp.propagation_options['N_rigid_reg_masks']] # This version template there is only one reg mask for each modality. # pfi_sj_list_reg_masks = [jph(pfo_tmp, 'moving_aff_warp_{0}_{1}.nii.gz'.format(suffix_reg, sp.arch_suffix_masks[1])) for _ in range(num_modalities)] # utils.stack_a_list_of_images_from_list_pfi(pfi_sj_list_reg_masks, pfi_moving_nrigid_sj_reg_mask) # # # if required Prepare the slim mask for the first modalities - SUBJECT: # if sp.propagation_options['N_rigid_slim_reg_mask'] and sp.propagation_controller['Get_N_rigid_slim_mask']: # pfi_moving_sj_on_target_aff_brain_mask_warp = jph(pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format(suffix_reg, sp.arch_suffix_masks[2])) # utils.prepare_slim_mask_from_path_to_stack(pfi_moving_nrigid_sj_reg_mask, pfi_moving_sj_on_target_aff_brain_mask_warp, pfi_moving_nrigid_sj_reg_mask_SLIM) if len(sp.propagation_options['N_rigid_mod_diff_bfc'] ) > 0 and sp.propagation_controller['Get_differential_BFC']: # Final output: pfi_target_mod_BFC = jph( pfo_tmp, 'target_nrigid_{}_mod_BFC.nii.gz'.format(sp.target_name)) pfi_moving_nrigid_mod_BFC = jph( pfo_tmp, 'moving_nrigid_{}_mod_BFC.nii.gz'.format(suffix_reg)) # Copy non-bfc as output to be modified cmd = 'cp {} {}'.format(pfi_target_mod, pfi_target_mod_BFC) print_and_run(cmd) cmd = 'cp {} {}'.format(pfi_moving_nrigid_sj_mod, pfi_moving_nrigid_mod_BFC) print_and_run(cmd) for bfc_mod in sp.propagation_options['N_rigid_mod_diff_bfc']: timepoint = sp.propagation_options['N_rigid_modalities'].index( bfc_mod) # Get target slice at timepoint pfi_bfc_target_mod_slice = jph( pfo_tmp, 'bfc_slice_target_{0}_{1}.nii.gz'.format( sp.target_name, bfc_mod)) utils.get_timepoint_by_path(pfi_target_mod, timepoint, pfi_bfc_target_mod_slice) # Get target mask slice at timepoint pfi_bfc_target_reg_mask_slice = jph( pfo_tmp, 'bfc_slice_target_{0}_{1}_mask.nii.gz'.format( sp.target_name, bfc_mod)) utils.get_timepoint_by_path(pfi_target_reg_mask, timepoint, pfi_bfc_target_reg_mask_slice) # Get moving at timepoint pfi_bfc_moving_mod_slice = jph( pfo_tmp, 'bfc_slice_moving_{0}_{1}.nii.gz'.format( suffix_reg, bfc_mod)) utils.get_timepoint_by_path(pfi_moving_nrigid_sj_mod, timepoint, pfi_bfc_moving_mod_slice) # Get moving mask at timepoint pfi_bfc_moving_reg_mask_slice = jph( pfo_tmp, 'bfc_slice_moving_{0}_{1}_mask.nii.gz'.format( suffix_reg, bfc_mod)) if sp.propagation_options['N_rigid_slim_reg_mask']: pfi_moving_aff_mask = pfi_moving_nrigid_sj_reg_mask_SLIM else: pfi_moving_aff_mask = pfi_moving_nrigid_sj_reg_mask assert os.path.exists(pfi_moving_aff_mask) utils.get_timepoint_by_path(pfi_moving_aff_mask, timepoint, pfi_bfc_moving_reg_mask_slice) # Output pfi_diff_bfc_target = jph( pfo_tmp, 'bfc_{0}.nii.gz'.format(sp.target_name)) pfi_diff_bfc_subject = jph(pfo_tmp, 'bfc_{0}.nii.gz'.format(suffix_reg)) cmd = sp.bfc_corrector_cmd + ' {0} {1} {2} {3} {4} {5} '.format( pfi_bfc_target_mod_slice, pfi_bfc_target_reg_mask_slice, pfi_diff_bfc_target, pfi_bfc_moving_mod_slice, pfi_bfc_moving_reg_mask_slice, pfi_diff_bfc_subject) print_and_run(cmd) # Integrate the partial BFC output in the final output - target utils.substitute_volume_at_timepoint_by_path( pfi_target_mod_BFC, pfi_diff_bfc_target, timepoint, pfi_target_mod_BFC) utils.substitute_volume_at_timepoint_by_path( pfi_moving_nrigid_mod_BFC, pfi_diff_bfc_subject, timepoint, pfi_moving_nrigid_mod_BFC) if sp.propagation_controller['N_rigid_alignment']: print('Non-rigid alignment, subject {}'.format(sj)) # Input target_mod = pfi_target_mod target_mask = pfi_target_reg_mask target_mask_SLIM = pfi_target_reg_mask_SLIM moving_mod = pfi_moving_nrigid_sj_mod moving_mask = pfi_moving_nrigid_sj_reg_mask moving_mask_SLIM = pfi_moving_nrigid_sj_reg_mask_SLIM if len(sp.propagation_options['N_rigid_mod_diff_bfc']) > 0: target_mod = jph( pfo_tmp, 'target_nrigid_{}_mod_BFC.nii.gz'.format(sp.target_name)) moving_mod = jph( pfo_tmp, 'moving_nrigid_{}_mod_BFC.nii.gz'.format(suffix_reg)) if sp.propagation_options['N_rigid_slim_reg_mask']: moving_mask = pfi_moving_nrigid_sj_reg_mask_SLIM assert os.path.exists(target_mod) assert os.path.exists(target_mask) assert os.path.exists(moving_mod) assert os.path.exists(moving_mask) if sp.propagation_options['N_rigid_same_mask_moving']: target_mask = moving_mask # Output pfi_cpp_nrigid_warp = jph( pfo_tmp, 'cpp_nrigid_warp_{}.nii.gz'.format(suffix_reg)) pfi_mod_nrigid_warp = jph( pfo_tmp, 'moving_nrigid_warp_{}_mod.nii.gz'.format(suffix_reg)) if sp.propagation_options['N_rigid_slim_reg_mask']: cmd = 'reg_f3d -ref {0} -rmask {1} -flo {2} -fmask {3} -cpp {4} -res {5} -omp {6} {7}'.format( target_mod, target_mask_SLIM, moving_mod, moving_mask_SLIM, pfi_cpp_nrigid_warp, pfi_mod_nrigid_warp, sp.num_cores_run, sp.propagation_options['N_rigid_parameters']) else: # Command cmd = 'reg_f3d -ref {0} -rmask {1} -flo {2} -fmask {3} -cpp {4} -res {5} -omp {6} {7}'.format( target_mod, target_mask, moving_mod, moving_mask, pfi_cpp_nrigid_warp, pfi_mod_nrigid_warp, sp.num_cores_run, sp.propagation_options['N_rigid_parameters']) print_and_run(cmd) if sp.propagation_controller['Propagate_n_rigid']: pfi_cpp_nrigid_warp = jph( pfo_tmp, 'cpp_nrigid_warp_{}.nii.gz'.format(suffix_reg)) assert os.path.exists(pfi_cpp_nrigid_warp) # Propagate to reg_mask affine transformed: pfi_moving_sj_on_target_aff_mask_warp = jph( pfo_tmp, 'moving_aff_warp_{}_{}.nii.gz'.format(suffix_reg, moving_suffix_mask)) assert os.path.exists(pfi_moving_sj_on_target_aff_mask_warp) pfi_reg_mask_sj_on_target_nrigid_warp = jph( pfo_tmp, 'moving_nrigid_warp_{}_reg_mask.nii.gz'.format(suffix_reg)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_target_mod, pfi_moving_sj_on_target_aff_mask_warp, pfi_cpp_nrigid_warp, pfi_reg_mask_sj_on_target_nrigid_warp) print_and_run(cmd) # Propagate to segm affine transformed: pfi_segm_sj_on_target_aff_warp = jph( pfo_tmp, 'segm_moving_aff_warp_{}.nii.gz'.format(suffix_reg)) assert os.path.exists( pfi_segm_sj_on_target_aff_warp), pfi_segm_sj_on_target_aff_warp pfi_segm_sj_on_target_nrigid = jph( pfo_tmp, 'segm_moving_nrigid_warp_{}.nii.gz'.format(suffix_reg)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_target_mod, pfi_segm_sj_on_target_aff_warp, pfi_cpp_nrigid_warp, pfi_segm_sj_on_target_nrigid) print_and_run(cmd)
def test_print_and_run_create_file_safety_off(): cmd = 'touch {}'.format(jph(test_dir, 'z_tmp_test', 'tmp.txt')) output_msg = print_and_run(cmd, safety_on=False, short_path_output=False) assert os.path.exists(jph(test_dir, 'z_tmp_test', 'tmp.txt')) assert output_msg == 'touch {}'.format( jph(test_dir, 'z_tmp_test', 'tmp.txt'))
def run_probabilistic_atlas_generator(commands, options): # Atlas data (input) - only the atlas, the label descriptor leading_modality = 'T1' pfi_labels_descriptor = jph(path_manager.pfo_multi_atlas, 'labels_descriptor.txt') # Probabilistic Atlas output if options['Bimodal']: pfo_subjects = jph(path_manager.pfo_root_probabilistic_atlas, 'subjects_bimodal') pfo_masks = jph(path_manager.pfo_root_probabilistic_atlas, 'masks_bimodal') else: pfo_subjects = jph(path_manager.pfo_root_probabilistic_atlas, 'subjects') pfo_masks = jph(path_manager.pfo_root_probabilistic_atlas, 'masks') pfo_all_segmentations = jph(path_manager.pfo_root_probabilistic_atlas, 'all_segm') pfo_tmp = jph(path_manager.pfo_root_probabilistic_atlas, 'z_tmp') pfo_pa_results = jph(path_manager.pfo_root_probabilistic_atlas, 'a_results') # most important # --- Main folder probabilistic atlas: print_and_run('mkdir {}'.format(path_manager.pfo_root_probabilistic_atlas)) if commands['Create_structure']: for p in [ pfo_subjects, pfo_masks, pfo_all_segmentations, pfo_pa_results, pfo_tmp ]: print_and_run('mkdir -p {}'.format(p)) # prepare folders structure and folder segmentations if commands['Prepare_data_in_folder_structure']: assert os.path.exists(pfo_all_segmentations) assert os.path.exists(pfo_tmp) for sj in path_manager.atlas_subjects: pfi_leading_mod = jph( path_manager.pfo_multi_atlas, sj, 'mod', '{0}_{1}.nii.gz'.format(sj, leading_modality)) pfi_segm = jph(path_manager.pfo_multi_atlas, sj, 'segm', '{0}_segm.nii.gz'.format(sj)) assert os.path.exists(pfi_leading_mod), pfi_leading_mod assert os.path.exists(pfi_segm), pfi_segm # ---- SEGMENTATION - just copy in the adequate folder --- pfi_segm_for_p_atlas = jph(pfo_all_segmentations, '{0}_segm.nii.gz'.format(sj)) print_and_run('cp {0} {1}'.format(pfi_segm, pfi_segm_for_p_atlas)) # ---- MASK AS BINARISED SEGMENTATION --- pfi_brain_mask = jph(pfo_tmp, '{0}_brain_tissue.nii.gz'.format(sj)) binarise_and_adjust_mask_from_segmentation_path( pfi_segm_input=pfi_segm_for_p_atlas, pfi_mask_output=pfi_brain_mask, pfo_temp=pfo_tmp, subject_name=sj, labels_to_exclude=[ 201, ]) # copy the obtained mask in the final masks folder, ready to create the probabilistic atlas. pfi_brain_mask_for_p_atlas = jph(pfo_masks, '{0}_mask.nii.gz'.format(sj)) print_and_run('cp {0} {1}'.format(pfi_brain_mask, pfi_brain_mask_for_p_atlas)) # ---- MAIN MODALITY --- # Trim: pfi_leading_mod_trimmed = jph( pfo_tmp, '{0}_{1}_trimmed.nii.gz'.format(sj, leading_modality)) print_and_run('seg_maths {0} -mul {1} {2}'.format( pfi_leading_mod, pfi_brain_mask_for_p_atlas, pfi_leading_mod_trimmed)) if options['Bimodal']: # prepare segmentation to be set in the second channel pfi_segm_prepared_for_second_channel = jph( pfo_tmp, '{}_segm_giraffe_skin.nii.gz'.format(sj)) prepare_mask_eroded_contour_from_segmentation_path( pfi_segm_for_p_atlas, pfi_segm_prepared_for_second_channel, pfo_tmp) # create stack mask and copy in the final folder: - will overwrite pfi_brain_mask_for_p_atlas pfi_stack_mask = jph( pfo_masks, '{0}_mask.nii.gz'.format(sj) ) # maks bimodal - will overwrite pfi_brain_mask_for_p_atlas cmd = 'seg_maths {0} -merge 1 4 {1} {2}'.format( pfi_brain_mask_for_p_atlas, pfi_brain_mask_for_p_atlas, pfi_stack_mask) print_and_run(cmd) # create stack modalities and copy in the final folder: pfi_stack_T1 = jph( pfo_subjects, '{}_bimodal.nii.gz'.format(sj)) # pfo_subject_bimodal cmd = 'seg_maths {0} -merge 1 4 {1} {2}'.format( pfi_leading_mod_trimmed, pfi_segm_prepared_for_second_channel, pfi_stack_T1) print_and_run(cmd) else: pfi_leading_mod_final = jph( pfo_subjects, '{0}_{1}.nii.gz'.format(sj, leading_modality)) print_and_run('cp {0} {1}'.format(pfi_leading_mod_trimmed, pfi_leading_mod_final)) pass if commands['Create_probabilistic_atlas']: here = os.path.dirname(os.path.realpath(__file__)) pfi_niftiyreg_run = jph(here, 'local_groupwise_niftyreg_run.sh') if options['Bimodal']: pfi_niftiyreg_param = jph( here, 'local_groupwise_niftyreg_params_bimodal.sh') cmd = 'cd {0}; ./groupwise_niftyreg_run.sh groupwise_niftyreg_params_bimodal.sh; cd {1}'.format( path_manager.pfo_root_probabilistic_atlas, here) else: pfi_niftiyreg_param = jph(here, 'local_groupwise_niftyreg_params.sh') cmd = 'cd {0}; ./groupwise_niftyreg_run.sh groupwise_niftyreg_params.sh; cd {1}'.format( path_manager.pfo_root_probabilistic_atlas, here) print_and_run('cp {0} {1}'.format( pfi_niftiyreg_run, jph(path_manager.pfo_root_probabilistic_atlas, 'groupwise_niftyreg_run.sh'))) if options['Bimodal']: print_and_run('cp {0} {1}'.format( pfi_niftiyreg_param, jph(path_manager.pfo_root_probabilistic_atlas, 'groupwise_niftyreg_params_bimodal.sh'))) else: print_and_run('cp {0} {1}'.format( pfi_niftiyreg_param, jph(path_manager.pfo_root_probabilistic_atlas, 'groupwise_niftyreg_params.sh'))) print_and_run(cmd) # Apply transformations obtained to create the probabilistic atlas global mask and average the results: if commands['Warp_anatomical']: # IMPORTANT!! This must be manually set and coherent with the content of the .sh params files # --- parameters: # number of affine loop to perform [for the paper 7] AFF_IT_NUM = 7 # number of non-rigid loop to perform [for the paper 7] NRR_IT_NUM = 7 if options['Bimodal']: results_folder = 'results_bimodal' subjects_folder = 'subjects_bimodal' masks_folder = 'masks_bimodal' mod_suffix = 'bimodal' else: results_folder = 'results' subjects_folder = 'subjects' masks_folder = 'masks' mod_suffix = 'T1' # suffix according to the study number (should indicate number of iterations and mono/multi) suffix_result = 'aff{0}nrig{1}'.format(AFF_IT_NUM, NRR_IT_NUM) # ---- pipeline: # copy and rename the results of the groupwise registration pfi_result_groupwise = jph( path_manager.pfo_root_probabilistic_atlas, results_folder, 'nrr_{}'.format(NRR_IT_NUM), 'average_nonrigid_it_{}.nii.gz'.format(NRR_IT_NUM)) assert os.path.exists(pfi_result_groupwise), pfi_result_groupwise pfi_result_groupwise_copy = jph( pfo_pa_results, 'PA_{0}_{1}.nii.gz'.format(mod_suffix, suffix_result)) cmd = 'seg_maths {0} -thr 0 {1}'.format(pfi_result_groupwise, pfi_result_groupwise_copy) print_and_run(cmd) # if multimodal, take only the first timepoint if results_folder == 'results_bimodal': pfi_result_groupwise_copy_tp1 = jph( pfo_pa_results, 'PA_T1_{0}_{1}_tp1.nii.gz'.format(mod_suffix, suffix_result)) cmd = 'seg_maths {0} -tp 0 {1}'.format( pfi_result_groupwise_copy, pfi_result_groupwise_copy_tp1) print_and_run(cmd) # resample each segmentation with the final transformation pfi_reference_image = jph(path_manager.pfo_root_probabilistic_atlas, subjects_folder, '1305_{}.nii.gz'.format(mod_suffix)) assert os.path.exists(pfi_reference_image), pfi_reference_image for sj in path_manager.atlas_subjects: print sj # Resample the segmentations. pfi_segmentation_sj = jph( path_manager.pfo_root_probabilistic_atlas, 'all_segm', '{}_segm.nii.gz'.format(sj)) pfi_sj_final_transformation = jph( path_manager.pfo_root_probabilistic_atlas, results_folder, 'nrr_{}'.format(NRR_IT_NUM), 'nrr_cpp_{0}_{1}_it{2}.nii.gz'.format(sj, mod_suffix, NRR_IT_NUM)) assert os.path.exists(pfi_segmentation_sj), pfi_segmentation_sj assert os.path.exists( pfi_sj_final_transformation), pfi_sj_final_transformation pfi_sj_warped_segmentation = jph( pfo_pa_results, 'segm_{0}_warped_on_average_atlas.nii.gz'.format(sj)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_reference_image, pfi_segmentation_sj, pfi_sj_final_transformation, pfi_sj_warped_segmentation) print_and_run(cmd) # Resample the Masks. pfi_mask_sj = jph(path_manager.pfo_root_probabilistic_atlas, masks_folder, '{0}_mask.nii.gz'.format(sj)) assert os.path.exists(pfi_mask_sj), pfi_mask_sj pfi_sj_warped_mask = jph( pfo_pa_results, 'mask_{0}_warped_on_average_atlas.nii.gz'.format(sj)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_reference_image, pfi_mask_sj, pfi_sj_final_transformation, pfi_sj_warped_mask) print_and_run(cmd) # ------------------------------------------------------------------------- # # Now we have the resulting warped segmentations and the probabilistic T1. # We can do some manipulations to have what we need: # ------------------------------------------------------------------------- # # We can generate an image with the probabilities for each label if commands['Create_probability_for_each_level']: if options['Bimodal']: subjects_folder = 'subjects_bimodal' mod_suffix = 'bimodal' else: subjects_folder = 'subjects' mod_suffix = 'T1' pfo_probabilities = jph(pfo_pa_results, 'probabilities') print_and_run('mkdir -p {}'.format(pfo_probabilities)) ldm = LdM(pfi_labels_descriptor) dict_labels = ldm.get_dict() for l in dict_labels.keys(): print '\nLabel {}'.format(l) pfi_prob_finding_label_l = jph(pfo_probabilities, 'prob_label_{}.nii.gz'.format(l)) # generate new empty data: pfi_reference_image = jph( path_manager.pfo_root_probabilistic_atlas, subjects_folder, '1305_{}.nii.gz'.format(mod_suffix)) assert os.path.exists(pfi_reference_image), pfi_reference_image im_ref = nib.load(pfi_reference_image) data_label_l = np.zeros_like(im_ref) # fill data_label_l with all the labels for sj in path_manager.atlas_subjects: print 'Subject {}'.format(sj) pfi_sj_warped_segmentation = jph( pfo_pa_results, 'segm_{0}_warped_on_average_atlas.nii.gz'.format(sj)) im_warp_segm_sj = nib.load(pfi_sj_warped_segmentation) where_l = im_warp_segm_sj.get_data() == l data_label_l = data_label_l + where_l.astype(np.float64) # normalise the filled labels: m = np.max(data_label_l) # in case the label is not present in the segmentation warn the user if m > 0: data_label_l = data_label_l / float(m) else: print 'Label {} not present in the segmentations'.format(l) im_prob_label_l = set_new_data(im_ref, data_label_l) nib.save(im_prob_label_l, pfi_prob_finding_label_l)
def process_MSME_per_subject(sj, controller): print('\nProcessing MSME, subject {} started.\n'.format(sj)) if sj not in list_all_subjects(pfo_subjects_parameters): raise IOError( 'Subject {} does not have a subject parameter ready.'.format(sj)) sj_parameters = pickle.load(open(jph(pfo_subjects_parameters, sj), 'r')) study = sj_parameters['study'] category = sj_parameters['category'] pfo_input_sj = jph(root_study_rabbits, '02_nifti', study, category, sj) pfo_output_sj = jph(root_study_rabbits, 'A_data', study, category, sj) if not os.path.exists(pfo_input_sj): raise IOError('Input folder Subject does not exist.') # -- Generate intermediate and output folders: pfo_mod = jph(pfo_output_sj, 'mod') pfo_segm = jph(pfo_output_sj, 'segm') pfo_mask = jph(pfo_output_sj, 'masks') pfo_tmp = jph(pfo_output_sj, 'z_tmp', 'z_MSME') print_and_run('mkdir -p {}'.format(pfo_output_sj)) print_and_run('mkdir -p {}'.format(pfo_mod)) print_and_run('mkdir -p {}'.format(pfo_segm)) print_and_run('mkdir -p {}'.format(pfo_mask)) print_and_run('mkdir -p {}'.format(pfo_tmp)) pfi_msme_nifti = jph(pfo_input_sj, sj + '_MSME', sj + '_MSME.nii.gz') if not os.path.exists(pfi_msme_nifti): print( 'MSME modality not given in the input folder after Nifti conversion. Bypass methods involving MSME' ) return if controller['squeeze']: print('- Processing MSME: squeeze {}'.format(sj)) assert os.path.exists(pfi_msme_nifti) pfi_msme = jph(pfo_tmp, sj + '_MSME.nii.gz') squeeze_image_from_path(pfi_msme_nifti, pfi_msme, copy_anyway=True) if controller['orient_to_standard']: print('- Processing MSME: orient to standard {}'.format(sj)) pfi_msme = jph(pfo_tmp, sj + '_MSME.nii.gz') assert check_path_validity(pfi_msme) cmd = 'fslreorient2std {0} {0}'.format(pfi_msme) print_and_run(cmd) set_translational_part_to_zero(pfi_msme, pfi_msme) if controller['extract_first_timepoint']: print('- Processing MSME: extract first layers {}'.format(sj)) pfi_msme = jph(pfo_tmp, sj + '_MSME.nii.gz') assert os.path.exists(pfi_msme) pfi_msme_original_first_layer = jph(pfo_tmp, sj + '_MSME_tp0.nii.gz') cmd0 = 'seg_maths {0} -tp 0 {1}'.format(pfi_msme, pfi_msme_original_first_layer) print_and_run(cmd0) if controller['register_tp0_to_S0']: print('- Processing MSME: create ficticious original MSME mask {}'. format(sj)) pfi_msme_original_first_layer = jph(pfo_tmp, sj + '_MSME_tp0.nii.gz') print('- Processing MSME: register tp0 to S0 {}'.format(sj)) pfi_s0 = jph(pfo_mod, sj + '_S0.nii.gz') pfi_s0_mask = jph(pfo_mask, sj + '_S0_roi_mask.nii.gz') pfi_msme_tp0 = jph(pfo_tmp, sj + '_MSME_tp0.nii.gz') assert os.path.exists(pfi_s0) assert os.path.exists(pfi_s0_mask) assert check_path_validity(pfi_msme_tp0) pfi_transf_msme_on_s0 = jph(pfo_tmp, sj + '_msme_on_S0_rigid.txt') pfi_warped_msme_on_s0 = jph(pfo_tmp, sj + '_MSME_tp0_up.nii.gz') cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -aff {3} -res {4} -omp {5} -rigOnly'.format( pfi_s0, pfi_s0_mask, pfi_msme_tp0, pfi_transf_msme_on_s0, pfi_warped_msme_on_s0, num_cores_run) print_and_run(cmd) if controller['register_msme_to_S0']: pfi_s0 = jph(pfo_mod, sj + '_S0.nii.gz') pfi_msme = jph(pfo_tmp, sj + '_MSME.nii.gz') pfi_transf_msme_on_s0 = jph(pfo_tmp, sj + '_msme_on_S0_rigid.txt') assert os.path.exists(pfi_s0) assert os.path.exists(pfi_msme) assert check_path_validity(pfi_transf_msme_on_s0) pfi_msme_upsampled = jph(pfo_tmp, sj + '_MSMEinS0.nii.gz') cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 1'.format( pfi_s0, pfi_msme, pfi_transf_msme_on_s0, pfi_msme_upsampled) print_and_run(cmd) if controller['get_mask_for_original_msme']: print('- Processing MSME: get mask for original msme:') # Start from the S0 mask (this will be saved as an extra mask as MSMEinS0 mask). pfi_s0_mask = jph(pfo_mask, '{}_S0_roi_mask.nii.gz'.format(sj)) pfi_warped_msme_on_s0 = jph(pfo_tmp, sj + '_MSME_tp0_up.nii.gz') assert os.path.exists(pfi_s0_mask), pfi_s0_mask assert os.path.exists(pfi_warped_msme_on_s0), pfi_warped_msme_on_s0 pfi_msme_up_lesion_mask = jph( pfo_tmp, '{}_msme_up_lesions_mask.nii.gz'.format(sj)) pfi_msme_up_reg_mask = jph(pfo_tmp, '{}_msme_up_reg_mask.nii.gz'.format(sj)) # Crop it properly to the MSMEinS0. percentile_lesion_mask_extractor( im_input_path=pfi_warped_msme_on_s0, im_output_path=pfi_msme_up_lesion_mask, im_mask_foreground_path=pfi_s0_mask, percentiles=(10, 98), safety_on=False) cmd = 'seg_maths {0} -sub {1} {2}'.format(pfi_s0_mask, pfi_msme_up_lesion_mask, pfi_msme_up_reg_mask) print_and_run(cmd) # Register MSMEinS0 with an approximative new mask over the original with no mask. pfi_msme_original_first_layer = jph(pfo_tmp, '{}_MSME_tp0.nii.gz'.format(sj)) pfi_msme_original_pre_mask = jph( pfo_tmp, '{}_MSME_tp0_pre_mask.nii.gz'.format(sj)) percentile_lesion_mask_extractor_only_from_image_path( pfi_msme_original_first_layer, pfi_msme_original_pre_mask, percentile_range=(30, 95)) # TODO, personal attribute? pfi_warped_msme_on_s0_back_on_msme = jph( pfo_tmp, '{}_warped_msme_on_s0_back_on_msme.nii.gz'.format(sj)) pfi_affine_msme_on_s0_back_on_msme = jph( pfo_tmp, '{}_affine_msme_on_s0_back_on_msme.txt'.format(sj)) cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -fmask {3} -res {4} -aff {5} -omp {6} -rigOnly'.format( pfi_msme_original_first_layer, pfi_msme_original_pre_mask, pfi_warped_msme_on_s0, pfi_s0_mask, pfi_warped_msme_on_s0_back_on_msme, pfi_affine_msme_on_s0_back_on_msme, num_cores_run) print_and_run(cmd) # Apply transformation to the S0 roi_mask and to S0 reg_mask for ma in ['roi_mask', 'reg_mask']: S0_mask = jph(pfo_mask, '{0}_S0_{1}.nii.gz'.format(sj, ma)) assert os.path.exists(S0_mask) MSME_mask = jph(pfo_mask, '{0}_MSME_{1}.nii.gz'.format(sj, ma)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( pfi_msme_original_first_layer, S0_mask, pfi_affine_msme_on_s0_back_on_msme, MSME_mask) print_and_run(cmd) # print('back-propagate the S0 mask on the MSME:') # pfi_aff = jph(pfo_tmp, sj + '_msme_on_S0_rigid.txt') # assert os.path.exists(pfi_aff) # # this very same transformation must be used to back propagate the segmentations! # pfi_inv_aff = jph(pfo_tmp, sj + '_S0_on_msmse_rigid.txt') # cmd0 = 'reg_transform -invAff {0} {1}'.format(pfi_aff, pfi_inv_aff) # print_and_run(cmd0) # pfi_S0_mask = jph(pfo_mask, sj + '_S0_roi_mask.nii.gz') # pfi_msme = jph(pfo_tmp, sj + '_MSME.nii.gz') # assert os.path.exists(pfi_S0_mask) # assert os.path.exists(pfi_msme) # pfi_mask_on_msme = jph(pfo_mask, sj + '_MSME_roi_mask.nii.gz') # cmd1 = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0'.format( # pfi_msme, pfi_S0_mask, pfi_inv_aff, pfi_mask_on_msme) # print_and_run(cmd1) # print('Dilate:') # assert check_path_validity(pfi_mask_on_msme) # dil_factor = 0 # cmd0 = 'seg_maths {0} -dil {1} {2}'.format(pfi_mask_on_msme, dil_factor, pfi_mask_on_msme) # print_and_run(cmd0) if controller['bfc']: print('- get bfc correction each slice:') pfi_msme_original = jph(pfo_tmp, sj + '_MSME.nii.gz') assert check_path_validity(pfi_msme_original) print('-- un-pack slices') im = nib.load(pfi_msme_original) tps = im.shape[-1] for tp in range(tps): pfi_tp = jph(pfo_tmp, sj + '_MSME_tp{}.nii.gz'.format(tp)) cmd0 = 'seg_maths {0} -tp {1} {2}'.format(pfi_msme_original, tp, pfi_tp) print_and_run(cmd0) print('-- bias-field correct the first slice') # bfc_param = subject[sj][3] bfc_param = [0.001, (50, 50, 50, 50), 0.15, 0.01, 400, (4, 4, 4), 3] pfi_tp0 = jph(pfo_tmp, sj + '_MSME_tp0.nii.gz') pfi_tp0_bfc = jph(pfo_tmp, sj + '_MSME_tp0_bfc.nii.gz') pfi_mask_on_msme = jph(pfo_mask, sj + '_MSME_roi_mask.nii.gz') assert os.path.exists(pfi_mask_on_msme) bias_field_correction(pfi_tp0, pfi_tp0_bfc, pfi_mask=pfi_mask_on_msme, prefix='', convergenceThreshold=bfc_param[0], maximumNumberOfIterations=bfc_param[1], biasFieldFullWidthAtHalfMaximum=bfc_param[2], wienerFilterNoise=bfc_param[3], numberOfHistogramBins=bfc_param[4], numberOfControlPoints=bfc_param[5], splineOrder=bfc_param[6], print_only=False) print('-- get the bias field from the bfc corrected') bias_field = jph(pfo_tmp, sj + '_bfc.nii.gz') cmd0 = 'seg_maths {0} -div {1} {2}'.format(pfi_tp0_bfc, pfi_tp0, bias_field) cmd1 = 'seg_maths {0} -removenan {0}'.format(bias_field) print_and_run(cmd0) print_and_run(cmd1) assert check_path_validity(bias_field) print('-- correct all the remaining slices') for tp in range(1, tps): pfi_tp = jph(pfo_tmp, sj + '_MSME_tp{}.nii.gz'.format(tp)) pfi_tp_bfc = jph(pfo_tmp, sj + '_MSME_tp{}_bfc.nii.gz'.format(tp)) cmd0 = 'seg_maths {0} -mul {1} {2}'.format(pfi_tp, bias_field, pfi_tp_bfc) print_and_run(cmd0) check_path_validity(pfi_tp_bfc) print('-- pack together all the images in a stack') cmd = 'seg_maths {0} -merge {1} {2} '.format(pfi_tp0_bfc, tps - 1, 4) for tp in range(1, tps): pfi_tp_bfc = jph(pfo_tmp, sj + '_MSME_tp{}_bfc.nii.gz'.format(tp)) cmd += pfi_tp_bfc + ' ' pfi_stack = jph(pfo_tmp, sj + '_MSME_BFC.nii.gz') cmd += pfi_stack print_and_run(cmd) if controller['bfc_up']: print('- get bfc correction each slice:') pfi_msme_upsampled = jph(pfo_tmp, sj + '_MSMEinS0.nii.gz') assert check_path_validity(pfi_msme_upsampled) print('-- un-pack slices') im = nib.load(pfi_msme_upsampled) tps = im.shape[-1] for tp in range(tps): pfi_up_tp = jph(pfo_tmp, sj + '_MSMEinS0_tp{}.nii.gz'.format(tp)) cmd0 = 'seg_maths {0} -tp {1} {2}'.format(pfi_msme_upsampled, tp, pfi_up_tp) print_and_run(cmd0) print('-- bias-field correct the first slice') # bfc_param = subject[sj][3] bfc_param = [0.001, (50, 50, 50, 50), 0.15, 0.01, 400, (4, 4, 4), 3] pfi_up_tp0 = jph(pfo_tmp, sj + '_MSMEinS0_tp0.nii.gz') pfi_up_tp0_bfc = jph(pfo_tmp, sj + '_MSMEinS0_tp0_BFC.nii.gz') pfi_mask = jph(pfo_mask, sj + '_S0_roi_mask.nii.gz') bias_field_correction(pfi_up_tp0, pfi_up_tp0_bfc, pfi_mask=pfi_mask, prefix='', convergenceThreshold=bfc_param[0], maximumNumberOfIterations=bfc_param[1], biasFieldFullWidthAtHalfMaximum=bfc_param[2], wienerFilterNoise=bfc_param[3], numberOfHistogramBins=bfc_param[4], numberOfControlPoints=bfc_param[5], splineOrder=bfc_param[6], print_only=False) print('-- get the bias field from the bfc corrected') bias_field_up = jph(pfo_tmp, sj + '_bfc_up.nii.gz') cmd0 = 'seg_maths {0} -div {1} {2}'.format(pfi_up_tp0_bfc, pfi_up_tp0, bias_field_up) cmd1 = 'seg_maths {0} -removenan {0}'.format(bias_field_up) print_and_run(cmd0) print_and_run(cmd1) assert check_path_validity(bias_field_up) print('-- correct all the remaining slices') for tp in range(1, tps): pfi_up_tp = jph(pfo_tmp, sj + '_MSMEinS0_tp{}.nii.gz'.format(tp)) pfi_up_tp_bfc = jph(pfo_tmp, sj + '_MSMEinS0_tp{}_bfc.nii.gz'.format(tp)) cmd0 = 'seg_maths {0} -mul {1} {2}'.format(pfi_up_tp, bias_field_up, pfi_up_tp_bfc) print_and_run(cmd0) check_path_validity(pfi_up_tp_bfc) print('-- pack together all the images in a stack') cmd_merge = 'seg_maths {0} -merge {1} {2} '.format( pfi_up_tp0_bfc, tps - 1, 4) for tp in range(1, tps): pfi_up_tp_bfc = jph(pfo_tmp, sj + '_MSMEinS0_tp{}_bfc.nii.gz'.format(tp)) cmd_merge += pfi_up_tp_bfc + ' ' pfi_stack_up = jph(pfo_tmp, sj + '_MSMEinS0_BFC.nii.gz') cmd_merge += pfi_stack_up print_and_run(cmd_merge) if controller['save_results']: print( 'save results - save only the bias field corrected as they proved to have the same results.' ) pfi_msme_nifti = jph(pfo_tmp, sj + '_MSME.nii.gz') # original pfi_msme_bfc = jph(pfo_tmp, sj + '_MSME_BFC.nii.gz') # original bfc pfi_msme_up = jph(pfo_tmp, sj + '_MSMEinS0.nii.gz') # up pfi_msme_up_bfc = jph(pfo_tmp, sj + '_MSMEinS0_BFC.nii.gz') # up bfc assert check_path_validity(pfi_msme_nifti) assert check_path_validity(pfi_msme_bfc) assert check_path_validity(pfi_msme_up) assert check_path_validity(pfi_msme_up_bfc) # pfi_final = jph(pfo_mod, sj + '_MSME.nii.gz') pfi_final_bfc = jph(pfo_mod, sj + '_MSME.nii.gz') # pfi_final_up = jph(pfo_mod, sj + '_MSMEinS0.nii.gz') pfi_final_bfc_up = jph(pfo_mod, sj + '_MSMEinS0.nii.gz') # cmd0 = 'cp {0} {1}'.format(pfi_msme_nifti, pfi_final) # cmd2 = 'cp {0} {1}'.format(pfi_msme_up, pfi_final_up) cmd1 = 'cp {0} {1}'.format(pfi_msme_bfc, pfi_final_bfc) cmd3 = 'cp {0} {1}'.format(pfi_msme_up_bfc, pfi_final_bfc_up) # print_and_run(cmd0) # print_and_run(cmd2) print_and_run(cmd1) print_and_run(cmd3) if controller['save_results_tp0']: print('save results - timepoint zero, only the bfc') # pfi_msme_nifti = jph(pfo_tmp, sj + '_MSME.nii.gz') # original # pfi_msme_up = jph(pfo_tmp, sj + '_MSMEinS0.nii.gz') # up pfi_msme_bfc = jph(pfo_tmp, sj + '_MSME_BFC.nii.gz') # original bfc pfi_msme_up_bfc = jph(pfo_tmp, sj + '_MSMEinS0_BFC.nii.gz') # up bfc # assert check_path_validity(pfi_msme_nifti) # assert check_path_validity(pfi_msme_up) assert check_path_validity(pfi_msme_bfc) assert check_path_validity(pfi_msme_up_bfc) pfo_tp0 = jph(pfo_mod, 'MSME_tp0') # pfi_final_tp0 = jph(pfo_tp0, sj + '_MSME_tp0.nii.gz') # pfi_final_up_tp0 = jph(pfo_tp0, sj + '_MSMEinS0_tp0.nii.gz') pfi_final_bfc_tp0 = jph(pfo_tp0, sj + '_MSME_tp0.nii.gz') pfi_final_bfc_up_tp0 = jph(pfo_tp0, sj + '_MSMEinS0_tp0.nii.gz') cmd0 = 'mkdir -p {}'.format(pfo_tp0) # cmd1 = 'seg_maths {0} -tp 0 {1}'.format(pfi_msme_nifti, pfi_final_tp0) # cmd3 = 'seg_maths {0} -tp 0 {1}'.format(pfi_msme_up, pfi_final_up_tp0) cmd2 = 'seg_maths {0} -tp 0 {1}'.format(pfi_msme_bfc, pfi_final_bfc_tp0) cmd4 = 'seg_maths {0} -tp 0 {1}'.format(pfi_msme_up_bfc, pfi_final_bfc_up_tp0) print_and_run(cmd0) # print_and_run(cmd1) # print_and_run(cmd3) print_and_run(cmd2) print_and_run(cmd4)
def clean_a_study(pfo_study, name_study_cleaned, suffix_acquisition_method=''): """ General cleaner to provide the converted study with tidy names and structure. :param pfo_study: path to folder study to clean :param name_study_cleaned: name you want the study to have after cleaning :param suffix_acquisition_method: extra suffix for the acquisition method, used when there are external files. :return: """ if not os.path.exists(pfo_study): raise IOError('Cannot clean non-existing studies at {}'.format(pfo_study)) list_experiments = list(np.sort(list(set(os.listdir(pfo_study)) - {'.DS_Store'}))) experiments_methods_list = [] for p in list_experiments: pfo_experiment_p = jph(pfo_study, p) pfi_acquisition_method = jph(pfo_experiment_p, 'acquisition_method.txt') if os.path.exists(pfi_acquisition_method): fi_acquisition_method = open(pfi_acquisition_method, 'r') acquisition_method = fi_acquisition_method.read() fi_acquisition_method.close() print acquisition_method list_files_in_experiment = list(set(os.listdir(pfo_experiment_p)) - {'.DS_Store', 'acquisition_method.txt'}) list_nii_gz_in_experiment = [j for j in list_files_in_experiment if j.endswith('.nii.gz')] num_nii = len(list_nii_gz_in_experiment) # conversion table for the filenames: if acquisition_method == 'FieldMap': acquisition_method = 'FM' elif (acquisition_method == 'FLASH' or acquisition_method == 'IntraGateFLASH') and num_nii == 3: acquisition_method = 'FOV' elif (acquisition_method == 'FLASH' or acquisition_method == 'RARE') and not num_nii == 3: acquisition_method = '3D' elif acquisition_method == 'MSME': acquisition_method = 'MSME' elif acquisition_method == 'DtiEpi': acquisition_method = 'DWI' acquisition_method += suffix_acquisition_method experiments_methods_list.append(acquisition_method) if acquisition_method in experiments_methods_list[:-1]: acquisition_method += str(experiments_methods_list.count(acquisition_method)) # fi are the files to be cleaned: for fi in list_files_in_experiment: if acquisition_method in fi: print('already converted?') else: # get filename and extension: fi_split = fi.split('.') fi_name = fi_split[0] if len(fi_split) == 3: extension = '.' + fi_split[1] + '.' + fi_split[2] elif len(fi_split) == 2: extension = '.' + fi_split[1] else: raise IOError if 'subscan_1' in fi_name: print_and_run('rm {}'.format(jph(pfo_experiment_p, fi))) else: print(fi_name) # replace the second element (experiment number) separated between '_' by the acquisition_method fi_name_components = fi_name.split('_') fi_name_components[0] = name_study_cleaned fi_name_components[1] = acquisition_method # get the stack back: new_fi = '' for c in fi_name_components: new_fi += c + '_' new_fi = new_fi[:-1].replace('_subscan_0', '') new_fi += extension cmd = 'mv {} {}'.format(jph(pfo_experiment_p, fi), jph(pfo_experiment_p, new_fi)) print_and_run(cmd) # rename b0 with S0 in coherence with the subsequent FSL steps: if acquisition_method.startswith('DWI'): for file_element_in_DWI_study in os.listdir(pfo_experiment_p): if file_element_in_DWI_study.endswith('_b0.nii.gz'): cmd = 'mv {} {}'.format(jph(pfo_experiment_p, file_element_in_DWI_study), jph(pfo_experiment_p, file_element_in_DWI_study.replace('_b0', '_S0'))) print_and_run(cmd) # rename the folder p containing the files: new_p = '{}_{}'.format(name_study_cleaned, acquisition_method) # '{}_{}'.format(p.split('_')[0], acquisition_method) cmd = 'mv {} {}'.format(pfo_experiment_p, jph(pfo_study, new_p)) print_and_run(cmd) cmd = 'rm {}'.format(jph(pfo_study, new_p, 'acquisition_method.txt')) print_and_run(cmd) else: if len(list(set(os.listdir(pfo_experiment_p)) - {'.DS_Store'})) == 0: # the experiment is an empty folder: get rid of it! print_and_run('rm -r {}'.format(pfo_experiment_p)) else: # the experiment folder is not empty, but there is no name method inside. Raise a warning! cmd = 'No acquisition_method.txt in the folder {} - maybe already cleaned?'.format(pfo_experiment_p) warnings.warn(cmd)
assert os.path.exists(pfi_T1W_moving_tp2), pfi_T1W_moving_tp2 assert os.path.exists(pfi_mask_moving_tp2), pfi_mask_moving_tp2 pfi_moving_on_target_warp_aff = jph( pfo_output_A4_AD, '{}_on_{}_warp_aff.nii.gz'.format(sj_second_tp, sj_first_tp)) pfi_moving_on_target_aff = jph( pfo_output_A4_AD, '{}_on_{}_aff.txt'.format(sj_second_tp, sj_first_tp)) cmd = 'reg_aladin -ref {0} -rmask {1} -flo {2} -fmask {3} -res {4} -aff {5} -speeeeed '.format( pfi_T1W_fixed_tp1, pfi_mask_fixed_tp1, pfi_T1W_moving_tp2, pfi_mask_moving_tp2, pfi_moving_on_target_warp_aff, pfi_moving_on_target_aff) print_and_run(cmd) pfi_moving_on_target_mask_aff = jph( pfo_output_A4_AD, '{}_on_{}_mask_warp_aff.nii.gz'.format( sj_second_tp, sj_first_tp)) cmd = 'reg_resample -ref {0} -flo {1} -trans {2} -res {3} -inter 0 '.format( pfi_T1W_fixed_tp1, pfi_mask_moving_tp2, pfi_moving_on_target_aff, pfi_moving_on_target_mask_aff) print_and_run(cmd) if control['generate_dataset_nrig']: for sj_first_tp, sj_second_tp in zip(params['subjects_FirstTP'], params['subjects_SecondTP']):
def denoise_mif_for_subject(sj, controller): pfi_DWI = jph(root_intermediate, '{}_DWI_slope_corrected_to_std.nii.gz'.format(sj)) pfi_brain_mask = jph(root_MASKs, '{}_brain.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI) assert os.path.exists(pfi_brain_mask) if controller['Denoise']: pfi_DWI_denoised = jph(root_DWIs_corrected, '{}_DWI.nii.gz'.format(sj)) pfi_DWI_noise = jph(root_intermediate, '{}_noise.nii.gz'.format(sj)) cmd = 'dwidenoise {} {} -noise {} -mask {}'.format( pfi_DWI, pfi_DWI_denoised, pfi_DWI_noise, pfi_brain_mask) print_and_run(cmd) if controller['Get_differences']: pfi_DWI_denoised = jph(root_DWIs_corrected, '{}_DWI.nii.gz'.format(sj)) pfi_DWI_noise = jph(root_intermediate, '{}_noise.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI_denoised) assert os.path.exists(pfi_DWI_noise) pfi_residual = jph(root_intermediate, '{}_residual.nii.gz'.format(sj)) cmd = 'mrcalc {} {} -subtract {}'.format(pfi_DWI, pfi_DWI_denoised, pfi_residual) print_and_run(cmd) if controller['Quality_control']: pfi_residual = jph(root_intermediate, '{}_residual.nii.gz'.format(sj)) assert os.path.exists(pfi_residual) cmd = 'mrview {}'.format(pfi_residual) print_and_run(cmd) if controller['Eddy_correct']: print('- eddy current {}'.format(sj)) pfi_DWI_denoised = jph(root_DWIs_corrected, '{}_DWI.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI_denoised) pfi_DWI_denoised_eddy = jph(root_DWIs_corrected, '{}_DWI_eddy.nii.gz'.format(sj)) cmd = 'eddy_correct {0} {1} 0 '.format(pfi_DWI_denoised, pfi_DWI_denoised_eddy) print_and_run(cmd) if controller['Quality_control_Eddy']: pfi_DWI_denoised = jph(root_DWIs_corrected, '{}_DWI.nii.gz'.format(sj)) pfi_DWI_denoised_eddy = jph(root_DWIs_corrected, '{}_DWI_eddy.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI_denoised), pfi_DWI_denoised assert os.path.exists(pfi_DWI_denoised_eddy), pfi_DWI_denoised_eddy cmd = 'mrview -load {0} -load {1}'.format(pfi_DWI_denoised, pfi_DWI_denoised_eddy) print_and_run(cmd) if controller['Create_multi_timepoints_mask']: im_dwi = nib.load(pfi_DWI) pfi_brain_mask_multi_timepoint = jph(root_tmp, '{}_brain_multi_timepoints.nii.gz'.format(sj)) nis_app = nis.App() nis_app.manipulate_shape.extend_slice_new_dimension(pfi_brain_mask, pfi_output=pfi_brain_mask_multi_timepoint, new_axis=3, num_slices=im_dwi.shape[-1]) del im_dwi, nis_app if controller['Grafting_denoised']: print('- grafting') pfi_DWI_denoised = jph(root_DWIs_corrected, '{}_DWI.nii.gz'.format(sj)) pfi_residual = jph(root_intermediate, '{}_residual.nii.gz'.format(sj)) pfi_brain_mask_multi_timepoint = jph(root_tmp, '{}_brain_multi_timepoints.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI_denoised) assert os.path.exists(pfi_residual) assert os.path.exists(pfi_brain_mask_multi_timepoint) pfi_DWI_denoised_grafted = jph(root_DWIs_corrected, '{}_DWIg.nii.gz'.format(sj)) nis_app = nis.App() nis_app.manipulate_intensities.get_grafting(pfi_residual, pfi_DWI_denoised, pfi_DWI_denoised_grafted, pfi_brain_mask_multi_timepoint) if controller['Grafting_denoised_Eddy']: print('- grafting eddy') pfi_DWI_denoised_eddy = jph(root_DWIs_corrected, '{}_DWI_eddy.nii.gz'.format(sj)) pfi_residual = jph(root_intermediate, '{}_residual.nii.gz'.format(sj)) pfi_brain_mask_multi_timepoint = jph(root_tmp, '{}_brain_multi_timepoints.nii.gz'.format(sj)) assert os.path.exists(pfi_DWI_denoised_eddy) assert os.path.exists(pfi_residual) assert os.path.exists(pfi_brain_mask_multi_timepoint) pfi_DWI_denoised_grafted_eddy = jph(root_DWIs_corrected, '{}_DWIg_eddy.nii.gz'.format(sj)) nis_app = nis.App() nis_app.manipulate_intensities.get_grafting(pfi_residual, pfi_DWI_denoised_eddy, pfi_DWI_denoised_grafted_eddy, pfi_brain_mask_multi_timepoint)