我们本节学习如何利用 OpenCV
中的 VideoCapture
类,来对视频进行读取显示,以及调用摄像头。
VideoCapture
它提供了从摄像机或视频文件捕获视频的 C++
接口, 作用是从视频文件或从摄像头捕获视频并显示出来。
1. 读取并播放视频
VideoCapture
读入视频方法有两种:
- 先实例化再初始化:
VideoCapture capture;
capture.open("demo.mp4");
- 在实例化的同时进行初始化:
VideoCapture capture("demo.mp4");
这两种写法的区别就如我们定义一个 int
类型的变量一样:
int a;
a = 1;
为先定义再初始化,而
int a = 1;
为在定义时初始化。
完整代码:
#include <iostream>
#include "opencv2/opencv.hpp"
using namespace cv;
int main()
{
VideoCapture capture("demo.mp4"); // 读入视频
if(!capture.isOpened()) // 判断文件是否正确打开
{
std::cout << "video not exist";
return -1;
}
while(1) // 循环显示每一帧
{
Mat frame; // 定义一个Mat 变量, 用于存储每一帧的图像
capture >> frame; // 读取当前帧到 Mat 变量中
imshow("读取视频", frame); // 显示当前帧
waitKey(30); // 延时 30 ms
}
capture.release(); //释放资源
return 0;
}
2. 通过摄像头采集视频
要调用摄像头进行视频采集的话,将代码
VideoCapture capture("demo.mp4")
替换为
VideoCapture capture(0)
表示从摄像头而不是从文件中读取视频。其它代码和通过读取视频文件播放视频代码一致,完整代码如下:
#include <iostream>
#include "opencv2/opencv.hpp"
using namespace cv;
int main()
{
VideoCapture capture(0); // 读入视频
if(!capture.isOpened()) // 判断文件是否正确打开
{
std::cout << "video not exist";
return -1;
}
while(1) // 循环显示每一帧
{
Mat frame; // 定义一个Mat 变量, 用于存储每一帧的图像
capture >> frame; // 读取当前帧到 Mat 变量中
imshow("读取视频", frame); // 显示当前帧
waitKey(30); // 延时 30 ms
}
capture.release(); //释放资源
return 0;
}
3. 采集视频并做 canny 检测
我们还可以用上面的摄像头调用示例程序来配合 canny
边缘检测, 得到 canny
边缘检测并高斯模糊后的摄像头采集视频,源码如下:
#include <iostream>
#include "opencv2/opencv.hpp"
using namespace cv;
int main()
{
VideoCapture capture(0); // 从摄像头读入视频
if(!capture.isOpened()) // 判断文件是否正确打开
{
std::cout << "video not exist";
return -1;
}
Mat edges;
while(1) // 循环显示每一帧
{
Mat frame; // 定义一个Mat 变量, 用于存储每一帧的图像
capture >> frame; // 读取当前帧到 Mat 变量中
cvtColor(frame, edges, COLOR_BGR2GRAY); // 转换 BGR 图为灰度图
// 使用 3x3 内核降噪 2x3+1=7
blur(edges, edges, Size(7, 7)); // 进行模糊
// 进行 canny 边缘检测并显示
Canny(edges, edges, 0, 30, 3);
imshow("边缘检测并模糊后的视频", edges); // 显示当前帧
waitKey(30); // 延时 30 ms
}
capture.release(); //释放资源
return 0;
}