def compute_nifti_bounding_box(img): """Finds bounding box from data and transforms it in world space for use on data with different attributes like voxel size.""" data = img.get_fdata(dtype=np.float32, caching='unchanged') affine = img.affine voxel_size = img.header.get_zooms()[0:3] voxel_bb_mins, voxel_bb_maxs = bounding_box(data) world_bb_mins = voxel_to_world(voxel_bb_mins, affine) world_bb_maxs = voxel_to_world(voxel_bb_maxs, affine) wbbox = WorldBoundingBox(world_bb_mins, world_bb_maxs, voxel_size) return wbbox
def crop_nifti(img, wbbox): """Applies cropping from a world space defined bounding box and fixes the affine to keep data aligned.""" data = img.get_fdata(dtype=np.float32, caching='unchanged') affine = img.affine voxel_bb_mins = world_to_voxel(wbbox.minimums, affine) voxel_bb_maxs = world_to_voxel(wbbox.maximums, affine) # Prevent from trying to crop outside data boundaries by clipping bbox extent = list(data.shape[:3]) for i in range(3): voxel_bb_mins[i] = max(0, voxel_bb_mins[i]) voxel_bb_maxs[i] = min(extent[i], voxel_bb_maxs[i]) translation = voxel_to_world(voxel_bb_mins, affine) data_crop = np.copy(crop(data, voxel_bb_mins, voxel_bb_maxs)) new_affine = np.copy(affine) new_affine[0:3, 3] = translation[0:3] return nib.Nifti1Image(data_crop, new_affine)