在 OpenCV 中使用 H.264 压缩编写视频文件
Writing a video file using H.264 compression in OpenCV
如何使用 OpenCV 中的 VideoWriter class 使用 H.264 压缩编写视频?我基本上想从网络摄像头获取视频并在按下一个字符后保存它。使用 MPEG4 Part 2 压缩时输出的视频文件很大。
当然可以使用VideoWriter
class,但需要使用代表H264标准的the correct FourCC code。 FourCC 代表四字符代码,它是媒体文件中使用的视频编解码器、压缩格式、颜色或像素格式的标识符。
具体来说,当你创建一个VideoWriter
对象时,你在构造它的时候指定了FourCC代码。有关详细信息,请参阅 OpenCV 文档:http://docs.opencv.org/trunk/modules/highgui/doc/reading_and_writing_images_and_video.html#videowriter-videowriter
我假设您使用的是 C++,因此 VideoWriter
构造函数的定义是:
VideoWriter::VideoWriter(const String& filename, int fourcc,
double fps, Size frameSize, bool isColor=true)
filename
是视频文件的输出,fourcc
是您要使用的代码的 FourCC 代码,fps
是所需的帧率,frameSize
是视频的所需尺寸,isColor
指定您是否希望视频是彩色的。尽管 FourCC 使用四个字符,但 OpenCV 有一个实用程序可以解析 FourCC 并输出一个整数 ID,用作查找以便能够将正确的视频格式写入文件。您使用 CV_FOURCC
函数,并指定四个单个字符 - 每个对应于您想要的编解码器的 FourCC 代码中的一个字符。请注意,CV_FOURCC
适用于 OpenCV 2.x。建议您对 OpenCV 3.x 及更高版本使用 cv::Videowriter::fourcc
。
具体来说,您可以这样称呼它:
int fourcc = CV_FOURCC('X', 'X', 'X', 'X');
int fourcc = VideoWriter::fourcc('X', 'X', 'X', 'X');
将X
替换为属于FourCC的每个字符(按顺序)。因为你想要 H264 标准,你会像这样创建一个 VideoWriter
对象:
#include <iostream> // for standard I/O
#include <string> // for strings
#include <opencv2/core/core.hpp> // Basic OpenCV structures (cv::Mat)
#include <opencv2/highgui/highgui.hpp> // Video write
using namespace std;
using namespace cv;
int main()
{
VideoWriter outputVideo; // For writing the video
int width = ...; // Declare width here
int height = ...; // Declare height here
Size S = Size(width, height); // Declare Size structure
// Open up the video for writing
const string filename = ...; // Declare name of file here
// Declare FourCC code - OpenCV 2.x
// int fourcc = CV_FOURCC('H','2','6','4');
// Declare FourCC code - OpenCV 3.x and beyond
int fourcc = VideoWriter::fourcc('H','2','6','4');
// Declare FPS here
double fps = ...;
outputVideo.open(filename, fourcc, fps, S);
// Put your processing code here
// ...
// Logic to write frames here... see below for more details
// ...
return 0;
}
或者,您可以在声明 VideoWriter
对象时简单地执行此操作:
VideoWriter outputVideo(filename, fourcc, fps, S);
如果您使用上述方法,则不需要调用 open
,因为这会自动打开编写器以将帧写入文件。
如果您不确定您的计算机是否支持 H.264,请指定 -1
作为 FourCC 代码,当您 运行显示计算机上所有可用视频编解码器的代码。我想提一下,这仅适用于 Windows。当您指定 -1
时,Linux 或 Mac OS 不会弹出此 window。换句话说:
VideoWriter outputVideo(filename, -1, fps, S);
如果您的计算机上不存在 H.264,您可以选择最合适的。完成后,OpenCV 将创建正确的 FourCC 代码以输入到 VideoWriter
构造函数中,这样您将获得一个 VideoWriter 实例,该实例表示 VideoWriter
将那种类型的视频写入文件。
一旦你准备好一个帧,存储在 frm
中以写入文件,你可以执行以下任一操作:
outputVideo << frm;
或
outputVideo.write(frm);
作为奖励,这里有一个关于如何在 OpenCV 中制作 read/write 视频的教程:http://docs.opencv.org/3.0-beta/doc/py_tutorials/py_gui/py_video_display/py_video_display.html - 然而,它是为 Python 编写的,但最好知道的是接近在 link 的底部,有一个已知适用于每个操作系统的 FourCC 代码列表。顺便说一句,他们为 H264 标准指定的 FourCC 代码实际上是 'X','2','6','4'
,因此如果 'H','2','6','4'
不起作用,请将 H
替换为 X
。
又是一个小记。如果你使用的是MacOS,那么你需要使用的是'A','V','C','1'
或者'M','P','4','V'
。根据经验,'H','2','6','4'
或'X','2','6','4'
尝试指定 FourCC 代码时似乎不起作用。
正如 rayryeng 所述,您需要将正确的 FourCC 代码传递给 VideoWriter
。
对于 H.264,大多数人使用 AVC,它看起来像这样:
cv2.VideoWriter_fourcc('a','v','c','1')
mp4v
似乎也适用于许多人。如果它们都没有,请检查您的可用编解码器列表。
如何使用 OpenCV 中的 VideoWriter class 使用 H.264 压缩编写视频?我基本上想从网络摄像头获取视频并在按下一个字符后保存它。使用 MPEG4 Part 2 压缩时输出的视频文件很大。
当然可以使用VideoWriter
class,但需要使用代表H264标准的the correct FourCC code。 FourCC 代表四字符代码,它是媒体文件中使用的视频编解码器、压缩格式、颜色或像素格式的标识符。
具体来说,当你创建一个VideoWriter
对象时,你在构造它的时候指定了FourCC代码。有关详细信息,请参阅 OpenCV 文档:http://docs.opencv.org/trunk/modules/highgui/doc/reading_and_writing_images_and_video.html#videowriter-videowriter
我假设您使用的是 C++,因此 VideoWriter
构造函数的定义是:
VideoWriter::VideoWriter(const String& filename, int fourcc,
double fps, Size frameSize, bool isColor=true)
filename
是视频文件的输出,fourcc
是您要使用的代码的 FourCC 代码,fps
是所需的帧率,frameSize
是视频的所需尺寸,isColor
指定您是否希望视频是彩色的。尽管 FourCC 使用四个字符,但 OpenCV 有一个实用程序可以解析 FourCC 并输出一个整数 ID,用作查找以便能够将正确的视频格式写入文件。您使用 CV_FOURCC
函数,并指定四个单个字符 - 每个对应于您想要的编解码器的 FourCC 代码中的一个字符。请注意,CV_FOURCC
适用于 OpenCV 2.x。建议您对 OpenCV 3.x 及更高版本使用 cv::Videowriter::fourcc
。
具体来说,您可以这样称呼它:
int fourcc = CV_FOURCC('X', 'X', 'X', 'X');
int fourcc = VideoWriter::fourcc('X', 'X', 'X', 'X');
将X
替换为属于FourCC的每个字符(按顺序)。因为你想要 H264 标准,你会像这样创建一个 VideoWriter
对象:
#include <iostream> // for standard I/O
#include <string> // for strings
#include <opencv2/core/core.hpp> // Basic OpenCV structures (cv::Mat)
#include <opencv2/highgui/highgui.hpp> // Video write
using namespace std;
using namespace cv;
int main()
{
VideoWriter outputVideo; // For writing the video
int width = ...; // Declare width here
int height = ...; // Declare height here
Size S = Size(width, height); // Declare Size structure
// Open up the video for writing
const string filename = ...; // Declare name of file here
// Declare FourCC code - OpenCV 2.x
// int fourcc = CV_FOURCC('H','2','6','4');
// Declare FourCC code - OpenCV 3.x and beyond
int fourcc = VideoWriter::fourcc('H','2','6','4');
// Declare FPS here
double fps = ...;
outputVideo.open(filename, fourcc, fps, S);
// Put your processing code here
// ...
// Logic to write frames here... see below for more details
// ...
return 0;
}
或者,您可以在声明 VideoWriter
对象时简单地执行此操作:
VideoWriter outputVideo(filename, fourcc, fps, S);
如果您使用上述方法,则不需要调用 open
,因为这会自动打开编写器以将帧写入文件。
如果您不确定您的计算机是否支持 H.264,请指定 -1
作为 FourCC 代码,当您 运行显示计算机上所有可用视频编解码器的代码。我想提一下,这仅适用于 Windows。当您指定 -1
时,Linux 或 Mac OS 不会弹出此 window。换句话说:
VideoWriter outputVideo(filename, -1, fps, S);
如果您的计算机上不存在 H.264,您可以选择最合适的。完成后,OpenCV 将创建正确的 FourCC 代码以输入到 VideoWriter
构造函数中,这样您将获得一个 VideoWriter 实例,该实例表示 VideoWriter
将那种类型的视频写入文件。
一旦你准备好一个帧,存储在 frm
中以写入文件,你可以执行以下任一操作:
outputVideo << frm;
或
outputVideo.write(frm);
作为奖励,这里有一个关于如何在 OpenCV 中制作 read/write 视频的教程:http://docs.opencv.org/3.0-beta/doc/py_tutorials/py_gui/py_video_display/py_video_display.html - 然而,它是为 Python 编写的,但最好知道的是接近在 link 的底部,有一个已知适用于每个操作系统的 FourCC 代码列表。顺便说一句,他们为 H264 标准指定的 FourCC 代码实际上是 'X','2','6','4'
,因此如果 'H','2','6','4'
不起作用,请将 H
替换为 X
。
又是一个小记。如果你使用的是MacOS,那么你需要使用的是'A','V','C','1'
或者'M','P','4','V'
。根据经验,'H','2','6','4'
或'X','2','6','4'
尝试指定 FourCC 代码时似乎不起作用。
正如 rayryeng 所述,您需要将正确的 FourCC 代码传递给 VideoWriter
。
对于 H.264,大多数人使用 AVC,它看起来像这样:
cv2.VideoWriter_fourcc('a','v','c','1')
mp4v
似乎也适用于许多人。如果它们都没有,请检查您的可用编解码器列表。