ZigZag Sin
登 陆
上一篇:dref Box 下一篇:stsd Box

stbl Box

Time
2022-2-21 11:39 阅读 299

具体 Box 分析

Stbl Box

官方介绍定义

image-20211223145946520

传送门:MP4 文档 P24页

介绍

这里终于接触到了可以说是 Mp4 Box 里面的核心内容了,最关键的 Stbl Box,这个 Box 主要核心作用就是把音视频的媒体数据和时间进行映射,可以根据这 Box 里面的信息,实时定位到视频各个时间段的数据。这个 Box 通常包含以下子 Box:

采样时间容器: Time To Sample 即 Stts Box

播放时间容器: (composition)Time To Sample 即 Ctts Box

Chunk 采样容器: Sample To Chunk 即 Stsc

采样大小容器: Sample Size 即 Stsz

Chunk 偏移容器:Chunk Offest 即 Stco

采样同步容器: Sync Sample 即 Stss

采样描述容器: Sample Description 即 Stsd Box

具体如下:

image-20211223152109319

全部子Box的声明

image-20211223152007818

字段分析:

Stbl Box 同样是 Container Box,所以这里也仅仅是8字节的分解符,这里Box Header部分不再分析。

代码定义

这里我们就把所有的 Box 定义完全

// BaseBox.h  

enum BOX_TYPE{
    FTYP,
    MOOV,
        MVHD,
        TRAK,
        LODS,
            TKHD,
            MDIA,
                MDHD,
                HDLR,
                MINF,
                    VMHD,
                    SMHD,
                    DINF,
                    STBL,
                        STSD,
                            AVC1,
                                AVCC,
                            MP4A,
                                ESDS,
                        STTS,
                        CTTS,
                        STSC,
                        STSZ,
                        STZ2,
                        STSS,
                        STCO,
                        CO64,
    UUID,
    MDAT,
    ERROR
};

struct BoxHeader{
    Timebyte _h_size[4] = {0};
    Timebyte _h_type[5] = {0};


    virtual unsigned int GetSize() {
        return _h_size[0] << 24 | _h_size[1] << 16 | _h_size[2] << 8 | _h_size[3];
    }

    unsigned int GetDataSize() {
        return GetSize() - 8;
    }

    virtual void to_string() {
        printf("box_size: %ud\n", GetSize());
        printf("box_type: %s\n", _h_type);
    }

    BOX_TYPE GetType() {
        if(_h_type[0]=='f'&&_h_type[1]=='t'&&_h_type[2]=='y'&&_h_type[3]=='p') return FTYP;
        else if (_h_type[0]=='m'&&_h_type[1]=='o'&&_h_type[2]=='o'&&_h_type[3]=='v') return MOOV;
        else if (_h_type[0]=='m'&&_h_type[1]=='d'&&_h_type[2]=='a'&&_h_type[3]=='t') return MDAT;
        else if (_h_type[0]=='m'&&_h_type[1]=='v'&&_h_type[2]=='h'&&_h_type[3]=='d') return MVHD;
        else if (_h_type[0]=='t'&&_h_type[1]=='r'&&_h_type[2]=='a'&&_h_type[3]=='k') return TRAK;
        else if (_h_type[0]=='t'&&_h_type[1]=='k'&&_h_type[2]=='h'&&_h_type[3]=='d') return TKHD;
        else if (_h_type[0]=='m'&&_h_type[1]=='d'&&_h_type[2]=='i'&&_h_type[3]=='a') return MDIA;
        else if (_h_type[0]=='m'&&_h_type[1]=='d'&&_h_type[2]=='h'&&_h_type[3]=='d') return MDHD;
        else if (_h_type[0]=='h'&&_h_type[1]=='d'&&_h_type[2]=='l'&&_h_type[3]=='r') return HDLR;
        else if (_h_type[0]=='m'&&_h_type[1]=='i'&&_h_type[2]=='n'&&_h_type[3]=='f') return MINF;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='b'&&_h_type[3]=='l') return STBL;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='s'&&_h_type[3]=='d') return STSD;
        else if (_h_type[0]=='a'&&_h_type[1]=='v'&&_h_type[2]=='c'&&_h_type[3]=='1') return AVC1;
        else if (_h_type[0]=='a'&&_h_type[1]=='v'&&_h_type[2]=='c'&&_h_type[3]=='C') return AVCC;
        else if (_h_type[0]=='m'&&_h_type[1]=='p'&&_h_type[2]=='4'&&_h_type[3]=='a') return MP4A;
        else if (_h_type[0]=='e'&&_h_type[1]=='s'&&_h_type[2]=='d'&&_h_type[3]=='s') return ESDS;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='t'&&_h_type[3]=='s') return STTS;
        else if (_h_type[0]=='c'&&_h_type[1]=='t'&&_h_type[2]=='t'&&_h_type[3]=='s') return CTTS;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='s'&&_h_type[3]=='s') return STSS;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='s'&&_h_type[3]=='z') return STSZ;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='c'&&_h_type[3]=='o') return STCO;
        else if (_h_type[0]=='s'&&_h_type[1]=='t'&&_h_type[2]=='s'&&_h_type[3]=='c') return STSC;

        return ERROR;
    }
};


// ...
// 其他 Box 的定义


class TimeStblBox : public BaseBox {
public:
    TimeStblBox(BoxHeader h);
    TimeStblBox(BoxHeader h, Timebyte * d): BaseBox(h, d){};
    ~TimeStblBox();
    void AnalyzeBoxHeader(BoxHeader header, size_t offset) override;
    void PrintDtsAndPts(); // 这个将来会用到我们这里先声明一个空实现  后面分析到对应Box来写这个函数
};

实现

//
// Created by Time on 2021/12/14.
//

#include "TimeMP4Box.h"

TimeStblBox::TimeStblBox(BoxHeader h) : BaseBox(h) {
    if (h.GetDataSize()) {
        data = new Timebyte[h.GetDataSize()];
    }
}

TimeStblBox::~TimeStblBox() {
}



void TimeStblBox::AnalyzeBoxHeader(BoxHeader header, size_t offset) {
    if (header.GetType() == STSD) {

    }
    if (header.GetType() == STTS) {

    }
    if (header.GetType() == CTTS) {

    }
    if (header.GetType() == STSC) {

    }
    if (header.GetType() == STSZ) {

    }
    if (header.GetType() == STCO) {


    }
    if (header.GetType() == STSS) {

    }
	PrintDtsAndPts();
}


void TimeStblBox::PrintDtsAndPts() {

    
}


上一篇:dref Box 下一篇:stsd Box
给我买个键盘吧。。。求打赏。。。
欢迎加群,一起交流~~~