How to find circles within a region of interest

9 views (last 30 days)
We're trying to find circles within a freehand drawn boundary. The issue that we're running into is that the circle finder code is also finding the edges of the region of interest and calling them circles. This is our code:
%open your image
A = imread('sample.png');
%create mask%
h_im= imshow(A);
e = imfreehand
mask = createMask(e,h_im);
imshow(mask)
%overlay mask
[rows, columns, numberofcolorbands]= size(A);
if numberofcolorbands == 1
maskImage = A;
maskImage(~mask) = 0;
else
maskedImage = bsxfun(@times,A,cast(mask,class(A)));
end
%Find circles in masked region
[centers, radii] = imfindcircles(maskImage,[2 4],'ObjectPolarity','dark','Sensitivity',1,'Method','twostage','EdgeThreshold',0.25);
imshow(maskImage);
h = viscircles(centers, radii);
And here is our sample output:
How do we specify that we want only the code to look within the boundary to find the circles and ignore the edge?
Thanks, Jenna and Amy

Answers (1)

Spandan Tiwari
Spandan Tiwari on 20 Dec 2016
imfindcircles uses circular Hough transform underneath and detecting circles with small radius (usually < 5) is always challenging. I don't see a simple way to play with the parameters of imfindcircles to get rid of the boundary circles. There's a parameter called 'EdgeThreshold' that you can try but the idea there is to keep the strong edges in the image for circle detection and ignore the weak ones. But in this case I won't be surprised if the edges at the boundary of the region are the strongest, in which case this parameter won't be able to remove the ones at the edges (at least not in one call). This means that we need to do some post-processing to identify and eliminate the spurious circles at the edges. If you are using imfreehand to create the region you can get the binary mask of the region as follows:
h = imfreehand();
% Create a binary mask
binaryImage = h.createMask();
Now you can get a mask for the boundary of the region as follows:
rad = 5;
boundaryMask = imdilate(binaryImage, 5) - imerode(binaryImage, 5);
'boundaryMask' will highlight pixels that are within a 'rad' distance from the boundary, on either side. From this point on, it should be easy to check whether a circle (its center maybe) lies within this boundary region or not.
  2 Comments
Image Analyst
Image Analyst on 20 Dec 2016
Maybe if they'd attached the input image, people could try things. With only the output image, I can't even see the circles they're trying to identify. Perhaps regionfill can be used to smear the blob outwards and reduce the strength of the signal near the boundary. But maybe just checking whether the circle is inside the ring of width 5 around the perimeter, like Spandan suggested, is better and/or simpler. It's just whether you want to avoid finding them in the first place versus finding them and then throwing them away if they're near the boundary.
Jenna Perry
Jenna Perry on 20 Dec 2016
Thanks for all of your answers, we figured out a work-around by first finding all of the circles in the image (instead of just the circles within our area of interest), then used the impoly function to select the area of interest. From there, we found if the centers of the circles fell within the coordinates of the polygon shape we created and were able to count the number of circles that fell within our region of interest.
%Find all of the circles in the image
[centers,radii] = imfindcircles(gammaimage,[2 4],'ObjectPolarity','dark','Sensitivity',1,'Method','twostage','EdgeThreshold',0.3);
%Visualize the circles found
h = viscircles(centers, radii);
%Define Region of Interest (ROI)
ROI = impoly();
%Find coordinates of ROI
pospoly = getPosition(ROI);
%See if circles fall within ROI
insideROI = inpolygon(centers(:,1), centers(:,2), pospoly(:,1),pospoly(:,2));
Thanks again for all of your suggestions, Jenna and Amy

Sign in to comment.

Community Treasure Hunt

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

Start Hunting!