ffmpeg学习笔记

10年前
ffmpeg的一流设计, 让我震撼, 浑然天成的代码, 让我为之着迷.

ffmpeg主要划分为几个模块, libavcodec, libavformat, libavutil, libswscale, libavfilter, libavdevice在这几个模块中, libavcodec是个重量级的library, 它包含了一系列的编码解码器的实现和框架, 你可以方便的在这个框架下添加自己的编解码器, 然后使用统一的接口进行调用.

这些模块中, 大多数即是一个单独的模块, 也是一个可以和其它模块互相协调, 比如使用libavformat中的demuxer模块然后再使用libavcodec进行解码, libavformat包含了一系列的muxer和demuxer以及io相关的操作. 

libavformat
其中libavformat有一个非常重要的结构: AVFormatContext
它几乎是ffmpeg中的一颗树, 其成员AVStream可以包含0种或多种流, 在AVStream中又可以包含已经打开的编解码器codec, 另外还有AVIOContext成员, 这个成员的作用就是io了, 你可以重写AVIOContext结构的成员函数read_packet或write_packet等, 来实现从不同介质读取音视频媒体数据(比如从网络、内存或磁盘等),关于ffmpeg的io方面,你还可以在libavformat中自己实现一个 PROTOCOL组件来实现同样的功能, 方法也很简单, 只要实现URLProtocol结构然后取个名字在allformats.c中使用REGISTER_PROTOCOL添加一行注册自己的协议就行了, 其它DEMUXER和MUXDEMUX方法也是相似的, 总结下就是:
libavformat中提供了
AVOutputFormat
AVInputFormat
URLProtocol
三个定义好的结构体, 根据自己需要去实现上面的结构体, 然后在allformats.c的av_register_all函数中添加注册就行了. 

libavcodec
其中libavcodec也有一个非常重要的结构: AVCodecContext
它包含了当前媒体信息的几乎所有参数(什么宽高啊, 运行估计啊, 码率控制啊...), 以及编解码指针(AVCodec), 甚至还可以设置硬件加速相关(如DXVA, linux下的 VAAPI啊). 其中最重要的就属AVCodec了, 它是直接指向编解码器实现, 如果你想自己实现一个编解码添加到libavcodec中, 那么也是非常方便的. 在libavcodec中, 它提供了以下几种功能组件的定义:
AVHWAccel
AVCodec
AVCodecParser
AVBitStreamFilter
方法同libavformat, 比如实现一个使用CoreAVC来解码H264的decodec, 可以定义一个名称, 实现AVCodec中对应的各函数指针, 然后在allcodecs.c中添加注册.