Simple Face Detection for Windows Phone (3/5)

Simple Face Detection for Windows Phone (3/5)

Simple Face Detection for Windows Phone (3/5)

To explain simple face detection, I wrote 5 posts with each another technique in the face detection process. When you combine all 5 steps, you will be able to detect faces in pictures or video streams.

The steps described in these posts are:

This third post covers how to determine the different blobs. This part seems very easy, but it’s actually quite hard to figure out.

During my school period I learned a technique to do this that runs through the picture multiple times coloring the picture line by line horizontal, smear it out vertical, diagonal and repeat that multiple times. When a blob is square, that’s easy to do. When a blob has a more complicated shape it can take many runs through the picture and the result still isn’t perfect. That’s why I decided to figure out a better way for this myself.

The first thing I tried is creating a recursive function that will color a pixel and call itself for each neighbor that should be colored. In theory this would be just a small function which is very effective. The downside of doing this, is that the function can call itself multiple times, so the computers stack will grow very quickly. When a blob is over about 30.000 pixels, the stack that calls the function over and over can overflow.

To fix this issue in an effective way without getting the risk of a stack overflow, I used a stack and a simple for loop. I added the first pixel of the fill area to a stack. While there are items on the stack, I pop out one item and color it. I check if the surrounding pixels should be colored as well, if so, I add them to the stack.

The color that I give to a pixel is not important, the main thing is that it’s unique and I wanted to set the alpha to 255 so that the color is visible. That’s why a pixel has the color number of the pixel added to #FF000000.

/// <summary>
/// Gives a color to each white area in a picture
/// </summary>
/// <param name="pixels">The picture</param>
/// <param name="width">The width of the pixture</param>
/// <param name="height">The Height of the picture</param>
public static void ColorBlobs(int[] pixels, int width, int height)
{
    int color = 0xFF << 24;

	for (int i = 0; i < pixels.Length; i++)
		if ((uint)pixels[i] == 0xFFFFFFFF)
			Fill(i, pixels, width, height, color + i);
}

/// <summary>
/// Fills a colored area in the picture with another color
/// </summary>
/// <param name="position">The position in the pixel array to start the fill</param>
/// <param name="pixels">The picture</param>
/// <param name="width">The width of the pixture</param>
/// <param name="height">The Height of the picture</param>
/// <param name="color">The color to fill the object with</param>
public static void Fill(int position, int[] pixels, int width, int height, int color)
{
    uint originalColor = (uint)pixels[position];
    Stack<int> stack = new Stack<int>();
    stack.Push(position);

    while (stack.Count > 0)
    {
        position = stack.Pop();
        pixels[position] = color;
        if (position + 1 < width * height && (uint)pixels[position + 1] == originalColor)
            stack.Push(position + 1);
        if (position + width < width * height && (uint)pixels[position + width] == originalColor)
            stack.Push(position + width);
        if (position - 1 >= 0 && (uint)pixels[position - 1] == originalColor)
            stack.Push(position - 1);
        if (position - width >= 0 && (uint)pixels[position - width] == originalColor)
            stack.Push(position - width);
    }
}
Black and white result from the YcBcR filter

Black and white result from the YcBcR filter

The blobs colored in

The blobs colored in

Download Download the whole demo project

4 thoughts on “Simple Face Detection for Windows Phone (3/5)”

Leave a Reply

Your email address will not be published. Required fields are marked *