Reshaping Blobs in a Binary

When processing an image with low contrast, I inevitably will distort some of the shapes when I threshold the grayscale image and convert it to binary.
Is there any way to reshape blobs after I have done the conversion to binary? I know the shapes should all be circular, but most have tails or look elongated.

1 个评论

Do you have a sample image? Are you doing any processing before the threshold?

请先登录,再进行评论。

 采纳的回答

Image Analyst
Image Analyst 2012-6-20

0 个投票

Regarding your latest comment...For each blob, get the EquivDiameter and the centroid, then call rectangle() to display a circle in the overlay at the centroid location with a diameter of EquivDiameter.

2 个评论

I = imread('TestImage.jpg');
BW = im2bw(I,graythresh(I));
[ai,bi] = size(BW);
figure,imshow(BW), hold on
props = regionprops(logical(BW),'Centroid','EquivDiameter');
centroids = cat(1,props.Centroid);
diams = cat(1,props.EquivDiameter);
for m = 1:length(centroids(:,1))
rectangle('Position',[centroids(m,1)-diams(m)/2,centroids(m,2)-
diams(m)/2,diams(m),diams(m)],'Curvature',[1,1],'FaceColor','r')
end
hold off
Where this is the "TestImage.jpg" that I used:
http://i.imgur.com/Q5C6j.jpg
This is the result:
http://i.imgur.com/kRz8m.jpg
These helpers were exactly what I was looking for and I got those shapes onto my image. Thank you!

请先登录,再进行评论。

更多回答(2 个)

Image Analyst
Image Analyst 2012-6-20

0 个投票

Perhaps, but it's not easy. Let's say you have a comet-shaped blob - pointier at one end than the other. Use bwboundaries() to get all the boundary coordinates. Use regionprops to get the equation of the major axis, using orientation and centroid. Then take the coordinate from each half of the blob. Half will come from the pointy side and half from the larger, rounder size. Scan each set of coordinates to find the minimum curvature over a range of pixels, say 10 or 20 pixels. The side with the larger minimum radius of curvature will be the circular side and the side with the smaller minimum radius of curvature will be the pointy side.
Alternatively you can use bwmorph('skel') to get the skeleton. Then, perhaps you can use bwmorph('endpoints') to get the ends of the skeleton and see which is closer to a boundary point. The endpoint at the pointy tail end will be closer to the nearest boundary point than the endpoint at the larger round head end. The circle would then be placed at the round head end with a radius equal to, say, the average distance of the closest 10 boundary points. Good luck.
Ryan
Ryan 2012-6-20

0 个投票

use region props area measurements and dilate the centroid points with a disk structuring element with the appropriate radius (assume circle and use A = pi*r^2). I have also read some academic papers in the past where they filled areas with the largest circle possible, but I am not sure how to program that.
For area of the circle, you could also use "EquivDiameter" from the regionprops.

5 个评论

If you have a blob with a long tail, the centroid will not be in the round head, but will be shifted toward the tail so the circle would not overlap the round head part. In the latter half of your answer you may be thinking of the skeleton. The skeleton traces out the locations of the largest circle that can fit inside the blob.
I was assuming exact positioning did not matter because he is willing to reshape. I am unsure how to do that with the skeleton, or maybe I am thinking of the wrong skeleton.
* I updated my answer to add mention of "EquivDiameter" with the region props command.
If he had some weird roundish shaped blob and he wanted a round one then he could use the centroid and EquivDiameter to place circles over the blobs. If he wanted the round part of a comet and wanted to discard the tail, then this would mislocate the circle. Your suggestion of uploading and image is a good one. He should also supply an image where he drew the circle outlines on it so we can see what he's really after. Of course the best way is to increase the contrast in the image capture step rather than try to fix it in the image processing step. For example adding more contrast solution, or lighting, or change the color of the lighting, or add fluorescent tagging material, or use dark field illumination or some other kind of illumination, or whatever.
I am not allowed to upload this image, so I apologize for that. I am using a median filter to "smooth" out the image and then a structuring element to fix the non-uniform lighting. After all of that, I apply a threshold and then use bwareaopen() to remove small pixel noise.
It sounds like fixing the problem may be more complicated then I'm willing to deal with. I don't want to shift shapes or distort their true size further by forcing them to be circular.
What I keep thinking is the following:
All I need to do is take the blob area obtained from regionprops(), and, given that the area of a circle is equal to pi*r^2, find the radius of each blob. Then I can draw a circle from the centroid of each blob given the radius found in the previous step. It doesn't sound too complicated in my head, but I haven't figured out anyway to even get started.
Do you think I could go somewhere with that?

请先登录,再进行评论。

Community Treasure Hunt

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

Start Hunting!

Translated by