--- a +++ b/ants/ops/crop_image.py @@ -0,0 +1,158 @@ + + + +__all__ = ['crop_image', + 'crop_indices', + 'decrop_image'] + + +import ants +from ants.decorators import image_method +from ants.internal import get_lib_fn + +@image_method +def crop_image(image, label_image=None, label=1): + """ + Use a label image to crop a smaller ANTsImage from within a larger ANTsImage + + ANTsR function: `cropImage` + + Arguments + --------- + image : ANTsImage + image to crop + + label_image : ANTsImage + image with label values. If not supplied, estimated from data. + + label : integer + the label value to use + + Returns + ------- + ANTsImage + + Example + ------- + >>> import ants + >>> fi = ants.image_read( ants.get_ants_data('r16') ) + >>> cropped = ants.crop_image(fi) + >>> fi2 = ants.merge_channels([fi,fi]) + >>> cropped2 = ants.crop_image(fi2) + >>> cropped = ants.crop_image(fi, fi, 100 ) + """ + if image.has_components: + return ants.merge_channels([crop_image(img, label_image, label) for img in ants.split_channels(image)], + channels_first=image.channels_first) + + inpixeltype = image.pixeltype + ndim = image.dimension + if image.pixeltype != 'float': + image = image.clone('float') + + if label_image is None: + label_image = ants.get_mask(image) + + if label_image.pixeltype != 'float': + label_image = label_image.clone('float') + + libfn = get_lib_fn('cropImage') + itkimage = libfn(image.pointer, label_image.pointer, label, 0, [], []) + return ants.from_pointer(itkimage).clone(inpixeltype) + + +@image_method +def crop_indices(image, lowerind, upperind): + """ + Create a proper ANTsImage sub-image by indexing the image with indices. + This is similar to but different from array sub-setting in that + the resulting sub-image can be decropped back into its place without + having to store its original index locations explicitly. + + ANTsR function: `cropIndices` + + Arguments + --------- + image : ANTsImage + image to crop + + lowerind : list/tuple of integers + vector of lower index, should be length image dimensionality + + upperind : list/tuple of integers + vector of upper index, should be length image dimensionality + + Returns + ------- + ANTsImage + + Example + ------- + >>> import ants + >>> fi = ants.image_read( ants.get_ants_data("r16")) + >>> cropped = ants.crop_indices( fi, (10,10), (100,100) ) + >>> cropped = ants.smooth_image( cropped, 5 ) + >>> decropped = ants.decrop_image( cropped, fi ) + """ + if image.has_components: + return ants.merge_channels([crop_indices(img, lowerind, upperind) for img in ants.split_channels(image)], + channels_first=image.channels_first) + + inpixeltype = 'float' + if image.pixeltype != 'float': + inpixeltype = image.pixeltype + image = image.clone('float') + + if (image.dimension != len(lowerind)) or (image.dimension != len(upperind)): + raise ValueError('image dimensionality and index length must match') + + libfn = get_lib_fn('cropImage') + itkimage = libfn(image.pointer, image.pointer, 1, 2, lowerind, upperind) + ants_image = ants.from_pointer(itkimage) + if inpixeltype != 'float': + ants_image = ants_image.clone(inpixeltype) + return ants_image + +@image_method +def decrop_image(cropped_image, full_image): + """ + The inverse function for `ants.crop_image` + + ANTsR function: `decropImage` + + Arguments + --------- + cropped_image : ANTsImage + cropped image + + full_image : ANTsImage + image in which the cropped image will be put back + + Returns + ------- + ANTsImage + + Example + ------- + >>> import ants + >>> fi = ants.image_read(ants.get_ants_data('r16')) + >>> mask = ants.get_mask(fi) + >>> cropped = ants.crop_image(fi, mask, 1) + >>> cropped = ants.smooth_image(cropped, 1) + >>> decropped = ants.decrop_image(cropped, fi) + """ + inpixeltype = 'float' + if cropped_image.pixeltype != 'float': + inpixeltype= cropped_image.pixeltype + cropped_image = cropped_image.clone('float') + if full_image.pixeltype != 'float': + full_image = full_image.clone('float') + + libfn = get_lib_fn('cropImage') + itkimage = libfn(cropped_image.pointer, full_image.pointer, 1, 1, [], []) + ants_image = ants.from_pointer(itkimage) + if inpixeltype != 'float': + ants_image = ants_image.clone(inpixeltype) + + return ants_image +