So I have an HSV filtered image that I am trying to do blob detection on but for some reason it is not working. The image is this one:https://i.stack.imgur.com/OhIaY.png
Using the Simple Blob Detector, I get this: https://i.stack.imgur.com/07wl0.png
However, on other samples such as https://i.stack.imgur.com/mYgbc.png, the code works perfectly fine and does the job I want. What parameter do I change? I'm really not sure what's going wrong, this should be working. My code is attached below:
import cv2
import numpy as np
from matplotlib import pyplot as plt
%matplotlib inline
plt.rcParams['figure.figsize'] = [20, 10]
img = cv2.imread('graphenetest.png')
#img = cv2.resize(img,(800,600))
SLG_MIN = np.array([114, 50, 50],np.uint8)
SLG_MAX = np.array([116, 255, 255],np.uint8)
hsv_img = cv2.cvtColor(img,cv2.COLOR_BGR2HSV)
frame_threshed = cv2.inRange(hsv_img, SLG_MIN, SLG_MAX)
imagem = cv2.bitwise_not(frame_threshed)
kernel = np.ones((10, 10), np.uint8)
#blur = cv2.morphologyEx(imagem, cv2.MORPH_CLOSE, kernel)
median = cv2.medianBlur(imagem,9)
im = median
plt.imshow(im)
plt.title('Single Layer Graphene Detected')
plt.show()
# Setup SimpleBlobDetector parameters.
params = cv2.SimpleBlobDetector_Params()
# Change thresholds
params.minThreshold = 50
params.maxThreshold = 100
# Filter by Area.
params.filterByArea = True
params.minArea = 10000
params.maxArea = 100000000
params.filterByCircularity = False
params.filterByInertia = False
params.filterByConvexity = False
# Create a detector with the parameters
ver = (cv2.__version__).split('.')
if int(ver[0]) < 3 :
detector = cv2.SimpleBlobDetector(params)
else :
detector = cv2.SimpleBlobDetector_create(params)
# Detect blobs.
keypoints = detector.detect(im)
# Draw detected blobs as red circles.
# cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS ensures
# the size of the circle corresponds to the size of blob
#im_with_keypoints = cv2.drawKeypoints(im, keypoints, np.array([]), (0,0,255), cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS)
img2 = im.copy()
for x in range(1,len(keypoints)):
img2=cv2.circle(img, (np.int(keypoints[x].pt[0]),np.int(keypoints[x].pt[1])), radius=np.int(keypoints[x].size), color=(255, 0, 0), thickness=10)
# Show blobs
plt.imshow(img)
plt.title('Single Layer Graphene Detected')
plt.show()
cv2.imwrite("SLG.png", img)
I tried messing with the parameters, making minArea = 150 works for the one it otherwise doesn't work for, but doing that screws the other shapes. I even tried adding a constraint to the circle drawing function:
if np.int(keypoints[x].size) >= 500:
but that did not help either. Besides all this parameter messing seems so arbitrary, I want something more systematic.
Here is the original image I am trying to do a detection on: https://imgur.com/a/UKh7Xfu