OpenCV 检查机器上是否安装了视频编解码器 (C++)
OpenCV checking if video-codec is installed on machine (C++)
问题:
我想实现一个安全版本以通过 OpenCV 将数据处理成视频,这应该适用于 Windows、Mac 和 Linux。数据必须保存在无损视频编解码器中。
在我目前的设置下保存文件完全没有问题,而且我知道使用-1
as fourcc
with videoWriter
会弹出一个window。
我不能保证的是系统完全有能力显示 window !所以弹出菜单可以作为后备方案,但不是主要解决方案。
问题:
有没有办法检查 OpenCV 是否在机器上安装了特定的视频编解码器而没有 运行 编译问题?类似于:
if (`codec installed`)
int codec = opencvfourcc(codec)
else
int codec = -1
OpenCV 使用 FFmpeg
解码视频文件。因此,如果 OpenCV 已在系统上使用 FFmpeg 版本构建,那么我们可以使用 FFmpeg 命令行来检查我们选择的编解码器的可用性。对于来自 C++ 的 运行 系统命令,我使用了来自 here. This post 的代码详细说明了如何检查 OS 类型。
#include <cstdio>
#include <iostream>
#include <memory>
#include <stdexcept>
#include <string>
#include <array>
#if defined(_WIN32) || defined(_WIN64)
#define OS_WINDOWS
#elif defined(__APPLE__) || defined(__MACH__)
#define OS_OSX
#elif defined(__linux__)
#define OS_LINUX
#endif
std::string exec(const std::string& command ) {
const char* cmd = command.c_str();
std::array<char, 128> buffer;
std::string result;
#if defined(OS_WINDOWS)
std::shared_ptr<FILE> pipe(_popen(cmd, "r"), _pclose);
#elif defined(OS_LINUX) || defined (OS_OSX)
std::shared_ptr<FILE> pipe(popen(cmd, "r"), pclose);
#endif
if (!pipe) throw std::runtime_error("popen() failed!");
while (!feof(pipe.get())) {
if (fgets(buffer.data(), 128, pipe.get()) != nullptr)
result += buffer.data();
}
return result;
}
int main() {
// codec of choice
std::string codec = "H264";
// if OS is linux or OSX then use FFmpeg with grep command
#if defined (OS_LINUX) || defined (OS_OSX)
std::string command = "ffmpeg -codecs | grep -i ";
// if WINDOWS then FFmpeg with findstr
#elif defined (OS_WINDOWS)
std::string command = "ffmpeg -codecs | findstr /i ";
#endif
// execute the system command and get the output
std::string str = exec(command+codec);
// if the output string contains the letters DEV then FFmpeg supports the codec
// D: Decoding supported
// E: Encoding supported
// V: Video codec
std::size_t found = str.find("DEV");
if(found != std::string::npos)
std::cout<<"Codec Found"<<std::endl;
return 0;
}
问题:
我想实现一个安全版本以通过 OpenCV 将数据处理成视频,这应该适用于 Windows、Mac 和 Linux。数据必须保存在无损视频编解码器中。
在我目前的设置下保存文件完全没有问题,而且我知道使用-1
as fourcc
with videoWriter
会弹出一个window。
我不能保证的是系统完全有能力显示 window !所以弹出菜单可以作为后备方案,但不是主要解决方案。
问题:
有没有办法检查 OpenCV 是否在机器上安装了特定的视频编解码器而没有 运行 编译问题?类似于:
if (`codec installed`)
int codec = opencvfourcc(codec)
else
int codec = -1
OpenCV 使用 FFmpeg
解码视频文件。因此,如果 OpenCV 已在系统上使用 FFmpeg 版本构建,那么我们可以使用 FFmpeg 命令行来检查我们选择的编解码器的可用性。对于来自 C++ 的 运行 系统命令,我使用了来自 here. This post 的代码详细说明了如何检查 OS 类型。
#include <cstdio>
#include <iostream>
#include <memory>
#include <stdexcept>
#include <string>
#include <array>
#if defined(_WIN32) || defined(_WIN64)
#define OS_WINDOWS
#elif defined(__APPLE__) || defined(__MACH__)
#define OS_OSX
#elif defined(__linux__)
#define OS_LINUX
#endif
std::string exec(const std::string& command ) {
const char* cmd = command.c_str();
std::array<char, 128> buffer;
std::string result;
#if defined(OS_WINDOWS)
std::shared_ptr<FILE> pipe(_popen(cmd, "r"), _pclose);
#elif defined(OS_LINUX) || defined (OS_OSX)
std::shared_ptr<FILE> pipe(popen(cmd, "r"), pclose);
#endif
if (!pipe) throw std::runtime_error("popen() failed!");
while (!feof(pipe.get())) {
if (fgets(buffer.data(), 128, pipe.get()) != nullptr)
result += buffer.data();
}
return result;
}
int main() {
// codec of choice
std::string codec = "H264";
// if OS is linux or OSX then use FFmpeg with grep command
#if defined (OS_LINUX) || defined (OS_OSX)
std::string command = "ffmpeg -codecs | grep -i ";
// if WINDOWS then FFmpeg with findstr
#elif defined (OS_WINDOWS)
std::string command = "ffmpeg -codecs | findstr /i ";
#endif
// execute the system command and get the output
std::string str = exec(command+codec);
// if the output string contains the letters DEV then FFmpeg supports the codec
// D: Decoding supported
// E: Encoding supported
// V: Video codec
std::size_t found = str.find("DEV");
if(found != std::string::npos)
std::cout<<"Codec Found"<<std::endl;
return 0;
}