由于项目需要,计划实现九路视频拼接,因此必须熟悉OpenCV对视频序列的处理。视频信号处理是图像处理的一个延伸,所谓的视频序列是由按一定顺序进行排放的图像组成,即帧(Frame)。在这里,主要记录下如何使用Qt+OpenCV读取视频中的每一帧,之后,在这基础上将一些图像处理的算法运用到每一帧上(如使用Canny算子检测视频中的边缘)。
一. 读取视频序列
OpenCV提供了一个简便易用的框架以提取视频文件和USB摄像头中的图像帧,如果只是单单想读取某个视频,你只需要创建一个cv::VideoCapture实例,然后在循环中提取每一帧。新建一个Qt控制台项目,直接在main函数添加:
#include <QCoreApplication>
#include <opencv2/core/core.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <opencv2/highgui/highgui.hpp>
#include <QDebug>
int main(int argc, char *argv[])
{
QCoreApplication a(argc, argv);
// 读取视频流
cv::VideoCapture capture("e:/BrokeGirls.mkv");
// 检测视频是否读取成功
if (!capture.isOpened())
{
qDebug() << "No Input Image";
return 1;
}
// 获取图像帧率
double rate= capture.get(CV_CAP_PROP_FPS);
bool stop(false);
cv::Mat frame; // 当前视频帧
cv::namedWindow("Extracted Frame");
// 每一帧之间的延迟
int delay= 1000/rate;
// 遍历每一帧
while (!stop)
{
// 尝试读取下一帧
if (!capture.read(frame))
break;
cv::imshow("Extracted Frame",frame);
// 引入延迟
if (cv::waitKey(delay)>=0)
stop= true;
}
return a.exec();
}
(注意:要正确打开视频文件,计算机中必须安装有对应的解码器,否则cv::VideoCapture无法理解视频格式!)运行后,将出现一个窗口,播放选定的视频(需要在创建cv::VideoCapture对象时指定视频的文件名)。
二. 处理视频帧
为了对视频的每一帧进行处理,这里创建自己的类VideoProcessor,其中封装了OpenCV的视频获取框架,该类允许我们指定每帧调用的处理函数。
首先,我们希望指定一个回调处理函数,每一帧中都将调用它。该函数接受一个cv::Mat对象,并输出处理后的cv::Mat对象,其函数签名如下:
void processFrame(cv::Mat& img, cv::Mat& out);
作为这样一个处理函数的例子,以下的Canny函数计算图像的边缘:
// 对视频的每帧做Canny算子边缘检测
void canny(cv::Mat& img, cv::Mat& out)
{
// 先要把每帧图像转化为灰度图
cv::cvtColor(img,out,CV_BGR2GRAY);
// 调用Canny函数
cv::Canny(out,out,100,200);
// 对像素进行翻转
cv::threshold(out,out,128,255,cv::THRESH_BINARY_INV);
}
定义好一个视频处理类,它将与一个回调函数相关联。使用该类,可以创建一个实例,指定输入的视频文件,绑定回调函数,然后开始对每一帧进行处理,要调用这个视频处理类,只需在main函数中添加:
// 定义一个视频处理类处理视频帧
// 首先创建实例
VideoProcessor processor;
// 打开视频文件
processor.setInput("e:/BrokeGirls.mkv");
// 声明显示窗口
// 分别为输入和输出视频
processor.displayInput("Input Video");
processor.displayOutput("Output Video");
// 以原始帧率播放视频
processor.setDelay(1000./processor.getFrameRate());
// 设置处理回调函数
processor.setFrameProcessor(canny);
// 开始帧处理过程
processor.run();
cv::waitKey();
未完待续…
时间: 2024-10-17 11:31:19