FFmpeg从入门到入魔(1):初探FFmpeg框架

本文介绍了FFmpeg的基本概念和框架,包括FFmpeg的音视频编解码、复用/解复用、I/O操作。重点分析了FFmpeg中的重要结构体,如AVFormatContext、AVInputFormat、AVOutputFormat、AVCodec和AVFrame,阐述了它们在FFmpeg中的作用和用途。此外,还讨论了FFmpeg命令行工具如ffplay、ffprobe和ffserver的功能。通过理解这些核心结构体,有助于深入掌握FFmpeg的音视频开发。
摘要由CSDN通过智能技术生成

1. FFmpeg介绍与裁剪

1.1 FFmpeg简介


FFmpeg(Fast forword mpeg,音视频转换器)是一个开源免费跨平台的视频和音频流方案,它提供了录制/音视频编解码、转换以及流化音视频的完整解决方案。ffmpeg4.0.2源码目录结构如下:

目录说明:FFmpeg|—compat 该目录存放的是兼容文件,以便兼容早期版本|—doc 说明文档|—ffbuild|—libavcodec 音视频编解码核心库|—libavdevice 各种设备的输入输出,比如Video4Linux2, VfW, DShow以及 ALSA|—libavfilter 滤镜特效处理|—libavformat I/O操作和封装格式(muxer/demuxer)处理|—libavswresample 音频重采样,格式转换和混音|— (1) 重采样:改变音频的采样率,比如从44100HZ降低到8000HZ|— (2)重新矩阵化:改变音频通道数量,比如从立体声道(stereo )变为单身道(mono)|— (3)格式转换:改变音频采样大小,比如将每个样本大小从16bits降低到8bits|—libavutil 工具库,比如算数运算、字符操作等|—libpostproc 后期效果处理,如图像的去块效应|—libswscale 视频像素处理,包括缩放图像尺寸、色彩映射转换、像素颜色空间转换等|—presets|—tests 测试实例|—configure 配置文件,编译ffmpeg时用到

1.2 命令行工具


FFmpeg框架中还提供了几个用于执行命令行完成音视频数据处理工具,包括ffplay、ffprobe、ffserver,具体解释如下:

Fast forword play,用ffmpeg实现的播放

Fast forword server,用ffmpeg实现的rtsp服务器

Fat forword probe,用来输入分析输入流

2. FFmpeg架构分析


在1.1小节中,我们对FFmpeg整体架构进行了简单介绍,阐述了框架中各个模块的功能。本节将在此基础上,重点阐述在利用FFmpeg进行音视频开发中牵涉到的重要步骤,数据结构体以及相关函数。

2.1 FFmpeg处理要点


总体来说,FFmpeg框架主要的作用在于对多媒体数据进行解协议、解封装、解码以及转码等操作,为了对FFmpeg在视音频中的应用有个更直观理解,下面给出解析rtsp网络流的流程图,该图演示了从打开rtsp流,到最终提取出解码数据或转码的大概过程,如下所示:

术语解释:

  • muxer:视音频复用器(封装器),即将视频文件、音频文件和字幕文件(如果有的话)合并为某一个视频格式,比如讲a.avi、a.mp3、a.srt合并为mkv格式的视频文件;

  • demuxer:视音频分离器(解封装器),即muxer的逆过程;

  • transcode:转码,即将视音频数据从某一种格式转换成另一种格式;

  • RTP包:Real-time Transport Protocol,实时传输协议,是一种基于UDP的网络传输协议,它介于应用层和传输层之间,负责对流媒体数据进行封包并实现媒体流的实时传输;

  • ES流:Elementary Streams,即原始流,也称视/音频裸流,是直接从编码器输出的数据流,可为视频数据流(如H.264、MJPEG等)或音频数据流(如AAC等);

  • PES流:Packetized Elementary Streams,分组ES流,PES流是ES流经过PES打包器将ES分组、打包、加入包头信息等处理后形成的数据流,是用来传递ES的一种数据结构。

  • 解协议:取出网络数据流无关报文信息,以获取真正的视音频数据,常见的协议有rtsp、rtmp、http和mms等;

  • 解封装:即demuxer,封装格式可以为.mp4/.avi/.flv/.mkv等;

  • 解码:将编码数据还原成原始内容,比如将H.264解码为YUV、AAC解码为PCM等;

2.1 FFmpeg重要的结构体


FFmpeg中有很多比较重要的结构体,比如与输入输出(I/O)有关的结构体AVIOContext、URLContext、URLProtocol ,与封装格式有关的结构体AVFormatContext、AVInputFormat、AVOutputFormat,与编解码有关的结构体AVCodec、AVCodecContext,以及与音视频数据有关的结构体AVStream、AVPacket、AVFrame等等。刚开始接触FFmpeg时,个人感觉一时间要理解区分这些结构体还是有点困难的,好在这些结构体当中有个“老大哥”-AVFormatContext,AVFormatContext可以说是贯穿整个FFmpeg开发,"犹如神一般的存在"。下面我们就在分析AVFormatContext结构体的基础上,阐述上述结构体的作用与区别。AVFormatContextAVFormatContext结构体描述了一个多媒体文件或流的构成和基本信息,是FFmpeg中最为基本的一个结构体,也是其他所有结构的根。其中,成员变量iformat和oformat为指向对应的demuxing(解封装)和muxing(封装)指针,变量类型分别为AVInputFormat、AVOutputFormat;pb为指向控制底层数据读写的指针,变量类型为AVIOContext;nb_streams表示多媒体文件或多媒体流中数据流的个数;streams为指向所有流存储的二级指针,变量类型AVStream;video_codec和audio_codec分别表示视频和音频编解码器,变量类型为AVCodec等等。AVFormatContext结构体(位于libavformat/avformat.h中)部分源码如下:

typedef struct AVFormatContext {

const AVClass *av_class;

// 输入容器格式

// 只在调用avformat_open_input()时被设置,且仅限Demuxing

struct AVInputFormat *iformat;

// 输出容器格式

// 只在调用avformat_alloc_output_context2()函数时被设置,且仅限封装(Muxing)

struct AVOutputFormat *oformat;

/**

* Format private data. This is an AVOptions-enabled struct

* if and only if iformat/oformat.priv_class is not NULL.

*

* - muxing: set by avformat_write_header()

* - demuxing: set by avformat_open_input()

*/

void *priv_data;

// 输/入输出(I/O)的缓存

// 说明:解封装(demuxing):值由avformat_open_input()设置

// 封装(muxing): 值由avio_open2设置,需在avformat_write_header()之前

AVIOContext *pb;

// stream info

int ctx_flags;

// AVFormatContext.streams中数据流的个数

// 说明:值由avformat_new_stream()设置

unsigned int nb_streams;

// 文件中所有流stream列表。创建一个新stream,调用avformat_new_stream()函数实现

// 当调用avformat_free_context()后,streams所占资源被释放

// 说明:解封装(demuxing):当调用avformat_open_input()时,streams值被填充

// 封装(muxing):streams在调用avformat_write_header()之前被用户创建

//

AVStream **streams;

// 输入或输出文件名,如输入:rtsp://184.72.239.149/vod/mp4:BigBuckBunny_115k.mov

// 说明:demuxing:当调用avformat_open_input()后被设置

// muxing: 当调用avformat_alloc_output_context2()后被设置,且需要调用avformat_write_header()之前

char filename[1024];

// component的第一帧位置,仅限Demuxing时由libavformat设置

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值