Laplacian of Gaussian Blob Detection showing blobs that shouldn't be there

206 Views Asked by At

I am trying to write a class that uses the Laplacian of Gaussian for blob detection. Here is the class that I wrote:

import cv2 as cv
import numpy as np
from sklearn.preprocessing import normalize
from scipy import ndimage

class Blob:
        
    BlobStack = [[[[]]]]
    
    def _getLGKernel(self,sx,sy):
        kx = (int(sx - 0.8)*4+1)*2+1
        ky = (int(sy - 0.8)*4+1)*2+1    
        gaussKernelX = np.float32(cv.getGaussianKernel(kx,sx))
        gaussKernelY = np.float32(cv.getGaussianKernel(ky,sy))
        d2GaussKernelX = cv.Laplacian(gaussKernelX,cv.CV_32F)[1:kx-1]
        d2GaussKernelY = cv.Laplacian(gaussKernelY,cv.CV_32F)[1:ky-1]
        d2GaussKernelX = normalize(d2GaussKernelX,axis=0)
        d2GaussKernelY = normalize(d2GaussKernelY,axis=0)
        return d2GaussKernelX, d2GaussKernelY
    
    def __init__(self,img,mins,maxs,steps):
        step = int((maxs-mins)/steps)
        r = range(mins,maxs+step,step)
        self.BlobStack = np.zeros((np.size(r),np.size(r),np.shape(img)[0],np.shape(img)[1]),dtype= np.float32)
        for i,sx in enumerate(r):
            for j,sy in enumerate(r):
                kernx, kerny = self._getLGKernel(sx, sy)
                self.BlobStack[i,j] = np.abs(cv.filter2D(img,cv.CV_64F,kernx,borderType = cv.BORDER_REPLICATE) \
                                             +cv.filter2D(img,cv.CV_64F,np.transpose(kerny),borderType = cv.BORDER_REPLICATE))        
        return
    
    def findLocalBlobs(self,sz):
        LocalBlobs = np.where(ndimage.maximum_filter(self.BlobStack,size=sz) == self.BlobStack)
        LocalBlobs = np.asarray(LocalBlobs).transpose()
        return  LocalBlobs

Right now I am using a test case with two circles of various darkness on a white background. I am getting many extra blobs that shouldn't be there. Some are at the minimum or maximum kernel size but some are at other kernel sizes. There are kernel sizes, which are sometimes the max kernel size in one direction but not always, that have a constant value in a large region that it is detecting a local minimum at. It is lower than the value of the actual blobs I want to detect but still well above what could be a floating point error. A straight forward filtering by the value of the LoG doesn't work because some of the 'phantom' blobs have a higher value than the circle with the lower contrast to the background.

I am more interested in help from a theoretical image processing prospective as this is just a project that I am using to learn from, but any help would be appreciated.

0

There are 0 best solutions below