H264关于一帧完整帧被分切成多个Slice时的合并思路

    在对H264进行编解码分析时,碰到一个完整视频帧被切分成多个Slice用于网络媒体传输的情况。而且接收端进行解码时需要一个完整帧(FFmpeg解码不需要拼接,内部已实现),因此怎么拼接多个Slice呢?

    对于H264视频流中关于NAL Unit句法、Slice Header结构等不是本文讲述的重点,相关资料可在网上查询,但需要对H264流媒体协议格式中的AVCC及Annex B格式有一定了解。本文主要以Annex B视频格式协议讲解。

    Annnex B格式在接收端接收到视频帧数据基本以0x000001或0x00000001开始,一般完整I帧包含:SPS、PPS、SEI、I帧数据(也有可能不包含SPS、PPS等信息),如下图:

            

P帧数据如下图:

            

若完整的视频帧未被切分成多个slice时,可直接被解码成YUV或RGB数据,但是当切分成多个slice,需要根据first_mb_in_slice计算每个帧片所在位置。

    比如上图B帧中数据为0x00 0x00 0x00 0x01 0x41 0xE2,读取第6位转成二进制:1110 0010,与上0x80:0xB8&0x80=0x80,即表示为一帧的第一片(可查询指数哥伦布码,即第一个位为1)。接下来一包数据为0x00 0x00 0x00 0x01 0x41 0x63,则与上0x80为0x0,则表示不是第一片(不是第一个片时的值在上一包的基础上会出现递增)。可归纳规律(假设的数据):

    第一包:0x00 0x00 0x00 0x01 0x41 0xE1

    第二包:0x00 0x00 0x00 0x01 0x41 0x62

    第三包:0x00 0x00 0x00 0x01 0x41 0x63

    第四包:0x00 0x00 0x00 0x01 0x41 0xE2

可看出第一包0xE1&0x80=0x80则是第一片,0x62&0x80=0x0则为第二包,直到遇到下一个0x80时为完整的一帧(第一包+第二包+第三包)。

    以上就是合并的基本思路,一般情况下I帧不会被切分成多了slice,而是以完整帧进行传输,P帧多数情况下存在切分的情况。

猜你喜欢

转载自blog.csdn.net/lizhijian21/article/details/80773031