OpenCV中更新窗口的waitKey()替代方法是什么?

3

到目前为止,我看到的所有示例和书籍都建议使用waitKey(1)强制重绘OpenCV窗口。这看起来很奇怪,而且太hacky了。

有没有其他替代方法?我尝试过cv::updateWindow,但它似乎需要OpenGL,因此会崩溃。我在Windows上使用VC++。


1
根据文档,这是唯一一个执行事件处理的方法。查看代码(modules\highgui\src\window_w32.cpp),它是一个相当简单的消息泵,你可以轻松地编写自己修改过的版本——去掉按键检查、睡眠等。 - Dan Mašek
这相当糟糕。我正在使用Python的OpenCV - 在这种环境下有什么替代品? - WestCoastProjects
1个回答

4

我查看了源代码,就像 @Dan Masek所说的那样,似乎没有其他的函数来处理Windows消息。 所以我最终编写了自己的小型DoEvents()函数用于VC++。以下是使用OpenCV逐帧显示视频帧并跳过所需帧数的完整源代码。

#include <windows.h>
#include <iostream>
#include "opencv2/opencv.hpp"

using namespace cv;
using namespace std;
bool DoEvents();

int main(int argc, char *argv[])
{
    VideoCapture cap(argv[1]);
    if (!cap.isOpened())
        return -1;

    namedWindow("tree", CV_GUI_EXPANDED | CV_WINDOW_AUTOSIZE);
    double frnb(cap.get(CV_CAP_PROP_FRAME_COUNT));
    std::cout << "frame count = " << frnb << endl;

    for (double fIdx = 0; fIdx < frnb; fIdx += 50) {
        Mat frame;
        cap.set(CV_CAP_PROP_POS_FRAMES, fIdx);
        bool success = cap.read(frame);
        if (!success) {
            cout << "Cannot read  frame " << endl;
            break;
        }
        imshow("tree", frame);
        if (!DoEvents())
            return 0;
    }
    return 0;
}

bool DoEvents()
{
    MSG msg;
    BOOL result;

    while (::PeekMessage(&msg, NULL, 0, 0, PM_NOREMOVE))
    {
        result = ::GetMessage(&msg, NULL, 0, 0);
        if (result == 0) // WM_QUIT
        {
            ::PostQuitMessage(msg.wParam);
            return false;
        }
        else if (result == -1)
            return true;    //error occured
        else
        {
            ::TranslateMessage(&msg);
            ::DispatchMessage(&msg);
        }
    }

    return true;
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接