Example #1
0
static void DiscardMissizedFaces(
    vec_DetPar& detpars) // io
{
    // constants (TODO These have not yet been rigorously empirically adjusted.)
    static const double MIN_WIDTH = 1.33; // as fraction of median width
    static const double MAX_WIDTH = 1.33; // as fraction of median width

    if (NSIZE(detpars) >= 3) // need at least 3 faces
    {
        // sort the faces on their width (smallest first) so can get median width
        sort(detpars.begin(), detpars.end(), DecreasingWidth);
        const int median     = cvRound(detpars[NSIZE(detpars) / 2].width);
        const int minallowed = cvRound(median / MIN_WIDTH);
        const int maxallowed = cvRound(MAX_WIDTH * median);
        // keep only faces that are not too big or small
        vec_DetPar all_detpars(detpars);
        detpars.resize(0);
        for (int iface = 0; iface < NSIZE(all_detpars); iface++)
        {
            DetPar* face = &all_detpars[iface];
            if (face->width >= minallowed && face->width <= maxallowed)
                detpars.push_back(*face);
            else if (trace_g || TRACE_IMAGES)
                lprintf("[discard face%d of %d]", iface, NSIZE(all_detpars));
        }
    }
}
Example #2
0
void DetectFaces(          // all face rects into detpars
    vec_DetPar&  detpars,  // out
    const Image& img,      // in
    int          minwidth) // in: as percent of img width
{
    CV_Assert(!facedet_g.empty()); // check that OpenFaceDetector_ was called

    int leftborder = 0, topborder = 0; // border size in pixels
    Image bordered_img(BORDER_FRAC == 0?
                       img: EnborderImg(leftborder, topborder, img));

    // Detection results are very slightly better with equalization
    // (tested on the MUCT images, which are not pre-equalized), and
    // it's quick enough to equalize (roughly 10ms on a 1.6 GHz laptop).

    Image equalized_img;
    cv::equalizeHist(bordered_img, equalized_img);

    CV_Assert(minwidth >= 1 && minwidth <= 100);

    // TODO smallest bioid faces are about 80 pixels width, hence 70 below
    const int minpix =
        MAX(minwidth <= 5? 70: 100, cvRound(img.cols * minwidth / 100.));

    // the params below are accurate but slow
    static const double SCALE_FACTOR   = 1.1;
    static const int    MIN_NEIGHBORS  = 3;
    static const int    DETECTOR_FLAGS = 0;

    vec_Rect facerects = // all face rects in image
        Detect(equalized_img, facedet_g, NULL,
               SCALE_FACTOR, MIN_NEIGHBORS, DETECTOR_FLAGS, minpix);

    // copy face rects into the detpars vector

    detpars.resize(NSIZE(facerects));
    for (int i = 0; i < NSIZE(facerects); i++)
    {
        Rect* facerect = &facerects[i];
        DetPar detpar; // detpar constructor sets all fields INVALID
        // detpar.x and detpar.y is the center of the face rectangle
        detpar.x = facerect->x + facerect->width / 2.;
        detpar.y = facerect->y + facerect->height / 2.;
        detpar.x -= leftborder; // discount the border we added earlier
        detpar.y -= topborder;
        detpar.width  = double(facerect->width);
        detpar.height = double(facerect->height);
        detpar.yaw = 0; // assume face has no yaw in this version of Stasm
        detpar.eyaw = EYAW00;
        detpars[i] = detpar;
    }
}
Example #3
0
void DetectFaces(          // all face rects into detpars
    vec_DetPar&  detpars,  // out
    const Image& img,      // in
    int          minwidth) // in: as percent of img width
{   

    //Polyphemus version: we already have the face, returns the whole image rectangle
    bool changedForPolyphemus = true;

    //UO
    //CV_Assert(!facedet_g.empty()); // check that OpenFaceDetector_ was called
    //OU

    if(changedForPolyphemus)
    {
        /*
        #ifdef WITH_GUI
        cv::namedWindow("StasmFace", CV_WINDOW_NORMAL);
        cv::imshow("StasmFace", img);//cv::Mat(img, Rect(0,0,img.cols, img.rows)));
        #endif
        */

        //if (img.cols != 800 || img.rows != 600) // sanity check
        //Err("Image must be 800x600 (your image is %dx%d)", img.cols, img.rows);
        DetPar detpar;
        detpar.x = img.cols / 2.; // approximate center of face
        detpar.y = img.rows / 2.;
        detpar.width = img.cols; // approximate size of face
        detpar.height = img.rows;
        detpar.yaw = 0;
        detpar.eyaw = EYAW00;
        detpars.resize(1);
        detpars[0] = detpar;

        //minwidth = 40;
    }
    else
    {

        int leftborder = 0, topborder = 0; // border size in pixels
        Image bordered_img(BORDER_FRAC == 0?
                           img: EnborderImg(leftborder, topborder, img));

        // Detection results are very slightly better with equalization
        // (tested on the MUCT images, which are not pre-equalized), and
        // it's quick enough to equalize (roughly 10ms on a 1.6 GHz laptop).

        Image equalized_img; cv::equalizeHist(bordered_img, equalized_img);

        CV_Assert(minwidth >= 1 && minwidth <= 100);

        // TODO smallest bioid faces are about 80 pixels width, hence 70 below
        const int minpix =
            MAX(minwidth <= 5? 70: 100, cvRound(img.cols * minwidth / 100.));

        // the params below are accurate but slow
        static const double SCALE_FACTOR   = 1.1;
        static const int    MIN_NEIGHBORS  = 3;
        static const int    DETECTOR_FLAGS = 0;

        vec_Rect facerects = // all face rects in image
            Detect(equalized_img, facedet_g, NULL,
                   SCALE_FACTOR, MIN_NEIGHBORS, DETECTOR_FLAGS, minpix);

        // copy face rects into the detpars vector
        detpars.resize(NSIZE(facerects));
        for (int i = 0; i < NSIZE(facerects); i++)
        {
            Rect* facerect = &facerects[i];
            DetPar detpar; // detpar constructor sets all fields INVALID
            // detpar.x and detpar.y is the center of the face rectangle
            detpar.x = facerect->x + facerect->width / 2.;
            detpar.y = facerect->y + facerect->height / 2.;
            detpar.x -= leftborder; // discount the border we added earlier
            detpar.y -= topborder;
            detpar.width  = double(facerect->width);
            detpar.height = double(facerect->height);
            detpar.yaw = 0; // assume face has no yaw in this version of Stasm
            detpar.eyaw = EYAW00;
            detpars[i] = detpar;
        }
    }

}