MP4文件格式分析

     Mp4算是一种比较复杂也比较常用的媒体格式,它是在“ISO/IEC 14496-14”标准文件中定义的,属于MPEG-4的一部分,是“ISO/IEC 14496-12(MPEG-4 Part 12 ISO base media file format)”标准中所定义的媒体格式的一种实现,后者定义了一种通用的媒体文件结构标准。MP4目前被广泛用于封装h.264视频和AAC音频,是高清视频的代表。

 

      一,概述:

        MP4文件中的所有数据都装在box(QuickTime中为atom)中,也就是说MP4文件由若干个box组成,每个box有类型和长度,可以将box理解为一个数据对象块。box中可以包含其他box,这种box称为container box。

        其中,size指明了整个box所占用的大小,包括header部分。如果box很大(例如存放具体视频数据的mdat box),超过了uint32的最大数值,size就被设置为1,并用接下来的8位uint64来存放大小。至于box的类型实在是太多太多,我们也没必要全部搞懂,因为通常情况下一个Mp4文件并不会包含太多的box类型,下面列出一个比较常见的包含方式:

        下面列出一些比较关键box的数据存放信息:

    可以看到,我们分析Mp4文件的主要工作就是分析它的媒体信息,这么多的box几乎都是在做这一个工作。

    二,box分析

    所有的Mp4文件有且仅有一个“ftyp”类型的box并且位于第一个;这个container box包含了一个moov box,它里面存储了当前MP4文件所有的媒体信息,使我们解析Mp4文件的重中之重;最后是一个“mdat”类型的box,顾名思义包含了我们需要的媒体数据,当然也可以为空。

    File Type Box(ftyp)

    该box有且只有1个,并且只能被包含在文件层,而不能被其他box包含。该box应该被放在文件的最开始,指示该MP4文件应用的相关信息。ftyp box包含一个32位的major brand(4个字符),一个32位的minor version(整数)和一个以32位为单位的compatible数组。这些都是用来指示文件应用级别的信息,ftyp box在标准文档中的定义如下:

aligned(8) class FileTypeBox extends Box(‘ftyp’) 
{
    unsigned int(32) major_brand; //标识符,如mp41 mp42
    unsigned int(32) minor_version; //版本号
    unsigned int(32) compatible_brands[]; // to end of the box
}

        Movie Box(moov)

        用来存放媒体的metadata信息,其内容信息由子box诠释。该box有且只有一个并且包含在文件层,一般情况下moov box会紧随ftyp box出现,但也有放在文件末尾的。在标准文档中定义如下:

aligned(8) class MovieBox extends Box(‘moov’)
{

}

        Movie Header(mvhd)

        用来存放媒体的metadata信息,其内容信息由子box诠释。该box有且只有一个并且包含在文件层,一般情况下moov box会紧随ftyp box出现,但也有放在文件末尾的。它在标准文档中的定义为 :

        

aligned(8) class MovieHeaderBox extends FullBox(‘mvhd’, version, 0) 
{
    // version 是当前box的版本,一般取0,也可取1
    if (version==1) 
    {
        unsigned int(64) creation_time;
        unsigned int(64) modification_time;
        unsigned int(32) timescale;
        unsigned int(64) duration;
    } 
    else 
    { // version==0
        unsigned int(32) creation_time; // 创建时间
        unsigned int(32) modification_time; // 最后一次修改时间    
        unsigned int(32) timescale; // 一秒时间内的刻度值
        unsigned int(32) duration; // timescale下的时间长度. 时长 = duration/timescale
    }
    template int(32) rate = 0x00010000; // typically 1.0 播放速率
    template int(16) volume = 0x0100; // typically, full volume
    const bit(16) reserved = 0;
    const unsigned int(32)[2] reserved = 0;
    // Unity matrix 视频变换矩阵
    template int(32)[9] matrix = { 0x00010000,0,0,0,0x00010000,0,0,0,0x40000000 };
    bit(32)[6] pre_defined = 0;
    unsigned int(32) next_track_ID; // 下一个track的ID号
}

        trak:

        trak box也是一个container box,其子box包含了该track的媒体数据引用和描述(hint track除外)。一个MP4文件中的媒体可以包含多个track,且至少有一个track,这些track之间彼此独立,有自己的时间和空间信息。trak box必须包含一个tkhd box和一个mdia box,trak box 在标准文档中的定义如下:

aligned(8) class TrackBox extends Box(‘trak’) 
{
}

        Trak Head(tkhd):

        包含了该track的特性和总体信息,如时长,宽高等。tkhd box在标准文档中的定义如下:

aligned(8) class TrackHeaderBox extends FullBox(‘tkhd’, version, flags)
{
    if (version==1) 
    {
        unsigned int(64) creation_time;
        unsigned int(64) modification_time;
        unsigned int(32) track_ID;
        const unsigned int(32) reserved = 0;
        unsigned int(64) duration;
    } 
    else 
    { // version==0
        unsigned int(32) creation_time; // 创建时间
        unsigned int(32) modification_time; // 修改时间
        unsigned int(32) track_ID; // 当前track的ID号
        const unsigned int(32) reserved = 0; // 保留位
        unsigned int(32) duration; // 当前track的时长
    }
    const unsigned int(32)[2] reserved = 0;
    template int(16) layer = 0; // 视频层次,小的在上面
    template int(16) alternate_group = 0; // track的分组信息,0表示未分组
    template int(16) volume = {if track_is_audio 0x0100 else 0};
    const unsigned int(16) reserved = 0;
    // unity matrix
    template int(32)[9] matrix= { 0x00010000,0,0,0,0x00010000,0,0,0,0x40000000 };
    unsigned int(32) width;//宽
    unsigned int(32) height; // 高
}

        mdia:

        包含类整个track的媒体信息,比如媒体类型和sample信息,它在标准文档中的定义如下:

aligned(8) class MediaBox extends Box(‘mdia’) 
{
}

        Media Head(mdhd):

        包含了了该track的总体信息,mdhd 和 tkhd 内容大致都是一样的。tkhd 通常是对指定的 track 设定相关属性和内容,而 mdhd 是针对于独立的 media 来设置的,一般情况下二者相同。它在标准文档中的定义如下:

        

aligned(8) class MediaHeaderBox extends FullBox(‘mdhd’, version, 0) 
{
    if (version==1) 
    {
        unsigned int(64) creation_time;
        unsigned int(64) modification_time;
        unsigned int(32) timescale;
        unsigned int(64) duration;
    } 
    else 
    { 
        // version==0
        unsigned int(32) creation_time; // 创建时间
        unsigned int(32) modification_time; // 最后修改时间
        unsigned int(32) timescale; // 时间刻度
        unsigned int(32) duration; // 时间时长
    }
    bit(1) pad = 0;
    unsigned int(5)[3] language; // ISO-639-2/T language code 媒体语言码
    unsigned int(16) pre_defined = 0;
}

        Handler(hdlr):

        解释了媒体的播放过程信息,该box也可以被包含在meta box(meta)中,它在标准文档中的定义如下:

aligned(8) class HandlerBox extends FullBox(‘hdlr’, version = 0, 0) 
{
    unsigned int(32) pre_defined = 0;
    // 当前类型。 “vide”-video track “soun”- sound track “hint”-hint track
    unsigned int(32) handler_type;
    const unsigned int(32)[3] reserved = 0;
    string name; // 可读名称
}

        Media Information Box(minf):

        minf box包含了所有描述该track中的媒体信息的对象,信息存储在其子box中,它在标准文档中的定义为:

aligned(8) class MediaInformationBox extends Box(‘minf’) 
{
}

 

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值