Using cvQueryFrame and boost::thread together

2019-03-06 04:05发布

问题:

I need to call cvQueryFrame (to capture a frame from a webcam with opencv) instead a thread created with boost. Here is a little example code:

void testCVfunc(){
    IplImage* frame;
    CvCapture *capture;
    capture = cvCreateCameraCapture(CV_CAP_ANY);
    if(!capture){
        exit(1);
    }
    frame = cvQueryFrame(capture);
    cvNamedWindow("testCV", 1);

    while(frame = cvQueryFrame(capture)){
        if(!frame){
            exit(2);
        }
        cvShowImage("testCV", frame);
        cvWaitKey(1);
    }
    cvReleaseImage(&frame);
    cvReleaseCapture(&capture);
}

int main(){
    //Method 1: without boost::thread, works fine
    testCVfunc();

    //Method 2: with boost::thread, show black screen
    char entree;
    boost::thread threadTestCV = boost::thread(&testCVfunc);
    std::cin >> entree;
}

As the comments say, testCVfunc does its job if I don't call it from a boost::thread, but I get a black screen if I use boost::thread. I don't get the problem, maybe someone does?

Thank you for your help.

回答1:

I've seen some problems when OpenCV is being executed from a secondary thread and it's difficult to pinpoint the origin of the problem when the behavior is not consistent on all platforms.

For instance, your source code worked perfectly with OpenCV 2.3.0 on Mac OS X 10.7.2. I don't know what platform you are using, but the fact that it worked on my computer indicates that OpenCV has some implementation issues with the platform you are using.

Now, if you can't move OpenCV's code to the primary thread, then you might want to start thinking about creating a 2nd program to handle all OpenCV related tasks, and use some sort of IPC mechanism to allow this program to communicate with your main application.



回答2:

I solved the problem by calling

cvCreateCameraCapture(CV_CAP_ANY);

in the main thread, even if it doesn't really answer the question:

why is this not working? question.

Hope this can help someone else.



回答3:

Try calling cv::startWindowThread(); in the main app and then creating a window within your thread. This worked for me.