OpenCV Eye Tracking проигрывает для некоторых кадров - PullRequest
1 голос
/ 19 октября 2011

Я вставляю код ниже, чтобы отслеживать оба глаза и накладывать изображение, когда отслеживаются оба глаза.
Я использую файлы haar xml для слежения за глазами и наложения на них изображения.
Моя проблема в том, что я получаю такой результат.

Img 1

image

Img 2

image

Img 3

image

Img 4

image

Img 5

image

Img 6

image

Img 7

image

Img 8

image

Img 9

image

Img 10

image

Я публикую свой код ниже

#include "cv.h"
#include "highgui.h"
#include <iostream>
#include <fstream>
#include <vector>
#include <stdio.h>
#include <sys/stat.h>
#include <ctype.h>
#include <string>
using namespace cv;
using namespace std;

void detectAndDisplay( Mat frame );
String face_cascade_name = "/root/opencv/newtutorial/haarcascade_frontalface_alt.xml";
String eyes_cascade_name = "/root/opencv/newtutorial/haarcascade_eye_tree_eyeglasses.xml";
CascadeClassifier face_cascade;
CascadeClassifier eyes_cascade;
RNG rng(12345);
IplImage *disp,*neg_img,*cpy_img,*imga;
IplImage *pic;
IplImage  *image_n = 0;
int make=0;
CvMat* warp_matrix = cvCreateMat(3,3,CV_32FC1);
namespace {
    void makevdo(){
        bool flag = false;
        fstream fin;
        char filename_new[200],filename_new_after[200];
        int n=0;
        Mat frame;
        double frameRate = 25.0;
        CvVideoWriter *vdowriter = cvCreateVideoWriter( "/root/opencv/newtutorial/test_converted_next.mov", CV_FOURCC('j','p','e','g'), frameRate, Size(640,480) );
        VideoWriter(outputFile,CV_FOURCC('j','p','e','g'),frameRate,Size(640,480));
        while(flag==false){
            sprintf(filename_new,"/root/opencv/newtutorial/mydirnext/filename%.3d.jpg",n);
            sprintf(filename_new_after,"/root/opencv/newtutorial/framesaftertrack/filename%.3d.jpg",n);
            fin.open(filename_new,ios::in);
            if( fin.is_open() )
            {
                frame = imread(filename_new);
                pic = cvLoadImage("/root/opencv/newtutorial/pic.png");
                image_n = cvLoadImage(filename_new,1);
                disp = cvCreateImage( cvGetSize(image_n), 8, 3 );
                cpy_img = cvCreateImage( cvGetSize(image_n), 8, 3 );
                neg_img = cvCreateImage( cvGetSize(image_n), 8, 3 );
                std::vector<Rect> faces;
                Mat frame_gray;
                cvtColor( frame, frame_gray, CV_BGR2GRAY );
                equalizeHist( frame_gray, frame_gray );
                face_cascade.detectMultiScale( frame_gray, faces, 1.1, 2, 0|CV_HAAR_SCALE_IMAGE, Size(30, 30) );
                CvPoint2D32f q[4];
                q[0].x= (float) pic->width * 0;
                q[0].y= (float) pic->height * 0;
                q[1].x= (float) pic->width;
                q[1].y= (float) pic->height * 0;
                q[2].x= (float) pic->width;
                q[2].y= (float) pic->height;
                q[3].x= (float) pic->width * 0;
                q[3].y= (float) pic->height;
                for( int i = 0; i < (int)faces.size(); i++ )
                {
                    faces[i].height*0.5), 0, 0, 360, Scalar( 255, 0, 255 ), 2, 8, 0 );
                    Mat faceROI = frame_gray( faces[i] );
                    std::vector<Rect> eyes;
                    eyes_cascade.detectMultiScale( faceROI, eyes, 1.1, 2, 0 |CV_HAAR_SCALE_IMAGE, Size(30, 30) );
                    if((int)eyes.size()==2 && (((eyes[0].x + eyes[0].width*0.5 ) < eyes[1].x) || ((eyes[1].x + eyes[1].width*0.5 ) < eyes[0].x))){
                        CvPoint2D32f p[4];
                        IplImage* blank  = cvCreateImage( cvGetSize(pic), 8, 3);
                        cvZero(blank);
                        cvNot(blank,blank);
                        if(eyes[0].x<eyes[1].x){
                            Point center0( faces[i].x + eyes[0].x + eyes[0].width*0.5, faces[i].y + eyes[0].y + eyes[0].height*0.5 ); 
                            float radius0 =  (eyes[0].width + eyes[0].height)*0.25 ;
                            Point center1( faces[i].x + eyes[1].x + eyes[1].width*0.5, faces[i].y + eyes[1].y + eyes[1].height*0.5 ); 
                            float radius1 =  (eyes[1].width + eyes[1].height)*0.25 ;
                            p[2].x= (float) center0.x - radius0;
                            p[2].y= (float) center0.y + radius0;
                            p[1].x= (float) center0.x - radius0;
                            p[1].y= (float) center0.y - radius0;
                            p[3].x= (float) center1.x + radius1;
                            p[3].y= (float) center1.y + radius1;
                            p[0].x= (float) center1.x + radius1;
                            p[0].y= (float) center1.y - radius1;
                        }
                        else{
                            Point center0( faces[i].x + eyes[1].x + eyes[1].width*0.5, faces[i].y + eyes[1].y + eyes[1].height*0.5 ); 
                            float radius0 =  (eyes[1].width + eyes[1].height)*0.25 ;
                            Point center1( faces[i].x + eyes[0].x + eyes[0].width*0.5, faces[i].y + eyes[0].y + eyes[0].height*0.5 ); 
                            float radius1 =  (eyes[0].width + eyes[0].height)*0.25 ;
                            p[2].x= (float) center0.x - radius0;
                            p[2].y= (float) center0.y + radius0;
                            p[1].x= (float) center0.x - radius0;
                            p[1].y= (float) center0.y - radius0;
                            p[3].x= (float) center1.x + radius1;
                            p[3].y= (float) center1.y + radius1;
                            p[0].x= (float) center1.x + radius1;
                            p[0].y= (float) center1.y - radius1;
                        }

                        cvGetPerspectiveTransform(q,p,warp_matrix);
                        cvZero(neg_img);
                        cvZero(cpy_img);
                        cvWarpPerspective( pic, neg_img, warp_matrix);
                        cvWarpPerspective( blank, cpy_img, warp_matrix);
                        cvNot(cpy_img,cpy_img);
                        cvAnd(cpy_img,image_n,cpy_img);
                        cvOr(cpy_img,neg_img,image_n);
                    }
                }
                cvSaveImage(filename_new_after,image_n);
                cvWriteFrame(vdowriter,image_n);
                cout<<"Read file filename"<< n <<endl;
            }
            else{
                flag=true;
            }
            fin.close();
            n++;
        }
        cvReleaseVideoWriter(&vdowriter);
        cvReleaseImage(&pic);
        cvReleaseImage(&imga);
        cvReleaseImage(&disp);
        cvReleaseImage(&neg_img);
        cvReleaseImage(&cpy_img);
        cvReleaseImage(&image_n);
    }

    int process(VideoCapture& capture) {
        char strFrame[]="/root/opencv/newtutorial/mydirnext";
        if(mkdir(strFrame,0777)==-1)
        {
            cout<<"Error Trying to delete"<<endl;
            if(system("rm -r /root/opencv/newtutorial/mydirnext")){
                cout << "Directory successfully deleted"<<endl;
            }
            if(mkdir(strFrame,0777)==-1){
                cout << "Error Again creating directory" << endl;
            }
        }
        int n = 0;
        char filename[200];
        string window_name = "video | q or esc to quit";
        cout << "press space to save a picture. q or esc to quit" << endl;
        namedWindow(window_name, CV_WINDOW_KEEPRATIO);
        Mat frame;
        for (;;) {
            capture >> frame;
            if (frame.empty())
                continue;
            imshow(window_name, frame);
            sprintf(filename,"/root/opencv/newtutorial/mydirnext/filename%.3d.jpg",n++);
            imwrite(filename,frame);
            char key = (char)waitKey(5);
            switch (key) {
            case 27:
                if(make==0){
                    make=1;
                    makevdo();
                }
            return 0;
            default:
            break;
            }
        }
        return 0;
    }
}
int main(int ac, char** av) {
    if( !face_cascade.load( face_cascade_name ) ){ printf("--(!)Error loading\n"); return -1; };
    if( !eyes_cascade.load( eyes_cascade_name ) ){ printf("--(!)Error loading\n"); return -1; };
    if (ac != 2) {
        return 1;
    }
    std::string arg = av[1];
    VideoCapture capture(arg);
    if (!capture.isOpened())
        capture.open(atoi(arg.c_str()));
    if (!capture.isOpened()) {
        cerr << "Failed to open a video device or video file!\n" << endl;
        return 1;
    }
    return process(capture);
}

Извините за публикацию такого количества изображений, но другого способа объяснить мою проблему нет.

1 Ответ

0 голосов
/ 29 октября 2011

Начните с извлечения всех методов / функций, которым вы можете дать разумное имя.Мы не хотим видеть методы длиннее 10 строк.Изображения не полезны вообще.Удалите наложение и покажите, что алгоритм утверждает, что распознает, когда это делает.Сначала те, где он узнает, затем те, где он не узнает.Таким образом, вы сможете лучше понять, в чем проблема.Но сначала убери грязный код.

...