FFmpeg实战之路

本章通过一些小的代码示例介绍 FFmpeg 里面一些基本常用的数据结构 跟 API 函数的使用。

学习 FFmpeg 的使用是比较有难度的,因为音视频封装格式,编码格式纷繁复杂,ffmpeg 里面很多代码都是处理格式兼容的。本章节的所有代码,为了便于初学者学习,删掉了一些兼容处理代码跟错误处理代码,所以不建议在正式环境使用这些代码,相同的功能,建议你直接从 ffmpeg.cffplay.cffprobe.c 这 3个文件里面抄代码,他们的兼容处理做得很好。

本章使用的编译环境是 qt creator 跟 msvc。请参考以下文章搭建好开发环境。



常用的结构体如下

1,AVFormatContext ,容器格式上下文,或者叫封装格式上下文。可以理解为 MP4 或者 FLV 的容器。

2,AVPacket,数据包(已编码压缩的数据),这里面的数据通常是一帧视频的数据,或者一帧音频的数据。

AVPacket 他本身是没有编码数据的,他只是管理编码数据。

3,AVCodecContext,这个结构体可以是 编码器 的上下文,也可以是 解码器 的上下文,两者使用的是同一种数据结构。

4,AVCodec,编解码信息。

5,AVCodecParameters,编解码参数。

6,AVFrame ,解码之后的 YUV 数据。AVFrameAVPacket 类似,都是一个管理数据的结构体,他们本身是没有数据的,只是引用了数据。

7,AVDictionary,一个传递参数的通用数据结构。这个结构体主要用来传递参数。


常用的 API 函数如下

1,avformat_open_input,打开输入文件,这个函数会生成 AVFormatContext 。打开输入文件有两种方式,char *filename 或者 AVInputFormat *fmt

2,avformat_find_stream_info ,探测函数,读取输入文件的一部分信息来分析出 各个流的情况。

3,av_packet_alloc,初始化一个 AVPacket

4,av_read_frame,从 AVFormatContext 容器里面读取一个 AVPacket,需要注意,虽然函数名是 frame,但是读取的是 AVPacket

5,av_packet_unref,减少 AVPacket 对 编码数据的引用次数。减到 0 会释放 编码数据的内存。

6,av_packet_free,释放 AVPacket 自身的内存。里面会调 av_packet_unref


1,avcodec_alloc_context3,通过传递 AVCodec 编解码信息来初始化上下文。

2,avcodec_parameters_to_context,把流的 AVCodecParameters 里面的 编解码参数 复制到 AVCodecContext

3,avcodec_open2,打开一个编码器 或者 解码器。

4,avcodec_send_packet,往 AVCodecContext 解码器 发送一个 AVPacket

5,avcodec_receive_frame,从 AVCodecContext 解码器 读取一个 AVFrame


1,avformat_alloc_output_context2,申请一个输出文件上下文,这个函数会生成 AVFormatContext

2,avformat_new_stream,往容器增加一个输出流,可以是音频流,或者视频流,或者一些其他的数据流。

3,avcodec_parameters_from_context,把 AVCodecContext 里面的 编解码参数 复制到输出流AVCodecParameters

4,avio_open2,正式打开输出文件。

5,avformat_write_header,往输出文件写入头信息。

6,av_interleaved_write_frame,把 AVPacket 写入输出文件。


这里我说一下自己个人一些偏面的想法,FFmpeg 的 API 函数的设计,有些地方不是特别好的,他没有对称性,例如有 avformat_open_input 是打开输入文件,却没有一个 avformat_open_ouput 函数来打开输出文件。

可能是我对 FFmpeg 的整体还不太理解。可能存在一些无法逾越的障碍来实现对称性。


参考资料:

1,《ffmpeg tutorial》 - dranger


版权所属 xianwanzhiyin.net 罗上文 2022 all right reserved,powered by Gitbook该文件修订时间: 2022-09-04 23:31:09

results matching ""

    No results matching ""