【问题标题】:OpenCV QT, Displaying Frames of a Video (Not using a While Loop)OpenCV QT,显示视频帧(不使用 While 循环)
【发布时间】:2020-02-04 06:17:39
【问题描述】:

我有一个简单的个人项目,它使用 QT 和 OpenCV 框架在 QLabel 中显示视频。我知道如何转换成 QImage 并设置 Pixmap。

但是,视频在 while 循环下运行得太快,当我检查时,无论我加载哪个视频,fps 都是 29 或 30。 为了解决这个问题,我还实现了一个 QTimer 在视频加载时启动。 我不确定如何使用它来显示具有我需要设置的适当帧速率的帧。

任何想法我可以如何实现这个?

【问题讨论】:

  • 您可以使用QTimer 设置它们也提到了here

标签: c++ qt opencv


【解决方案1】:

我之前在我的项目中做了 mat 到 QImage 的转换。

static QImage Mat2QImage(const cv::Mat3b &src) {
    QImage dest(src.cols, src.rows, QImage::Format_ARGB32);
    for (int y = 0; y < src.rows; ++y) {
        const cv::Vec3b *srcrow = src[y];
        QRgb *destrow = (QRgb*)dest.scanLine(y);
        for (int x = 0; x < src.cols; ++x) {
            destrow[x] = qRgba(srcrow[x][2], srcrow[x][1], srcrow[x][0], 255);
        }
    }
    return dest;
}

用法可能是这样的

void foo::timeout() // A slot which QTimer's timeout signal is connected to
{
    // I didn't tested the code but it should work
    Mat frame;
    m_cap >> frame;
    QImage img = Mat2QImage(frame);

    QPixmap pixmap = QPixmap::fromImage(img);
    ui->streamDisplay->setPixmap(pixmap);
}

据我记得,Mat 图像应该是 ARGB32。它以 30 fps 的速度顺利运行。

我听说最好的性能解决方案是使用 QOpenglWidget,但我不知道如何实现相同的功能。也许你可以看看。

my older repo link

display-code-cpp

image-conversion-cpp

【讨论】:

  • 您好,我已经成功通过QTimer解决了这个问题。感谢您的贡献。会看代码
【解决方案2】:

使用while循环并没有错,你只需要正确计算帧率,然后为每个循环休眠,就这样:

int FPS = static_cast<int>(capture.get(cv::CAP_PROP_FPS));
uint delayTime = static_cast<uint>(1000 / FPS);
while(capture.read(frame))
{
    // process the frame 
    ...
    // now sleep (milli secconds)
    QThread::msleep(delayTime);
}

现在视频将以正常速率显示。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-12-03
    • 2012-11-27
    • 1970-01-01
    • 1970-01-01
    • 2017-05-28
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多