国标MPEG-PS实时流播放器开发(附例子)

本文详细介绍了如何实现一个支持GB28181标准的MPEG-PS实时流播放器。内容包括PS流的基本概念,如ES、PES和PS的封装结构,以及播放器的功能设计。文章还探讨了PS流的码流结构,强调了PSM在解析流编码类型中的作用,并描述了播放器的解封装、解码和显示流程。最后,讨论了播放器的多线程设计和处理策略,确保了低延迟的实时流处理。
摘要由CSDN通过智能技术生成

公安部制定的GBT 28181标准广泛应用于安防领域,这个标准规定了传输的视音频数据要封装成PS流格式。PS格式(原名叫MPEG-PS)在很多领域已经应用了很长一段时间,特别是在安防、广播电视、影音制作等领域,我们熟知的DVD格式(vob)就是用PS封装的。这篇文章我打算给大家讲解怎么实现一个PS流的实时流播放器,通过这篇文章学习,大家就知道一个实时流播放器应该如何设计、如何对PS流做处理等。

一、基本概念

1)ES  

   ES–Elementary  Streams 是直接从编码器出来的数据流,可以是编码过的视频数据流(H.264,MJPEG等),音频数据流,或其他编码数据流的统称。ES流经过PES打包器之后,被转换成PES包。

    ES是只包含一种内容的数据流,如只含视频或只含音频等,打包之后的PES也是只含一种性质的ES,如只含视频ES的PES,只含音频ES的PES等。

2)PES

    PES–Packetized  Elementary Streams  (分组的ES),ES形成的分组称为PES分组,是用来传递ES的一种数据结构。PES流是ES流经过PES打包器处理后形成的数据流,在这个过程中完成了将ES流分组、打包、加入包头信息等操作(对ES流的第一次打包)。PES流的基本单位是PES包。PES包由包头和payload组成。

3)PS

   PS–Program Stream(节目流)PS流由PS包组成,而一个PS包又由若干个PES包组成(到这里,ES经过了两层的封装)。PS包的包头中包含了同步信息与时钟恢复信息。

4)PTS、DTS

   PTS–PresentationTime Stamp(显示时间标记)表示显示单元出现在系统目标解码器(H.264、MPEG4等)的时间。

   DTS–Decoding Time Stamp(解码时间标记)表示将存取单元全部字节从解码缓存器移走的时间。

   PTS/DTS是打在PES包的包头里面的,这两个参数是解决音视频同步显示,防止解码器输入缓存上溢或下溢的关键。每一个I(关键帧)、P(预测帧)、B(双向预测 帧)帧的包头都有一个PTS和DTS,但PTS与DTS对于B帧不一样。

PTS/DTS是相对SCR(系统参考)的时间戳,系统时钟频率为90Khz,是以90000为单位的,PTS/DTS到ms的转换公式是PTS/90,转换到秒为PTS/90000。如果没有B帧,PTS和DTS的顺序应该是一致的,如果有B帧,则需要先解码P帧,才能解出来B帧,所以需要PTS和DTS来控制解码时间和显示时间。

根据对前面概念的理解,我总结出以下几点:

1. PS流是一种复合流,可以包含视频流和音频流数据,也可以只包含一种流(视频、音频)的数据;

2. PES流是对原始ES流进行的第一层封装,PES流的基本单位是PES包,由包头和payload组成。

3. ES流即音视频裸流,是从编码器里面出来的原始视频音频流,ES流只包含一种内容,里面是视频或者音频;

4. ES首先需打包成PES包,然后PES加上PS包头,变成了标准的PS流进行存储或传输;

5. PES帧是变长的,每个帧的长度可能不一样;

6. 一般情况下是一帧数据放在一个PES包里面,但是一个PES包的最大长度为65535字节,因此一帧数据有可能被分为多个PES;

7 一个PS包包含若干个PES帧,是由PS头和一个或多个PES帧所组成

8. PS流解码时根据PS包里面的DTS和PTS时间戳确定帧的解码顺序和播放的时间。

9. 解封装PS流是一个封装的逆过程,需要先从原始的PS包里面去掉PS头,分解出PES包,然后去掉PES包头,得到ES裸流。

 

二、PS流码流结构

      I Frame    PS_Header | PS_Map | PES |.......|PES
      P Frame    PS_Header | PES | .......|PES
      Audio Frame   PS_Header | (PS_Map) | PES  (音频一般封装在一个PES里面即可)

更详细的结构图如下:

这里要特别注意上面的PS System Map,简称PSM。关于PSM的介绍:

(以下这段内容摘录自:博客「SunkingYang」的文章《H264解码之PS流解析》,原文链接:https://blog.csdn.net/y601500359/article/details/97649112)

————————————————

PSM介绍

PSM提供了对PS流中的原始流和他们之间的相互关系的描述信息;PSM是作为一个PES分组出现,当stream_id == 0xBC时,说明此PES包是一个PSM;PSM是紧跟在系统头部后面的;PSM是作为PS包的payload存在的;
PSM由很多字段组成,其字节顺序如下所示:

其中,最关键的是这两个字段:

stream_type字段:类型字段,占位8bit;表示原始流ES的类型;这个类型只能标志包含在PES包中的ES流类型;值0x05是被禁止的;常见取值类型有:MPEG-4 视频流:0x10;H.264 视频流:0x1B;G.711 音频流:0x90;因为PSM只有在关键帧打包的时候,才会存在,所以如果要判断PS打包的流编码类型,就根据这个字段来判断;
elementary_stream_id字段:流ID字段,占位8bit;表示此ES流所在PES分组包头中的stream_id字段的值;其中0x(C0~DF)指音频,0x(E0~EF)为视频;


PSM只有在关键帧打包的时候,才会存在;IDR包含了SPS,PPS和I帧;每个IDR NALU前一般都会包含SPS、PPS等NALU,因此将SPS、PPS、IDR的NALU 封装为一个PS 包,包括PS头,PS system header,PSM,PES;所以一个IDR NALU PS 包由外到内顺序是:PS header| PS system header | PSM| PES。对于其它非关键帧的PS包,就简单多了,直接加上PS头和PES 头就可以了。顺序为:PS header | PES header | h264raw data。以上是对只有视频video 的情况,如果要把音频Audio也打包进PS 封装,只需将数据加上PES header 放到视频PES 后就可以了。顺序如下:PS 包=PS头|PES(video)|PES(audio);
————————————————

简而言之,播放器需要拿到PSM表的信息,从里面提取出各个Stream的elementary_stream_id,stream_type,这样就知道了哪个流对应哪种编码格式。

三、播放器的功能

1. 播放本地PS文件(这个功能不是这个例子的重点,但是为了便于测试,也加进来了,其实文件播放和实时流播放有些流程是一样的)。

2.  支持从网络接收MPEG-PS流,用UDP方式接收数据,支持接收UDP裸流或带RTP头的MPEG-PS流。

3. 对网络收到的PS流进行保存。

4. 支持从内存中读取MPEG-PS流,支持对流进行解封装(PS-》PES,PES-》ES),最终将流转化成ES流格式。

5. 将ES流送给FFmpeg解码,显示视频。

6. 能够获得PS流中视音频轨的相关信息(视频编码格式、视频宽高、音频编码格式)。

 

三、播放器设计

播放器的界面如下图:

整个播放器的处理流程图如下:

  • 2
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 6
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值