ffmeg 反交错「建议收藏」

ffmeg 反交错「建议收藏」ffmeg反交错分类: 多媒体编程2015-01-2009:31 1037人阅读 评论(0) 收藏 举报ffmpeg反交错avfilter过滤器      昨天发现播放TS流(PAL25FPS)时有横纹,查资料找到原因是解码出来的画面是用于隔行扫描显示的画面,需要进行反交错处理成逐行扫描显示画面.因为是帧内交错,所以不要IVTC(IVTC是match场操作


Jetbrains全系列IDE使用 1年只要46元 售后保障 童叟无欺

ffmeg 反交错

分类: 多媒体编程
 
1037人阅读 
评论(0) 
收藏 
举报

      昨天发现播放TS流(PAL 25FPS)时有横纹,查资料找到原因是解码出来的画面是用于隔行扫描显示的画面,需要进行反交错处理成逐行扫描显示画面.因为是帧内交错,所以不要IVTC(IVTC是match场操作,这里已经在同一帧了)。

    在ffmpeg中,进行反交错需要用到avfilter,即图像过滤器,ffmpeg中有很多过滤器,很强大,反交错的过滤器是yadif.

    基本的过滤器使用流程是:

          解码后的画面—>buffer过滤器—->其他过滤器—->buffersink过滤器—>处理完的画面

    所有的过滤器形成了过滤器链,一定要的两个过滤器是buffer过滤器和buffersink过滤器,前者的作用是将解码后的画面加载到过滤器链中,后者的作用是将处理好的画面从过滤器链中读取出来.

    那么进行反交错的过滤器链应该是这样的:

        buffer过滤器—>yadif过滤器—>buffersink过滤器


    过滤器相关的结构体:

    AVFilterGraph: 管理所有的过滤器图像

    AVFilterContext: 过滤器上下文

    AVFilter: 过滤器


    下面来看如何创建过滤器链:

    第一步,创建AVFilterGraph

        AVFilterGraph *filter_graph=avfilter_graph_alloc();

    第二步,获取要使用的过滤器:

        AVFilter *filter_buffer=avfilter_get_by_name(“buffer”);

        AVFilter *filter_yadif=avfilter_get_by_name(“yadif”);

        AVFilter *filter_buffersink=avfilter_get_by_name(“buffersink”);

    第三步,创建过滤器上下文,即AVFilterContext:

        int avfilter_graph_create_filter(AVFilterContext **filt_ctx, const AVFilter *filt,
                                 const char *name, const char *args, void *opaque,
                                 AVFilterGraph *graph_ctx);

    参数说明:filt_ctx用来保存创建好的过滤器上下文,filt是过滤器,name是过滤器名称(在过滤器链中应该唯一),args是传给过滤器的参数(每个过滤器不同,可以在相应的过滤器代码找到),opaque在代码中没有被使用,graph_ctx是过滤器图像管理指针.例:

        AVFilterContext *filter_buffer_ctx,*filter_yadif_ctx,*filter_buffersink_ctx;

        //创建buffer过滤器

        snprintf(args, sizeof(args),
            “video_size=%dx%d:pix_fmt=%d:time_base=%d/%d:pixel_aspect=%d/%d”,
            dec_ctx->width, dec_ctx->height, dec_ctx->pix_fmt,
            dec_ctx->time_base.num, dec_ctx->time_base.den,
            dec_ctx->sample_aspect_ratio.num, dec_ctx->sample_aspect_ratio.den);
        avfilter_graph_create_filter(&filter_buffer_ctx, avfilter_get_by_name(“buffer”), “in”,
                                       args, NULL, filter_graph);

        //创建yadif过滤器

        avfilter_graph_create_filter(&filter_yadif_ctx, avfilter_get_by_name(“yadif”), “yadif”,
                                   “mode=send_frame:parity=auto:deint=interlaced”, NULL, filter_graph);

        //创建buffersink过滤器

        enum AVPixelFormat pix_fmts[] = { AV_PIX_FMT_YUV420P, AV_PIX_FMT_NONE };

        avfilter_graph_create_filter(&filter_buffersink_ctx, avfilter_get_by_name(“buffersink”), “out”,
                                       NULL, NULL,filter_graph);

        av_opt_set_int_list(filter_buffersink_ctx, “pix_fmts”, pix_fmts,
                              AV_PIX_FMT_NONE, AV_OPT_SEARCH_CHILDREN);

    

    第四步,连接过滤器

        avfilter_link(filter_buffer_ctx, 0, filter_yadif_ctx, 0);

        avfilter_link(filter_yadif_ctx, 0, filter_buffersink_ctx, 0);

    第五步,检查所有配置是否正确:

        if ((ret = avfilter_graph_config(player->filter_graph, NULL)) < 0){

            LOGE(0,”avfilter_graph_config:%d\n”,ret);
            goto end;
        }

    注意上面所有的函数都应该检查返回值,这里是略写,到这里如果没出错的话,过滤器链就创建好了.


    如何使用过滤器链进行过滤,主要是使用两个函数:

    //将解码后的frame推送给过滤器链

    int av_buffersrc_add_frame_flags(AVFilterContext *buffer_src,
                                 AVFrame *frame, int flags);

    //将处理完的frame拉取出来:

    int av_buffersink_get_frame(AVFilterContext *ctx, AVFrame *frame);
    例如:

    av_buffersrc_add_frame_flags(filter_buffer_ctx, orgin_frame, AV_BUFFERSRC_FLAG_KEEP_REF);

    while(1){

        ret = av_buffersink_get_frame(filter_buffersink_ctx, frame);
        if (ret == AVERROR(EAGAIN) || ret == AVERROR_EOF){

            break;
        }

        display(frame);

    };


    反交错前的图像和反交错后的图像对比:

    ffmeg 反交错「建议收藏」

    ffmeg 反交错「建议收藏」

    虽然比较模糊,但是横纹确实去掉了.

    找了一下,发现ffmpeg中还有一个反交错的过滤器kerndeint,是GPL授权,使用时要配置打开GPL

    传入参数thresh=0:map=0:order=1:sharp=0:twoway=0后,看来起比yadif要好一些,效果如下图:

    ffmeg 反交错「建议收藏」

    ffmpeg还有一些deinterlace的过滤器,测试发现在过滤时间和画面质量方面,比较好的是pp/lb过滤器。

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/193498.html原文链接:https://javaforall.net

赞 (0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 安装完Ubuntu 15.04桌面后要做的15件事

    安装完Ubuntu 15.04桌面后要做的15件事

    2022年3月2日
  • Jlink或者stlink用于SWD接口下载程序

    Jlink或者stlink用于SWD接口下载程序最近要使用stm32f103c8t6最小系统板,直接ISP串口下载程序太麻烦,就想着使用swd接口来调试。结果:通过SWD接口下载程序成功,但调试失败,还不知原因,会的的人麻烦交流一下。SWD接口:3.3VDIO(数据)CLK(时钟)GND1.首先声明jlink和stlink都有jtag和swd调试功能。jlink接口如下:如图,我使用的就是VCC…

    2022年4月25日
  • MATLAB画图——基础篇「建议收藏」

    MATLAB画图——基础篇「建议收藏」MATLAB画图——基础篇在MATLAB使用的过程中,学会画图是一项必要的技能。在这里,我总结了部分简单的画图函数,同时附上代码(本文中的程序为了方便给出的数据都很简单,大家可以自己去尝试其他数据)。这对刚刚开始接触MATLAB的小白来说,我认为还是很有帮助的。文章目录一、plot()函数1.二维图形(1)绘图选项(2)图形的辅助标注和窗口的分割(3)格式2.三维图形(1)格式(2)网格矩阵生成函数:meshgrid(3)mesh函数(4)surf函数二、特殊图形1.对数坐标图2.极坐标图3.条形图一

    2022年9月20日
  • 机器学习 —— 浅谈贝叶斯和MCMC

    机器学习 —— 浅谈贝叶斯和MCMC‍‍Abstract:最近课业内的任务不是很多,又临近暑假了,就在网上搜了一些有关于机器学习和深度学习的课程进行学习。网上的资料非常繁多,很难甄别,我也是货比三家进行学习…

    2022年5月5日
  • 软件工程与软件测试_软件工程导论(第六版)

    软件工程与软件测试_软件工程导论(第六版)1.软件测试基础2.单元测试3.集成测试4. 确认测试5.白盒测试技术6.黑盒测试技术7.调试8.软件可靠性

    2022年10月4日
  • 永恒之蓝漏洞原理分析_永恒之蓝是谁激活成功教程的

    永恒之蓝漏洞原理分析_永恒之蓝是谁激活成功教程的本文转自行云博客https://www.xy586.top/文章目录摘要前提需要原理漏洞利用摘要什么是永恒之蓝永恒之蓝(EternalBlue)爆发于2017年4月14日晚,是一种利用Windows系统的SMB协议漏洞来获取系统的最高权限,以此来控制被入侵的计算机。甚至于2017年5月12日,不法分子通过改造“永恒之蓝”制作了wannacry勒索病毒,使全世界大范围内遭受了该勒索病毒,甚至波及到学校、大型企业、政府等机构,只能通过支付高额的赎金才能恢复出文件。不过在该病毒出来不久就被微软通.

    2022年10月17日

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号