Hi. I want to detect a face and draw line exactly around the face to crop it.

I searched a lot and used the EmguCV face detector. but now my code just draw a "rectangle" around the face and if I crop it, I will have a rectangle with a face inside it and it's not useful for me. this is the core of my simple code:

CascadeClassifier _cascadeClassifier = new CascadeClassifier(Application.StartupPath + "/haarcascade_frontalface_alt_tree.xml");
using (var firstImage = Image.FromStream(saveImageStream))
{
    var bgrImage = new Image(new Bitmap(firstImage));
    Image grayFrame = bgrImage.Convert();
    var faces = _cascadeClassifier.DetectMultiScale(grayFrame, 1.01, 1, Size.Empty);
    foreach (var face in faces)
    {
        bgrImage.Draw(face, new Bgr(Color.BurlyWood), 3);
    }
    Image detectedImage = bgrImage.ToBitmap();
    detectedImage.Save("detectedImage .jpg");
}

the output of this code is a picture with "rectangle" around the face. you can see in the attached picture.

Untitled_-_3.jpg

the output of this code is a picture with "rectangle" around the face. But how can I detect face and "draw line around the face" like an oval that consist all elements of the face and not anything else?

thank you

Here's a bit of ancient history for you. Way back in the day one of the very first breakthroughs in image recognition was made by a computer hobbyist, and it is germaine to your problem. The main problem in image recognition is edge extraction - how does one do that? It turns out that there is a fairly simple algorithm for extracting the edges from an image:

1) Take the image as a bitmap.
2) Make a duplicate of the image.
3) Offset the duplicate one pixel horizontally and one pixel vertically from the original.
4) XOR the two images back together, pixel-for-pixel.

This was originally done for monochrome images - for a color image you will probably have to come up with some manner of comparison threshold whereby you can tell whether two colors are sufficiently similar to count as the same (and thus cancel out) rather than using a simple exclusive-or. It will also extract all the edges, which in your sample above might not give you a clean line along the jaws on either side and you'll get lips, nose, brows, hairline and other spurious elements. But you might want to give it a try - it might get you close enough to a solution that you can see a fairly simple way to clean up the result and arrive at an acceptable solution.

You could also combine this with other algorithms. There is a fairly common and popular algorithm whose sole function is to take a full-color image and reduce it to simple gray-scale - that might take care of 90% of the color problems right there and bring you back to a simple exclusive-or. There are a lot of such algorithms - search for "color to grayscale" and you'll find several that are trivial to implement.