• 4.图像处理库libswscale的sws_getContext(),sws_scale(),avdevice_register_all(),gdigrab简记


    原文链接:https://blog.csdn.net/leixiaohua1020/article/details/44305697

      FFmpeg中的图像处理(缩放,YUV/RGB格式转换)类库libswsscale的源代码。libswscale是一个主要用于处理图片像素数据的类库。可以完成图片像素格式的转换,图片的拉伸等工作。有关libswscale的使用可以参考文章:https://blog.csdn.net/leixiaohua1020/article/details/42134965

      它的初始化函数为sws_getContext(),它的数据处理函数为sws_scale()。

      SwsContext是使用libswscale时候一个贯穿始终的结构体。但是我们在使用FFmpeg的类库进行开发的时候,是无法看到它的内部结构的。在libswscaleswscale.h中只能看到一行定义:struct SwsContext;

      它的定义位于libswscaleswscale_internal.h中,(几百行的定义)

      sws_getContext()是初始化SwsContext的函数。

    struct SwsContext *sws_getContext(int srcW, int srcH, enum AVPixelFormat srcFormat,
                                      int dstW, int dstH, enum AVPixelFormat dstFormat,
                                      int flags, SwsFilter *srcFilter,
                                      SwsFilter *dstFilter, const double *param);

    该函数包含以下参数:

    srcW:源图像的宽
    srcH:源图像的高
    srcFormat:源图像的像素格式
    dstW:目标图像的宽
    dstH:目标图像的高
    dstFormat:目标图像的像素格式
    flags:设定图像拉伸使用的算法

     成功执行的话返回生成的SwsContext,否则返回NULL。

      成功执行的话返回生成的SwsContext,否则返回NULL。sws_getContext()的定义位于libswscaleutils.c  

      从sws_getContext()的定义中可以看出,它首先调用了一个函数sws_alloc_context()用于给SwsContext分配内存。然后将传入的源图像,目标图像的宽高,像素格式,以及标志位分别赋值给该SwsContext相应的字段。最后调用一个函数sws_init_context()完成初始化工作。下面我们分别看一下sws_alloc_context()和sws_init_context()这两个函数。
      

      sws_init_context()除了对SwsContext中的各种变量进行赋值之外,主要按照顺序完成了以下一些工作:
    1. 通过sws_rgb2rgb_init()初始化RGB转RGB(或者YUV转YUV)的函数(注意不包含RGB与YUV相互转换的函数)。
    2. 通过判断输入输出图像的宽高来判断图像是否需要拉伸。如果图像需要拉伸,那么unscaled变量会被标记为1。
    3. 通过sws_setColorspaceDetails()初始化颜色空间。
    4. 一些输入参数的检测。例如:如果没有设置图像拉伸方法的话,默认设置为SWS_BICUBIC;如果输入和输出图像的宽高小于等于0的话,也会返回错误信息。
    5. 初始化Filter。这一步根据拉伸方法的不同,初始化不同的Filter。
    6. 如果flags中设置了“打印信息”选项SWS_PRINT_INFO,则输出信息。
    7. 如果不需要拉伸的话,调用ff_get_unscaled_swscale()将特定的像素转换函数的指针赋值给SwsContext中的swscale指针。
    8. 如果需要拉伸的话,调用ff_getSwsFunc()将通用的swscale()赋值给SwsContext中的swscale指针(这个地方有点绕,但是确实是这样的)。
      

    1.初始化RGB转RGB(或者YUV转YUV)的函数。注意这部分函数不包含RGB与YUV相互转换的函数。

    sws_rgb2rgb_init()

    sws_rgb2rgb_init()的定义位于libswscale gb2rgb.c,

    从sws_rgb2rgb_init()代码中可以看出,有两个初始化函数:rgb2rgb_init_c()是初始化C语言版本的RGB互转(或者YUV互转)的函数,rgb2rgb_init_x86()则是初始化X86汇编版本的RGB互转的函数。
    PS:在libswscale中有一点需要注意:很多的函数名称中包含类似“_c”这样的字符串,代表了该函数是C语言写的。与之对应的还有其它标记,比如“_mmx”,“sse2”等。
      C语言版本的RGB互转函数的初始化函数rgb2rgb_init_c(),定义位于libswscale gb2rgb_template.c,

    可以看出rgb2rgb_init_c()执行后,会把C语言版本的图像格式转换函数赋值给系统的函数指针。

      rgb24tobgr24_c()完成了RGB24向BGR24格式的转换。函数的定义如下所示。从代码中可以看出,该函数实现了“R”与“B”之间位置的对调,从而完成了这两种格式之间的转换。

      rgb24to16_c()完成了RGB24向RGB16像素格式的转换。

      yuyvtoyuv422_c()完成了YUYV向YUV422像素格式的转换。

      该函数将YUYV像素数据分离成为Y,U,V三个分量的像素数据。其中extract_even_c()用于获取一行像素中序数为偶数的像素,对应提取了YUYV像素格式中的“Y”。extract_odd2_c()用于获取一行像素中序数为奇数的像素,并且把这些像素值再次按照奇偶的不同,存储于两个数组中。对应提取了YUYV像素格式中的“U”和“V”。
      rgb2rgb_init_x86()用于初始化基于X86汇编语言的RGB互转的代码。由于对汇编不是很熟,不再作详细分析。

      

      可以看出,rgb2rgb_init_x86()首先调用了av_get_cpu_flags()获取CPU支持的特性,根据特性调用rgb2rgb_init_mmx(),rgb2rgb_init_3dnow(),rgb2rgb_init_mmxext(),rgb2rgb_init_sse2(),rgb2rgb_init_avx()等函数。

      

    2.判断图像是否需要拉伸。

    这一步主要通过比较输入图像和输出图像的宽高实现。系统使用一个unscaled变量记录图像是否需要拉伸,如下所示。

    unscaled = (srcW == dstW && srcH == dstH);

    3.初始化颜色空间。

    初始化颜色空间通过函数sws_setColorspaceDetails()完成。sws_setColorspaceDetails()是FFmpeg的一个API函数,它的声明如下所示:

    int sws_setColorspaceDetails(struct SwsContext *c, const int inv_table[4],
                                 int srcRange, const int table[4], int dstRange,
                                 int brightness, int contrast, int saturation);

    简单解释一下几个参数的含义:
    c:需要设定的SwsContext。
    inv_table:描述输出YUV颜色空间的参数表。
    srcRange:输入图像的取值范围(“1”代表JPEG标准,取值范围是0-255;“0”代表MPEG标准,取值范围是16-235)。
    table:描述输入YUV颜色空间的参数表。
    dstRange:输出图像的取值范围。
    brightness:未研究。
    contrast:未研究。
    saturation:未研究。
      

      其他雷神博客也还有,可去看。。。。。

      

  • 相关阅读:
    域渗透基础(二)
    域渗透基础(一)
    域环境搭建
    java基础(五)-----new一个对象的具体过程
    数据结构(八)-----散列表
    数据结构(七)-----跳表
    数据结构(六)-----队列
    数据结构(五)-----栈
    数据结构(四)-----链表
    数据结构(三)-----数组
  • 原文地址:https://www.cnblogs.com/wddx5/p/13306503.html
Copyright © 2020-2023  润新知