【opencv】C++ 读取视频创建单通道视频

46 篇文章 4 订阅
#include <iostream> // for standard I/O
#include <string>   // for strings
#include <opencv2/core.hpp>     // Basic OpenCV structures (cv::Mat)
#include <opencv2/videoio.hpp>  // Video write
using namespace std;
using namespace cv;
static void help()
{
    cout
        << "------------------------------------------------------------------------------" << endl
        << "这个程序展示了如何编写视频文件."                                   << endl
        << "您可以提取输入视频的 R 或 G 或 B 颜色通道."              << endl
        << "Usage:"                                                                         << endl
        << "./video-write <input_video_name> [ R | G | B] [Y | N]"                          << endl
        << "------------------------------------------------------------------------------" << endl
        << endl;
}
int main(int argc, char *argv[])
{
    help();
    if (argc != 4)
    {
        cout << "Not enough parameters" << endl;
        return -1;
    }
    const string source      = argv[1];           //源文件名
    const bool askOutputType = argv[3][0] =='Y';  //如果为 false,它将使用输入编解码器类型  
    VideoCapture inputVideo(source);              // 打开输入
    if (!inputVideo.isOpened())
    {
        cout  << "无法打开输入视频: " << source << endl;
        return -1;
    }
    string::size_type pAt = source.find_last_of('.');                  // 查找扩展点 Find extension point
    const string NAME = source.substr(0, pAt) + argv[2][0] + ".avi";   //  形成容器新名称
    int ex = static_cast<int>(inputVideo.get(CAP_PROP_FOURCC));     //获取编码器类型 整型  Get Codec Type- Int form
    // 通过位运算符从 int 转换为 char          Transform from int to char via Bitwise operators
    char EXT[] = {(char)(ex & 0XFF) , (char)((ex & 0XFF00) >> 8),(char)((ex & 0XFF0000) >> 16),(char)((ex & 0XFF000000) >> 24), 0};
    Size S = Size((int) inputVideo.get(CAP_PROP_FRAME_WIDTH),    //获取输入尺寸  Acquire input size
                  (int) inputVideo.get(CAP_PROP_FRAME_HEIGHT));
    VideoWriter outputVideo;                                        //打开输出  Open the output
    if (askOutputType)
        outputVideo.open(NAME, ex=-1, inputVideo.get(CAP_PROP_FPS), S, true);
    else
        outputVideo.open(NAME, ex, inputVideo.get(CAP_PROP_FPS), S, true);
    if (!outputVideo.isOpened())
    {
        cout  << "无法打开输出视频进行写入: " << source << endl;
        return -1;
    }
    cout << "Input frame resolution: Width=" << S.width << "  Height=" << S.height
         << " of nr#: " << inputVideo.get(CAP_PROP_FRAME_COUNT) << endl;
    cout << "输入编码器类型Input codec type: " << EXT << endl;
    int channel = 2; //选择要保存的通道  Select the channel to save
    switch(argv[2][0])
    {
    case 'R' : channel = 2; break;
    case 'G' : channel = 1; break;
    case 'B' : channel = 0; break;
    }
    Mat src, res;
    vector<Mat> spl;
    for(;;) //显示在窗口中捕获的图像并重复 Show the image captured in the window and repeat
    {
        inputVideo >> src;              // 读取read
        if (src.empty()) break;         // 检查是否到结束check if at end
        split(src, spl);                // 处理 - 仅提取正确的通道 process - extract only the correct channel
        for (int i =0; i < 3; ++i)
            if (i != channel)
                spl[i] = Mat::zeros(S, spl[0].type());//其他通道设置为0
       merge(spl, res);//混合后输出
       //outputVideo.write(res); //save or
       outputVideo << res;//写入视频文件
    }
    cout << "Finished writing" << endl;
    return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值