Automatically crop an object from a solid background as close as possible to the object edges.

7 views (last 30 days)
I am trying to crop an object/product from a relatively solid background but have been struggling to get a perfect implementation or at least something that works most of the time.
My previous questions were asked on Stack Overflow and I've been able to get decent results and cropping a rectangle works almost perfectly:
My current approach is to find a mask of the image and then change every unwanted pixel to white, but this hasn't given me consistent results:
original = imread('1.jpg');
level = graythresh(original);
img = rgb2gray(original);
mask = im2bw(img,level+0.1);
se = strel('line',10,90);
mask = imdilate(~mask,se);
mask = imfill(mask,'holes');
bw = activecontour(img,mask);
rows = numel(original(:,1,1));
columns = numel(original(1,:,1));
for i = 1:rows
for j = 1:columns
if ( bw(i,j,1) == 0 )
original(i,j,:) = 255;
end
end
end
imshow(original);
A preview image:

Accepted Answer

Image Analyst
Image Analyst on 17 Jun 2014
From the looks of your code, it looks like you should come to Answers before Stack Overflow. For example, you last double loop can be done vectorized. Anyway, if you want as close as possible, why are you dilating your image and doing an activecontour? Both of these will give you a boundary slightly off your "true" boundary. I'd recommend converting to hsv colorspace and threshold for high saturation. The objects will be selected and the white background will not be selected (because white and shadows have low S value). See the color segmentation demos in my File Exchange, especially this one: http://www.mathworks.com/matlabcentral/fileexchange/28512-simple-color-detection-by-hue
  1 Comment
Jacques Fourie
Jacques Fourie on 20 Jun 2014
Hi Image Analyst, I get the mask pretty well, but how do I get rid of any writing inside the product label and how do I use the mask to isolate the product, I tried the following code and the valueMask and saturationMask looks good on their own...
rgbImage = imread('5.jpg');
% Convert RGB image to HSV
hsvImage = rgb2hsv(rgbImage);
% Extract out the H, S, and V images individually
hImage = hsvImage(:,:,1);
sImage = hsvImage(:,:,2);
vImage = hsvImage(:,:,3);
hueThresholdLow = 0;
hueThresholdHigh = graythresh(hImage);
saturationThresholdLow = 0.09;
saturationThresholdHigh = 1.0;
valueThresholdLow = graythresh(vImage);
valueThresholdHigh = 1.0;
hueMask = (hImage >= hueThresholdLow) & (hImage <= hueThresholdHigh);
saturationMask = (sImage >= saturationThresholdLow) & (sImage <= ... saturationThresholdHigh);
valueMask = (vImage >= valueThresholdLow) & (vImage <= ... valueThresholdHigh);
mask = (saturationMask & valueMask);

Sign in to comment.

More Answers (0)

Categories

Find more on Convert Image Type in Help Center and File Exchange

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!