Fast Peak Detection for 2D Images via GL Shader

A common task in image analysis and recognition is the peak detection. n this article, we will discuss GL shader code, which finds peaks quickly in a 2D array/image.

What is peak detection and why we do it?

Algorithms such as Hough transform and Harris corners detection often require post-processing to isolate the dominant regions of interest. Otherwise we get too noisy image results that prevent our successful segmentation.

Example of Peak detection in 2d Image
Example result of Hough transform – left: without peak detection, right: with peak detection

This simple peak detector source code helps to achieve this. The algorithm uses a generic non-maximum suppression to eliminate local minima and preserve the dominant results.

Source Code

This algorithm uses separable non-maximal suppression to achieve better performance. Its valuable property to search for peaks in parallel makes it suitable for GPU implementations.

precision mediump float;
#define KERNEL_SIZE %kernelSize%

// our texture
uniform sampler2D u_image;
uniform vec2 u_textureSize;
uniform vec2 u_direction;
#define GET_PIXEL(_p) (texture2D(u_image, textCoord + onePixel*float(_p)))

void main() {
  vec2 onePixel = u_direction / u_textureSize;
  vec2 textCoord = gl_FragCoord.xy / u_textureSize;
  
  if (any(lessThan(GET_PIXEL(0).rgb, vec3(0.0))))
  {
    gl_FragColor = vec4(vec3(0.0), 1.0);
  }
  else
  {
    int maxIndex = KERNEL_SIZE;
    float maxValue = 0.0;
    
    for (int i = -KERNEL_SIZE; i <= KERNEL_SIZE; i++)
    {
      vec3 color = GET_PIXEL(i).rgb;
      float p = dot(color, color);
      if (p > maxValue)
      {
        maxValue = p;
        maxIndex = i;
      }
    }
    vec4 color = GET_PIXEL(maxIndex);
    gl_FragColor = ((maxIndex == 0) ? color : vec4(vec3(-color.rgb)*u_direction.y, 1.0));
  }
}

How this peak detector works?

The following steps briefly describe how the above peak detector code works:

  • First, we define the constant “KERNEL_SIZE” so that it is equal to the maximum distance between the peaks;
  • For each row in the image we use a sliding window with the defined size. At each step we invert all non-maximum values to a negative number;
  • Next we handle the non-maximum values per each column in the same was as in the previous step.
  • Pixels with negative value are set to zero

Online Example

fivekogfx harris corners detector thumb

WEB APPLET

See how it works in the browser!

Conclusion

In this article we reveal a simple, but yet fast way to isolate peaks in 2D image/array using OpenGL/WebGL shader code. If you find this article useful, you can browse our image analysis algorithms and our software developers portal.


Related articles