Search code examples
imagematlabimage-processingbounding-boxbinary-image

Resizing an image to fit around an isolated object in MATLAB


I am working with RGB images that contain a single object against a monochrome background.

My goal is to isolate the object in the image and resize the image to contain only the object.

I have successfully been able to detect the object by converting the image to a binary image using an appropriate threshold. Then, in order to isolate the object in the original RGB image I use the binary image as a mask with the original RGB image.

maskedImage = bsxfun(@times,originalimage, cast(binaryimage,class(originalimage)));

This leaves me with a image only containing the object surrounded by a black background. This is due to the fact that the binary image mask I used contained the object in white pixels and the background in black pixels and since possess intensity values of 0 the masking process converted all pixels that didn't belong to the object to black pixels. I've attached an example below.

two muppets

I would now like to draw a bounding box around the object and resize the image to the size of the bounding box, so that I can get rid as much of the surrounding black pixels as possible. Is there any way of doing this? Any help would be appreciated.


Solution

  • Given the segmented image, you want to crop out all of the black pixels and provide the closest bounding box that fully encapsulates the object. That's very simple.

    You already have a binary mask that determines what is an object and what's background. You simply need to find the minimum spanning bounding box. You can find the top-left and bottom right corner by obtaining all of the pixel locations that are non-zero in the mask, and finding the minimum and maximum row and column coordinates. You'd then just use these to crop out the segmented image.

    As such:

    %// Find all non-zero locations in the mask
    [row,col] = find(binaryImage);
    
    %// Find the top left corner of the mask
    topLeftRow = min(row);
    topLeftCol = min(col);
    
    %// Find the bottom right corner of the mask
    bottomRightRow = max(row);
    bottomRightCol = max(col);
    
    %// Extract the object
    extracted = maskedImage(topLeftRow:bottomRightRow, topLeftCol:bottomRightCol, :);