FFmpeg学习笔记汇总

2022-11-14 19:33:06 浏览数 (1)

第1章 FFmpeg简介

1.1 FFmpeg定义

FFmpeg既是一款音视频编解码工具,同时也是一组音视频编解码开发套件,作为编解码开发套件,它为开发者提供了丰富的音视频处理的调用接口。 FFmpeg提供了多种媒体格式的封装和解封装,包括多种音视频编码、多种协议的流媒体、多种色彩格式转换、多种采样率转换、多种码率转换等;FFmpeg框架提供了多种丰富的插件模块,包含封装与解封装的插件、编码与解码的插件等。

FFmpeg中的“FF”指的是“FastForward”(快进),曾经有人写信给FFmpeg的项目负责人,询问“FF”是不是代表“FastFreec”或者“FastFourier”的意思。FFmpeg中的“mpeg则是人们通常理解的Moving Picture Experts Group(动态图像专家组),FFmpeg是一个很全面的图像处理套件。其实从2000年发展至今,FFmpeg中的“FF”已经可以用各种组合进行理解,因为FFmpeg的强大足以支撑这些意义。

1.2 FFmpeg的基本组成

(1)FFmpeg的封装模块AVFormat

  AVFormat中实现了目前多媒体领域中的绝大多数媒体封装格式,包括封装和解封装 FFmpeg基本组成模块MP4、FLV、KV、TS等文件封装格式,RTMP、RTSP、MMS、HLS等网络协议封装格式。 FFmpeg是否支持某种媒体封装格式,取决于编译时是否包含了该格式的封装库。根据实际需求,可进行煤体封装格式的扩展,增加自己定制的封装格式,即在AVFormat中增加自己的封装处理模块。

(2)FFmpeg的编解码模块AVCodec

AVCodec中实现了目前多媒体领域绝大多数常用的编解码格式,既支持编码,也支持解码。AVCodec除了支持MPEG4、AAC、MJPEG等自带的媒体编解码格式之外,还支持第三方的编解码器,如H.264(AVC)编码,需要使用x264编码器;H.265(HEVC)编码,需要使用x265编码器:MP3(mp3lame)编码,需要使用libmp3lame编码器。如果

(3)FFmpeg的滤镜模块AVFilter

AVFilter库提供了一个通用的音频、视频、字幕等滤镜处理框架。在AVFilter中,滤镜框架可以有多个输入和多个输出。

  • 相同的Filter线性链之间用逗号分隔
  • 不同的Filter线性链之间用分号分隔

(4)FFmpeg的视频图像转换计算模块swscale

swscale模块提供了高级别的图像转换API,例如它允许进行图像缩放和像素格式转换,常见于将图像从1080p转换成720p或者480p等的缩放,或者将图像数据从YUV420P转换成YUYV,或者YUV转RGB等图像格式转换。

(5)FFmpeg的音频转换计算模块swresample

swresample模块提供了高级别的音频重采样API。例如它允许操作音频采样、音频通道布局转换与布局调整。

1.3FFmpeg的编解码工具ffmpeg

fmpeg是FFmpeg源代码编译后生成的一个可执行程序,其可以作为命令行工具使用。

fmpeg的主要工作流程相对比较简单,具体如下。

1)解封装(Demuxing)。 2)解码(Decoding)。 3)编码(Encoding)。 4)封装(Muxing)。 其中需要经过6个步骤,具体如下。 1)读取输人源。 2)进行音视频的解封装。

3)解码每一帧音视频数据

4)编码每一帧音视频数据。

5)进行音视频的重新封装。

6)输出到目标。

 1.5 FFmpeg的播放器fplay

FFmpeg不但可以提供转码、转封装等功能,同时还提供了播放器相关功能,使用FFmpeg的avformat与avcodec,可以播放各种媒体文件或者流。如果想要使用fplay,那么系统首先需要有SDL来进行fplay的基础支撑。 fplay是FFmpeg源代码编译后生成的另一个可执行程序,与fmpeg在FFmpeg项目中充当的角色基本相同,可以作为测试工具进行使用,fplay提供了音视频显示和播放相关的图像信息、音频的波形信息等。

注意: 有时通过源代码编译生成fplay不一定能够成功,因为mplay在旧版本时依赖于SDL-1.2,而fplay在新版本时依赖于SDL-2.0,需要安装对应的SDL才能生成flaya

1.6 FFmpeg的多媒体分析器ffprobe

ffprobe也是FFmpeg源码编译后生成的一个可执行程序。ffprobe是一个非常强大的多媒体分析工具,可以从媒体文件或者媒体流中获得你想要了解的媒体信息,比如音频的参数、视频的参数、媒体容器的参数信息等。 例如它可以帮助分析某个媒体容器中的音频是什么编码格式、视频是什么编码格式,同时还可以得到媒体文件中媒体的总时长、复合码率等信息。 使用fprobe可以分析媒体文件中每个包的长度、包的类型、顿的信息等

1.7 FFmpeg编译

FFmpeg在官方网站中提供了已经编译好的可执行文件。因为FFmpeg是开源的,所以也可以根据自己的需要进行手动编译。FFmpeg官方建议用户自行编译使用FFmpeg的最新版本,因为对于一些操作系统,比如Linux系统(无论是Ubuntu还是RedHat),如果使用系统提供的软件库安装fimpeg时会发现其版本相对比较老旧,比如使用apt-getinstall fmpeg或者yuminstallfmpeg安装fmpeg,那么默认支持的版本都很老,有些新的功能并不支持,如一些新的封装格式或者通信协议。

1.8FFmpeg编码支持与定制

FFmpeg本身支持一些音视频编码格式、文件封装格式与流媒体传输协议,但是支持的数量依然有限,FFmpeg所做的只是提供一套基础的框架,所有的编码格式、文件封装格式与流媒体协议均可以作为FFmpeg的一个模块挂载在FFmpeg框架中。这些模块以第三方的外部库的方式提供支持,可以通过FFmpeg源码的configure命令查看FFmpeg所支持的音视频编码格式、文件封装格式与流媒体传输协议,对于FFmpeg不支持的格式,可以通过configure--help查看所需要的第三方外部库,然后通过增加对应的编译参数选项进行支持。

代码语言:javascript复制
configure--help

二.FFmpeg工具使用基础

FFmpeg中常用的工具主要是fimpeg、fprobe、ffplay,它们分别用作多媒体的编解码工具、内容分析工具和播放器。

  1. fpeg主要用于音视频编解码
  2. ffprobe主要用于音视频内容分析
  3. fplay主要用于音视频播放、可视化分析

2.1 fmpeg常用命令

fmpeg在做音视频编解码时非常方便,所以在很多场景下转码使用的是fmpeg,通过ffmpeg--help可以看到fmpeg常见的命令大概分为6个部分,具体如下。

  1. ffmpeg信息查询部分
  2. 公共操作参数部分
  3. 文件主要操作参数部分
  4. 视频操作参数部分
  5. 音频操作参数部分
  6. 字幕操作参数部分

通过ffmpeg--help查看到的help信息是fmpeg命令的基础信息,如果想获得高级参数部分,那么可以通过使用ffmpeg --help long参数来查看,如果希望获得全部的帮助信息,那么可以通过使用ffmpegg --help full参数来获得。 看fmpeg的版本,包括子模块的详细版本信息,如libavformat、libavcodec、libavutil、libavfilter、libswscale、libswresample的版本。

代码语言:javascript复制
ffmpeg --help long
ffmpegg --help ful

2.2ffprobe常用命令

在FFmpeg套件中,除了fmpeg作为多媒体处理工具之外,还有ffprobe多媒体信息查看工具,ffprobe主要用来查看多媒体文件的信息. fprobe常用的参数比较多,可以通过fprobe--help来查看详细的帮助信息。

代码语言:javascript复制
fprobe--help

使用fprobe-showpacketsinput.flv查看多媒体数据包信息:

通过showpackets查看的多媒体数据包信息使用PACKET标签括起来,其中包含的信息主要如表

字段

说明

.codec_type

多媒体类型,如视频包、音频包等

Stream index

多媒体的stream索引

PIS

多媒体的显示时间值

pIs_time

根据不同格式计算过后的多媒体的显示时间

dts

多媒体解码时间值

dts time

根据不同格式计算过后的多媒体解码时间

duration

多媒体包占用的时间值

duration timc

根据不同格式计算过后的多媒体包所占用的时间值

size

多媒体包的大小

pos

多媒体包所在的文件偏移位置

flags

多媒体包标记,如关键包与非关键包的标记

除了packets与data之外,ffprobe还可以分析多媒体的封装格式,通过ffprobe-show_formatoutput.mp4命令可以查看多媒体的封装格式,其使用FORMAT标签括起来显示:

下面对输出信息关键字段进行说明,具体见表

字段

说明

filename

文件名

nb streams

媒体中包含的流的个数

nbprograms

节目数(相关的概念在2.3节中会有详细的介绍)

format name

使用的封装模块的名称

format long name

封装的完整名称

start time

媒体文件的起始时间

duration

媒体文件的总时间长度

size

媒体文件的大小

bit rate

媒体文件的码率

 通过ffprobe-show_framesinput.dv命令可以查看视频文件中的赖信息,输出的顺信息将使用FRAME标签括起来

代码语言:javascript复制
[FRAME]
media_type=video
stream index=0
key_frame=l
pkt pts=80
pkt_pts_time=0.080000
pkt dts=80
pkt dts_time=0.080000
begt effort timegtamp=80
best effort timestamp_time=0.080000
pkt_duration=N/A
pkt duration time=N/A
pkt_pog=344
pkt_size=8341
width=1280
height=714
pix fmt=yuv420p
6ample_aspect_ratio=1:1
pict_type=T
coded picture number=0
display picture number=0
interlaced frame=0
top_field first=o
repeat pict=0
[/FRAME]

通过-show_frames参数可以查看每一帧的信息,下面就来介绍一下其中重要的信息,具体见表

属性

说明

media type

的类型(视频、音频,字幕等)

video

stream index

帧所在的索引区域

0

key_frame

是否为关键顿

1

pktpts

Frame包的pts

0

pkt pis time

Frame包的ps的时间显示

0.08

pkt dts

Frame包的dts

80

pkt dis time

Frame包的dts的时间显示

0.08

pkt duration

Frame包的时长

NIA

pkt duration time

Frame包的时长时间显示

NIA

pkt pos

Frame包所在文件的偏移位置

344

width

显示的宽度

1280

height

显示的高度

714

pix fimt

倾的图像色彩格式

yuv420p

piet type

侦类型

I

 通过-show streams参数可以查看到多媒体文件中的流信息,流的信息将使用STREAM标签括起来:

1eve1=31如以上输出内容所示,从中可以看到流的信息,具体属性及说明见表

属性

说明

index

流所在的索引区域

0

codecnamc

编码名

h264

codee long name

编码全名

MPEG-4 part 10

profile

编码的profile

High

属性

说明

level

编码的level

31

has b frames

包含B赖信息

2

codec type

编码类型

video

codec timebase

编码的时间截计算基础单位

1750

pix fmt

图像显示的色彩格式

yuv420p

codedwidth

图像的宽度

1280

coded height

图像的高度

714

codec tag string

编码的标签数据

[0][0][0][0]

Tframe rateavg frame rate

实际硕率平均帧率

25/125/

time base

时间基数(用来进行timestamp计算)

1/1000

bit rate

码率

200000

xbit ratemax

最大码率

N/A

nb_frames

帧数

N/A

2.3 ffplay常用命令

在编译旧版本FFmpeg源代码时,如果系统中包含了SDL-1.2版本,就会默认将ffplay编译生成出来,如果不包含SDL-1.2或者版本不是SDL-l.2时,将无法生成ffplay文件,所以,如果想使用flay进行流媒体播放测试,则需要安装SDL-1.2.而在新版本的FFmpeg源代码中,需要SDL-2.0之后的版本才能有效生成ffplay.。 在FFmpeg中通常使用ffplay作为播放器,其实ffplay同样也可以作为很多音视频数据的图形化分析工具,通过ffplay可以看到视频图像的运动估计方向、音频数据的波形等.

下表是ffplay的基础参数

参数

说明

x

强制设置视频显示窗口的宽度

y

强制设置视频显示窗口的高度

s

设置视频显示的宽高

fs

强制全屏显示

an

屏蔽音频

vn

屏蔽视频

sn

屏蔽字幕

ss

根据设置的秒进行定位拖动

t

设置播放视频/音频的长度

bytes

设置定位拖动的策略,0为不可拖动,1为可拖动,-1为自动

nodisp

关闭图形化显示窗口

f

强制使用设置的格式进行解析

window title

设置显示窗口的标题

af

设置音频的滤镜

codec

强制使用设置的codec进行解码

autorotate

自动旋转视频

下面这个表是ffplay高级参数

参数

说明

ast

设置将要播放的音额流

vst

设置将要播放的视频流

sst

设置将要播放的字幕流

stats

输出多媒体播放状态

fast

非标准化规范的多媒体兼容优化

sync

音视频同步设置可根据音频时间、视频时间或者外部扩展时间进行参考

autoexit

多媒体播放完毕之后自动退出fplay,fplay默认播放完毕之后不退出播放器

cxitonkeydown

当有按键按下事件产生时退出ffplay

exitonmousedown

当有鼠标按键事件产生时退出fplay

loop

设置多媒体文件循环播放的次数

framedrop

当CPU资源占用过高时,自动丢顿

infbuf

设置无极限的播放器buffer,这个选项常见于实时流媒体播放场景

vf

视频滤镜设置

acodec

强制使用设置的音频解码器

vcodec

强制使用设置的视频解码器

scodec

强制使用设置的字幕解码器

 第3章 FFmpeg转封装

(累了orz,下次更,有人看可以关注回复我下,更有动力)

3.1.1MP4格式标准介绍

MP4格式标准为IS0-14496Part12、IS0-14496Part14,标准内容并不是特别多,下面就来着重介绍一些重要的信息。

如果要了解MP4的格式信息,首先要清楚几个概念,具体如下。

MP4文件由许多个Box与FullBox组成

每个Box由Header和Data两部分组成

FullBox是Box的扩展,其在Box结构的基础上,在Header中增加8位version标志和24位的f1ags标志

Header包含了整个Box的长度的大小(size)和类型(type),当size等于O时,代表这个Box是文件的最后一个Box。当siz等于1时,说明Box长度需要更多的位来描述,在后面会定义一个64位的largesize用来描述Box的长度。当Type为uuid时,说明这个Box中的数据是用户自定义扩展类型

Data为Box的实际数据,可以是纯数据,也可以是更多的子Box

当一个Box中Data是一系列的子Box时,这个Box又可以称为Container(容器)

Box MP4文件中Box的组成可以用表3-1所示的列表进行排列,表3-1中标记“V”的Box为必要Box,否则为可选Box。

第4章FFmpeg转码

4.1.2H.264编码举例

3.H.264的proffle与level设置

这里的profile(档次)与level(等级)的设置与H.264标准文档ISO-14496-Part10中描述的profile、level的信息基本相同,×264编码器支持Baseline、Extented、Main、High、High10、High422、High444共7种profile参数设置,根据profile的不同,编码出来的视频的很多参数也有所不同,具体的情况可以参考表。

4.4FFmpeg输出AAC

在音视频流中,无论直播与点播,AAC都是目前最常用的一种音频编码格式,例如RTMP直播、HLS直播、RTSP直播、FLV直播、FLV点播、MP4点播等文件中都是常见的AAC音视频。

与MP3相比,AAC是一种编码效率更高、编码音质更好的音频编码格式,常见的使用AAC编码后的文件存储格式为m4a,如在iPhone或者iPad中即为m4a.FFmpeg可以支持AAC的三种编码器具体如下。

aac:FFmpeg本身的AAC编码实现

libfaac:第三方的AAC编码器

·libfdk_aac:第三方的AAC编码器

后两种编码器为非GPL协议,所以使用起来需要注意,在预编译时需要注意采用nonfree的支持。

4.4.4AAC音频质量对比

AAC-LC的音频编码可以采用libfaac、libfdk aac、FFmpeg内置AAC三种,其质量顺序排列如下。

libfdk aac音频编码质量最优

FFmpeg内置AAC编码次于libfdk aac但优于libfaac

libfaac在FFmpeg内置AAC编码为实验品时是除了libfdk_aac之外的唯一选择

第5章 FFmpeg流媒体

AAC-LC的音频编码可以采用libfaac、libfdk_aac、FFmpeg内置AAC三种,其质量顺序排列如下

libfdkaac音频编码质量最优

FFmpeg内置AAC编码次于libfdkaac但优于libfaac

libfaac在FFmpeg内置AAC编码为实验品时是除了Iibfdkaac之外的唯一选择。

随着互联网、移动互联网的发展,人们获取信息的方式开始从纸质媒体转向互联网文字媒体,又从文字媒体转向音视频流媒体。音视频流媒体又称为“流媒体”,而用于处理流媒体的压缩、录制、编辑操作,开源并强大的工具屈指可数,FFmpeg就是常见的流媒体处理工具。

3.解析trak子容器

trak容器中定义了媒体文件中的一个track的信息,一个媒体文件中可以包含多个trak,每个trak都是独立的,具有自己的时间和空间占用的信息,每个trak容器都有与它关联的media容器描述信息。trak容器的主要使用目的具体如下。

包含媒体数据的引用和描述(media track)

包含modifier track信息

流媒体协议的打包信息(hint track),hint track可以引用或者复制对应的媒体采样数据

hint track和modifier track必须保证完整性,同时要与至少一个media track一起存在。

一个trak容器中要求必须要有一个Track Header Atom(tkhd)、一个Media Atom(mdia),其他的Atom都是可选的,例如如下的atom选项。

Track剪辑容器:Track Clipping Atom(clip)

Track画板容器:Track Matte Atom(matt)

Edit容器:Edit Atom(cdts)

Track参考容器:Track Reference Atom(tref)

Track配置加载容器:Track Load Settings Atom(load)

Track输出映射容器:Track Input Map Atom(imap)

用户数据容器:User Data Atom(udta)

0 人点赞