关于highgui库
HighGui是一个可以移植的图形工具包。
OpenCV将与操作系统,文件系统,摄像机之类的硬件进行交互的一些函数纳入HighGui(high-level graphical user interface)库中,有了HighGui,我们可以方便的打开窗口,显示图像,读出或者写入图像相关的文件(包含图像与视屏),处理简单的鼠标,光标和键盘事件。也可以使用HighGui创建其他一些很有用的控件,如滑动条,并把它加入窗口。
头文件:#include “opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
关于<fstream>:具体见c++复习篇:()
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include <iostream>
#include <fstream>
using namespace std;
int g_slider_position = 0;
int g_run = 1, g_dontset = 0;
cv::VideoCapture g_cap;
void onTrackbarSlide(int pos, void*)
{
g_cap.set(cv::CAP_PROP_POS_FRAMES, pos);
if (!g_dontset)
g_run = 1;
g_dontset = 0;
}
int main()
{
cv::namedWindow("金克拉",cv::WINDOW_AUTOSIZE);
g_cap.open("C:/Users/86136/Desktop/opencv学习/图片输出测试/test_2.mp4");
int frames = (int)g_cap.get(cv::CAP_PROP_FRAME_COUNT);
int tmpw = (int)g_cap.get(cv::CAP_PROP_FRAME_WIDTH);
int tmph = (int)g_cap.get(cv::CAP_PROP_FRAME_HEIGHT);
cout << "VIDEO has " << frames << "frames of dimensions(" << tmpw << "," << tmph << ")." << endl;
cv::createTrackbar("Position", "金克拉", &g_slider_position, frames, onTrackbarSlide);
cv::Mat frame;
while (1)
{
if (g_run != 0)
{
g_cap >> frame;
if (frame.empty())
break;
int current_pos = (int)g_cap.get(cv::CAP_PROP_POS_FRAMES);
g_dontset = 1;
cv::setTrackbarPos("Position", "金克拉", current_pos);
cv::imshow("金克拉", frame);
g_run -= 1;
}
char c = (char)cv::waitKey(10);
if (c == 's')
{
g_run = 1;
cout << "single step run=" << g_run << endl;
}
if (c == 'r')
{
g_run = -1;
cout << "Run mode run=" << g_run << endl;
}
if (c == 27)
break;
}
return 0;
}
以下是加入了滑动条的视频编程:
(1)全局变量设置:
(编程规范:全局变量加g_xxx)
int g_slider_position = 0; 储存滑动条位置
int g_run = 1; 每次有新跳转时,置0 ; 正数则是在停止之前要放的图片数目;负数则是视频连续播放模式
int g_dontset = 0; 避免触发单步模式,在滑动时候
cv::VideoCapture g_cap; 帧读取结构
(2)调整滑动条的回调程序:
void onTrackbarSlide(int pos, void*)
{
g_cap.set(cv::CAP_PROP_POS_FRAMES, pos); if (!g_dontset)
g_run = 1;
g_dontset = 0;}
CAP_PROP_POS_FRAMES:
应该指的是当前进度条所在位置
g_cap.set(propld,value):
修改,value就是你想要设置成的新值。
if (!g_dontset)
g_run = 1; 因为跳转,g_run置1
g_dontset = 0; 避免触发单步模式,在滑动时候
(3)关于主函数:
int main()
{
cv::namedWindow("金克拉",cv::WINDOW_AUTOSIZE);
g_cap.open("C:/Users/86136/Desktop/opencv学习/图片输出测试/test_2.mp4");
int frames = (int)g_cap.get(cv::CAP_PROP_FRAME_COUNT);
int tmpw = (int)g_cap.get(cv::CAP_PROP_FRAME_WIDTH);
int tmph = (int)g_cap.get(cv::CAP_PROP_FRAME_HEIGHT);
cout << "VIDEO has " << frames << "frames of dimensions(" << tmpw << "," << tmph << ")." << endl;
cv::createTrackbar("Position", "金克拉", &g_slider_position, frames, onTrackbarSlide);
cv::Mat frame;
while (1)
{
if (g_run != 0)
{
g_cap >> frame;
if (frame.empty())
break;
int current_pos = (int)g_cap.get(cv::CAP_PROP_POS_FRAMES);
g_dontset = 1;
cv::setTrackbarPos("Position", "金克拉", current_pos);
cv::imshow("金克拉", frame);
g_run -= 1;
}
char c = (char)cv::waitKey(10);
if (c == 's')
{
g_run = 1;
cout << "single step run=" << g_run << endl;
}
if (c == 'r')
{
g_run = -1;
cout << "Run mode run=" << g_run << endl;
}
if (c == 27)
break;
}
return 0;
}
关于g_cap.open("C:/Users/86136/Desktop/opencv学习/图片输出测试/test_2.mp4")以及cv::VideoCapture类
OpenCV将会打开文件并做好准备读取它,如果打开成功,我们将可以开始读取视频的帧,并且cv::VideoCapture的成员函数isOpened()将会返回true
详见
int frames = (int)g_cap.get(cv::CAP_PROP_FRAME_COUNT);
int tmpw = (int)g_cap.get(cv::CAP_PROP_FRAME_WIDTH);
int tmph = (int)g_cap.get(cv::CAP_PROP_FRAME_HEIGHT);
这三个就是对已经打开的视频获取相关信息;
cv::createTrackbar("Position", "金克拉", &g_slider_position, frames, onTrackbarSlide);
/* create trackbar and display it on top of given window, set callback */
CVAPI(int) cvCreateTrackbar( const char* trackbar_name, const char* window_name,
int* value, int count, CvTrackbarCallback on_change CV_DEFAULT(NULL));
trackbar_name 被创建的trackbar名字。
window_name 窗口名字,这个窗口将为被创建trackbar的父对象。
value 整数指针,它的值将反映滑块的位置。这个变量指定创建时的滑块位置。
count 滑块位置的最大值。最小值一直是0。
on_change 每次滑块位置被改变的时候,被调用函数的指针。这个函数应该被声明为void Foo(int); 如果没有回调函数,这个值可以设为NULL。
函数cvCreateTrackbar用指定的名字和范围来创建trackbar(滑块或者范围控制),指定与trackbar位置同步的变量,并且指定当trackbar位置被改变的时候调用的回调函数。
(画个饼:被创建的trackbar默认显示在指定窗口的顶端,可以通过函数cvGetTrackbarPos来获取trackbar显示的位置信息,以及通过函数cvSetTrackbarPos来重新设置trackbar的显示位置)
以上详见:
cv::Mat frame;
专门存储图像的数据结构
循环里面的代码分析:
while (1)
{
if (g_run != 0)
{
g_cap >> frame;
if (frame.empty())
break;
int current_pos = (int)g_cap.get(cv::CAP_PROP_POS_FRAMES);
g_dontset = 1;
cv::setTrackbarPos("Position", "金克拉", current_pos);
cv::imshow("金克拉", frame);
g_run -= 1;
}
char c = (char)cv::waitKey(10);
if (c == 's')
{
g_run = 1;
cout << "single step run=" << g_run << endl;
}
if (c == 'r')
{
g_run = -1;
cout << "Run mode run=" << g_run << endl;
}
if (c == 27)
break;
}
首先第一个判断(视频没有结束)下:
将一帧赋值给frame;
判断frame是否为空,为空则退出;
强制类型转换int类型,将视频当前所处在的帧数赋值给current_pos
g_dontset=1
setTrackbarPos函数:("position","金克拉",current_pos)
展示当前帧的图片
g_run自减一(因为距离播放结束,少了一张图片)
char c = (char)cv::waitKey(10);
这个是每次while循环监测输入的字母,作出相应的操作
if (c == 's')
{
g_run = 1;
cout << "single step run=" << g_run << endl;
}
if (c == 'r')
{
g_run = -1;
cout << "Run mode run=" << g_run << endl;
}
if (c == 27)
break;
这里是三个if判断语句:
1,输入s则g_run赋值为1,然后下一次循环里面,g_run 自减1,变成0,在下一次循环,if语句内的语句不执行,于是视频停止放映
2,输入r g_run赋值为-1 ,下次,下下n次循环,不断趋近-无穷大,于是乎,视频里的图片连续播放
3,27是esc,退出程序