大家好,又见面了,我是你们的朋友全栈君。
Matroska封装格式非常灵活、兼容性好,既适用于本地文件存储又可以进行实时流传输。本篇文章主要探讨Matroska的编解码器映射,如何封装视频流、音频流、字幕流。如果要Matroska的介绍、功能和基本结构,请查看上一篇文章:走进音视频的世界——Matroska封装格式的介绍(一)。
一、Matroska流
Matroska有两种传输流:文件访问(存储)和实时流传输(直播)。
1. 文件存储
Matroska是一种容器,支持把多媒体流封装成为文件,存储于本地。Matroska的开销很小,非常适合将音乐/视频存储在文件服务器上,而对使用的带宽没有很大影响。Matroska不需要在播放之前加载索引,因此可以非常快速地开始播放。只有在第一次请求搜索时才能加载索引。
2. 直播
实时流媒体相当于互联网上的电视广播。有2种服务器用于实时流传输:RTP / RTSP和HTTP。Matroska不能在RTP上使用。RTP已经具有定时和通道机制,如果在Matroska中加倍,则会浪费时间。此外,如果RTP和Matroska级别的信息不匹配,则可能会造成混淆。可以通过HTTP(或任何其他基于TCP的普通协议)对Matroska进行实时流传输。
实时Matroska流与文件不同,因为它通常没有已知的结尾(仅在客户端断开连接时才结束)。为此,Segment Element
必须将“大小”部分的所有位都设置为1。另一种选择是Segment Element
与已知大小连接,一个接一个。该解决方案允许在每个段之间更改编解码器/分辨率。例如,这允许在电视节目中在4:3和16:9之间切换。如果流既无MetaSeek
列表或Cues
在流的开始列表,它应该被视为非可查找。即使可以在信息流中盲目向前搜索,也不建议这样做。
二、编解码器映射
Codec Mapping(编解码器映射)
是一组属性,用于识别,命名和上下文化可以包含在Matroska群集中的编码数据的格式和特征。Matroska中使用的每个TrackEntry都必须引用定义,并且Codec Mapping
使用 Codec ID
来标识和描述其关联簇中编码数据的格式。Codec ID
是一个唯一的注册标识符,代表存储在Track中的编码。某些编码可能还需要某种形式的编解码器初始化,以便为其解码器提供上下文和技术元数据。
1. 编解码器ID
每个支持在Matroska中存储的编解码器都必须具有唯一的Codec ID
。根据编解码器的相关类型,每个表Codec ID
必须以下表中的字符串为前缀。Codec ID Prefix的
所有字符必须是大写字母(AZ)除的最后一个字符Codec ID Prefix
,其必须为下划线(“_”)。编解码器类型与ID前缀对应关系如下表所示:
编解码器类型 | 编解码器ID前缀 |
---|---|
视频 | “ V_” |
声音的 | “A_” |
字幕 | “ S_” |
按钮 | “ B_” |
每个Codec ID
必须在Major Codec ID
后面紧跟一个Codec ID Prefix
。而Major Codec ID
可能跟一个可选的Codec ID Suffix
通信的一个改进Major Codec ID
。如果使用a Codec ID Suffix
,则Codec ID
必须在Major Codec ID
和和之间使用正斜杠(“ /”)作为分隔符Codec ID Suffix
。在Major Codec ID
必须只由大写字母(AZ)和数字(0-9)的。在Codec ID Suffix
必须只由大写字母(AZ),数字(0-9),下划线(“_”)和斜杠(“/”)的。Codec IDs及其组成部分如下表所示:
编解码器ID前缀 | 主要编解码器ID | 分隔器 | 编解码器ID后缀 | 编解码器ID |
---|---|---|---|---|
A_ | AAC | / | MPEG2 / LC / SBR | A_AAC / MPEG2 / LC / SBR |
V_ | MPEG4 | / | ISO / ASP | V_MPEG4 / ISO / ASP |
2. 初始化
在Matroska中存储的每种编码都必须具有定义的初始化。而且初始化必须描述初始化解码器所需的数据存储,该数据必须存储在中CodecPrivate Element
。当初始化在轨道中更新时,必须将更新后的初始化数据写入CodecState Element要求在
第一个Cluster
的初始化数据中。如果编码不需要任何形式的初始化,则none
必须被用来定义的初始化和CodecPrivate Element
不应该被写入和必须被忽略。被定义为要存储在中的初始化数据CodecPrivate Element
称为Private Data
。
3. 编解码器块添加
Block
可以将上下文关联或补充a的其他数据存储在BlockAdditional Element
a的内BlockMore Element
。该BlockAdditional
数据可以与的内容一起传递给相关的解码器Block Element
。每一个BlockAdditional
都带有一个BlockAddID
,用于标识其包含的数据类型。BlockAddID
值的含义如下表所示:
BlockAddID值 | 定义 |
---|---|
0 | 无效。 |
1个 | 表示BlockAdditional数据的上下文由对应的定义Codec Mapping。 |
2或更大 | BlockAddID的2和更大的值被映射到BlockAddIDValue的BlockAdditionMapping相关联的轨道。 |
以下XMLBlockGroup Element
通过BlockAdditions的示例描绘了的嵌套元素:
<BlockGroup>
<Block>{Binary data of a VP9 video frame in YUV}</Block>
<BlockAdditions>
<BlockMore>
<BlockAddID>1</BlockAddID>
<BlockAdditional>
{alpha channel encoding to supplement the VP9 frame}
</BlockAdditional>
</BlockMore>
</BlockAdditions>
</BlockGroup>
4. 视频编解码器映射
V_MPEG4 / ISO / SP
编解码器ID:V_MPEG4 / ISO / SP
编解码器名称:MPEG4 ISO简单配置文件(DivX4)
描述:流是通过改进的编解码器AP创建的,甚至是从AVI进行多路复用的(简单配置文件中没有b帧),帧顺序是编码顺序。
V_MPEG4 / ISO / ASP
编解码器ID:V_MPEG4 / ISO / ASP
编解码器名称:MPEG4 ISO高级简单配置文件(DivX5,XviD,FFMPEG)
描述:流是通过改进的编解码器API创建的,或者是从MP4进行多路复用的,而不是简单地从AVI进行多路复用的。请注意,在这些本机流中处理b帧的方式有所不同,因为这里no
插入了虚拟帧,其帧顺序与编码顺序完全相同,与MP4流相同。
V_MPEG4 / ISO / AVC
编解码器ID:V_MPEG4 / ISO / AVC
编解码器名称:AVC / H.264
说明:按照ISO.14496-15中的说明存储的AVC/H.264的单个图片(可以是一个帧,一个字段或两个具有相同时间戳的字段)。
初始化:Private Data
包含AVCDecoderConfigurationRecord
[ISO.14496-15]中定义的结构。该AVCDecoderConfigurationRecord
结构后可以跟一个扩展块,该扩展块以big-endian字节顺序的4字节扩展块大小字段开头扩展块减4(不包括扩展块大小字段的大小)和BlockAddIDType
与“ mvcC”的a对应的4字节字段,后跟与BlockAddIDExtraData
for的内容对应的内容mvcC。
V_MPEGH / ISO / HEVC
编解码器ID:V_MPEGH / ISO / HEVC
编解码器名称:HEVC / H.265
说明:按照ISO.14496-15中所述存储的HEVC/H.265的单个图片(可以是一个帧,一个字段或两个具有相同时间戳的字段)。
初始化:Private Data
包含HEVCDecoderConfigurationRecord
[ISO.14496-15]中定义的结构。
V_VP9
编解码器ID:V_VP9
编解码器名称:VP9编解码器格式
说明:VP9是由Google作为VP8的后继产品而开发的一种开放且免版税的视频压缩格式。VP9比特流和解码过程规范草案
编解码器块添加:alpha通道的单通道编码可以存储在中BlockAdditions
。在BlockAddId
所述的BlockMore
含这些数据必须是1。
5. 音频编解码器映射
A_MPEG / L3
编解码器ID:A_MPEG / L3
编解码器名称:MPEG Audio 1,2,2.5 Layer III
说明:数据包含每个帧的MPEG Audio标头中播放所需的所有内容。对应的ACM wFormatTag:0x0055
A_PCM / INT / LIT
编解码器ID:A_PCM / INT / LIT
编解码器名称:PCM Integer Little Endian
说明:必须从读取和设置音频位深度BitDepth Element
。音频采样必须被视为有符号值,除非音频位深度为8(必须将其解释为无符号值)。对应的ACM wFormatTag:0x0001
A_AC3
编解码器ID:A_AC3
编解码器名称:(Dolby™)AC3
说明:BSID <= 8,对应的ACM wFormatTag:0x2000; 通道号必须从相应的音频元素中读取
A_DTS
编解码器ID:A_DTS
编解码器名称:数字影院系统
说明:支持DTS,DTS-ES,DTS-96 / 26,DTS-HD高分辨率音频和DTS-HD主音频。私人数据无效。对应的ACM wFormatTag:0x2001
A_VORBIS
编解码器ID:A_VORBIS
编解码器名称:Vorbis
初始化:Private Data
按顺序包含前三个Vorbis数据包。数据包的长度在它们之前。实际布局为:
- 字节1:
#p
在CodecPrivate块中,不同数据包的数量减一。对于当前(截至2016年7月8日)Vorbis标头,该名称必须为“ 2”。 - 字节2..n:第一个
#p
数据包的长度,以Xiph样式的花边编码。最后一个数据包的长度是CodecPrivate块的长度减去在这些字节中编码的长度减去一。 - 字节n 1 ..:Vorbis标识标头,然后是Vorbis注释标头 ,再是编解码器设置标头。
A_FLAC
编解码器ID:A_FLAC
编解码器名称:FLAC(免费无损音频编解码器)
初始化:Private Data
包含第一个数据包之前的所有标头/元数据包。这些包括仅包含单词fLaC
以及所有元数据包的第一个标头包。
A_AAC / MPEG2 / MAIN
编解码器ID:A_AAC / MPEG2 / MAIN
编解码器名称:MPEG2 Main Profile
说明:通道号和采样率必须从相应的音频元素中读取。从ADTS标头中剥离音频流,并应用基于常规Matroska帧的混合方案。AAC音频始终使用wFormatTag 0xFF。
A_WAVPACK4
编解码器ID:A_WAVPACK4
编解码器名称:WavPack无损音频压缩器
描述:Wavpack数据包包括一个剥离的报头,后跟帧数据。对于多轨道(> 2个轨道),一帧包含许多数据包。有关更多详细信息,请查看WavPack混合说明。
编解码器BlockAdditions:对于混合A_WAVPACK4
编码(包括有损编码和补充校正以产生无损编码),校正部分存储在BlockAdditional中。在BlockAddId
所述的BlockMore
含这些数据必须是1。
6. 字幕编解码映射
S_TEXT / UTF8
编解码器ID:S_TEXT / UTF8
编解码器名称:UTF-8纯文本
说明:基本文本字幕。
S_TEXT / SSA
编解码器ID:S_TEXT / SSA
编解码器名称:字幕格式
说明:[脚本信息]和[V4样式]部分存储在编解码器中。每个事件都存储在其自己的块中。
S_TEXT / WEBVTT
编解码器ID:S_TEXT / WEBVTT
编解码器名称:Web视频文本轨道格式(WebVTT)
描述:高级文本字幕。
S_IMAGE / BMP
编解码器ID:S_IMAGE / BMP
编解码器名称:位图
说明:基于基本图像的字幕格式;字幕存储为图像,就像DVD中一样。Matroska块标题中的时间戳指示开始显示时间,持续时间由Duration元素设置。字幕位图的完整数据存储在块的数据部分中。
S_DVBSUB
编解码器ID:S_DVBSUB
编解码器名称:数字视频广播(DVB)字幕
说明:这是数字视频广播标准中使用的图形字幕格式。
S_VOBSUB
编解码器ID:S_VOBSUB
编解码器名称:VobSub字幕
说明:与DVD上使用的字幕格式相同。仅支持格式版本7和更高版本。VobSubs由两个文件组成,.idx包含信息,而.sub包含实际数据。.idx文件将删除所有空行,所有注释以及以alt
开头的行。以id
开头的行应该转换为适当的Matroska跟踪语言元素,并被丢弃。除包含时间戳和文件位置的行以外的所有其余行都放入CodecPrivate
元素中。
对于包含时间戳记和文件位置的每一行,都从.sub文件中的相应位置读取数据。此数据由MPEG程序流组成,而MPEG程序流又包含SPU数据包。丢弃MPEG节目流数据,并将每个SPU数据包放入一个Matroska帧中。
三、视频标签
1. 基本电影
在一张DVD(XML版本)上添加电影的标题,导演,发行日期和评论,示例如下:
标签
- 标签(关于电影)
- SimpleTag
- TagName =“标题”
- TagString =“ Dune”
- SimpleTag
- TagName =“导演”
- TagString =“大卫·林奇”
- SimpleTag
- TagName =“ DATE_RELEASED”
- TagString =“ 1984”
- SimpleTag
- TagName =“评论”
- TagString =“最好的科幻电影之一。”
- SimpleTag
2. 多集DVD
如果有一组DVD,每个DVD包含整个季节的几集,可以使用Simpsons DVD。这些情节的范围如下:
第1季
- DVD#1(第UID章= 98)
- 第1集(第UID章= 123)
- 简介(第UID章= 963)
- 剧集内容(第UID章= 852)
- 第2集(第UID章= 234)
- 简介(第UID章= 159)
- 剧集内容(第UID章= 267)
- 第3集(第UID章= 345)
- 介绍
- 剧集内容
- 第4集(UID第456章)
- 介绍
- 剧集内容
- 第1集(第UID章= 123)
- DVD#2(第UID章= 87)
- 第5集(第UID章= 567)
- 介绍
- 剧集内容
- 第6集(第UID章= 678)
- 介绍
- 剧集内容
- 第5集(第UID章= 567)
四、音频标签
音频内容通常带有标签,即关于您可以收听的内容的元信息,例如艺术家姓名,曲目标题,发行年份等。问题是,人们现在为了确保一致性而只将CD翻录到一个文件中在他们的硬盘上,通常可以避免在现场/古典/混音专辑中出现间隙问题。
1. 包含所有曲目的单个文件
标签
- 标签
- 目标(没有目标意味着文件的全部内容,否则您可以放置所有ChapterUID)
- TargetTypeValue = 50
- TargetType =“专辑”
- SimpleTag
- TagName =“艺术家”
- TagString =“微纳特”
- SimpleTag
- TagName =“标题”
- TagString =“哔哔哔”
- SimpleTag
- TagName =“ TOTAL_PARTS”
- TagString =“ 9”
- SimpleTag
- TagName =“ DATE_RELEASED”
- TagString =“ 2004-04”
- 目标(没有目标意味着文件的全部内容,否则您可以放置所有ChapterUID)
- 标签
- 目标(没有章目标,因为该文件可能不包含一个目标,但是如果有的话,您可以使用它)
- TargetTypeValue = 30
- TargetType =“ TRACK”
- SimpleTag
- TagName =“标题”
- TagString =“婴儿想哭了”
- SimpleTag
- TagName =“ PART_NUMBER”
- TagString =“ 1”
- 目标(没有章目标,因为该文件可能不包含一个目标,但是如果有的话,您可以使用它)
五、字幕存储
在Matroska中存储字幕的指针列表:
- 仅包含字幕任何Matroska文件应该使用扩展名“.mks”。
- 根据经验,对所有编解码器的一般规则,信息是全局的整个流应该被保存在CodecPrivate元素。
- 放置在Matroska中时,应删除以时间戳本机存储格式使用的开始和停止时间戳,因为如果以后对其进行编辑,它们可能会造成干扰。相反,应该使用“块时间戳”和“持续时间”来表示时间戳的显示时间。
- 因为“字幕”流实际上只是一个叠加流,所以可以使用任何具有透明层的东西,包括视频。
1. SRT字幕
SRT可能是所有字幕格式中最基本的。
它由四个部分组成,所有部分均在文本中:
1.一个数字,指示它在序列中是哪个字幕。2.字幕出现在屏幕上,然后消失的时间。3.字幕本身。4.空白行指示新字幕的开始。示例如下:
代码语言:javascript复制1
00:02:17,440 --> 00:02:20,375
Senator, we're making
our final approach into Coruscant.
2
00:02:20,476 --> 00:02:22,501
Very good, Lieutenant.
2. WebVTT
“ Web视频文本轨道格式”(简称:WebVTT)由万维网联盟(W3C)开发。其规格可免费获得。
在Matroska中存储WebVTT的指导原则是:
- 一致性:以与其他字幕编解码器类似的方式存储数据
- 简单性:使现有基础架构的解码和重新混合尽可能容易
- 完整性:从原始WebVTT文件中保留尽可能多的数据
存储WebVTT
CodecID:编解码器标识
要使用的CodecID为S_TEXT/WEBVTT
。
CodecPrivate:全局WebVTT块的存储
该元素包含第一个字幕条目之前的所有全局块。它从“ WEBVTT
”文件标识标记开始,但不包括可选的字节顺序标记。示例如下:
WEBVTT with text after the signature
STYLE
::cue {
background-image: linear-gradient(to bottom, dimgray, lightgray);
color: papayawhip;
}
/* Style blocks cannot use blank lines nor "dash dash greater
than" */
NOTE comment blocks can be used between style blocks.
STYLE
::cue(b) {
color: peachpuff;
}
REGION
id:bill
width:40%
lines:3
regionanchor:0%,100%
viewportanchor:10%,90%
scroll:up
NOTE
Notes always span a whole block and can cover multiple
lines. Like this one.
An empty line ends the block.
hello
00:00:00.000 --> 00:00:10.000
Example entry 1: Hello <b>world</b>.
NOTE style blocks cannot appear after the first cue.
00:00:25.000 --> 00:00:35.000
Example entry 2: Another entry.
This one has multiple lines.
00:01:03.000 --> 00:01:06.500 position:90% align:right size:35%
Example entry 3: That stuff to the right of the timestamps are cue
settings.
00:03:10.000 --> 00:03:20.000
Example entry 4: Entries can even include timestamps.
For example:<00:03:15.000>This becomes visible five seconds
after the first part.
可以到GitHub一起学习音视频:https://github.com/xufuji456/FFmpegAndroid
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。