首家启用html5直播技术,HTML5直播技术探究

传统直播技术,大多使用RTMP通过Flash进行传输。随着HTML5的逐渐实现,等媒体标签的浏览器支持,

很多视频逐渐向HTML5靠拢。Youtube等视频网站纷纷开始使用HTML5播放器,然而纵观当前的直播网站,大多

还是依赖Flash。直播为何不采用HTML5呢?

目前的HTML5直播思路有以下几种。一是使用js调用WebGL渲染视频,用websocket/XHR传输,比如jsmpeg项目,

实现了一个MPEG1的js解析器,该项目存在很多bug,另外由于MPEG1的效能极低(比GIF好不了多少),传输的视频

质量较差,而且js解析消耗很高CPU,这种方案不是很理想。二是使用Native的解码方案,使用MediaSourceExtension。

MSE支持一些格式,比如H264,VP8,VP9等(因浏览器而异),这里就VP8/VP9进行讨论。VP8/VP9的容器一般是webm,

然而chrome对webm的解析貌似不正确(很多网友说很多webm视频能够在Firefox上面使用MSE播放,但是不能在chrome上面

播放,ffmpeg压制出来的视频就是无法被chrome播放的)。webm格式大致可以分割为两部分,启动信息和媒体片段:

...

...

启动信息中包含了轨道数量,音视频轨道的编码,颜色,持续时间等等信息,后面的媒体信息里面包含了混杂的轨道流。MSE的一般模式

如下:

var video = document.querySelector('video');

var assetURL = 'frag_bunny.webm';

var mimeCodec = 'video/webm; codecs="vp9, vorbis"';

if ('MediaSource' in window && MediaSource.isTypeSupported(mimeCodec)) {

var mediaSource = new MediaSource();

//console.log(mediaSource.readyState); // closed

video.src = URL.createObjectURL(mediaSource);

mediaSource.addEventListener('sourceopen', sourceOpen);

} else {

console.error('Unsupported MIME type or codec: ', mimeCodec);

}

function sourceOpen (_) {

//console.log(this.readyState); // open

var mediaSource = this;

var sourceBuffer = mediaSource.addSourceBuffer(mimeCodec);

fetchAB(assetURL, function (buf) {

sourceBuffer.addEventListener('updateend', function (_) {

mediaSource.endOfStream();

video.play();

//console.log(mediaSource.readyState); // ended

});

sourceBuffer.appendBuffer(buf);

});

};

function fetchAB (url, cb) {

console.log(url);

var xhr = new XMLHttpRequest;

xhr.open('get', url);

xhr.responseType = 'arraybuffer';

xhr.onload = function () {

cb(xhr.response);

};

xhr.send();

};

基本套路是先创建一个MediaSource,然后将MediaSource的URL传给Video标签,然后MediaSource会open,在sourceopen

事件中创建一个特定编码的SourceBuffer,然后将webm流填入这个SourceBuffer。但是这种方案需要准备好的webm,这种

webm的启动信息里面包含了视频长度,每个偏移在哪里找等等信息。对于直播流来说,因为实时性要求,不可能在头部回写视频

流的信息,所以有了一种DASH的解决方案,DASH.js。这种方案

将webm的启动信息和媒体信息分离,并且将视频和音频轨道分离:

0818b9ca8b590ca3270a3433284dd417.png

通过HTTP传输,然后在浏览器端使用MSE解析。DASH会为每个轨道(视频/音频)创建一个SourceBuffer,先填入启动信息(头),

然后持续填入媒体片段(chunk)。但是MSE默认会从0开始播放,但是对于直播流,用户开始看的时候可能直播流已经进行了一段时间,

这时候如果向SourceBuffer填入当前时间(比如61.25s)的片段,Video标签并不会播放,这时候通过设置Video的currentTime可以

解决,通过SourceBuffer的buffered属性可以获得已经解析好的视频片段的开始时间和结束时间。但是实践发现,少于2s的chunk

极容易被解析失败,如果要求较小粒度的传输控制,可能要在前端使用js做buffer缓冲。

编程时需要注意的有,SourceBuffer的appendBuffer接受的buffer的时间范围是SourceBuffer的appendWindowStart和appendWindowEnd

控制的,在这个范围外的片段不会被接受。MSE的操作都是异步操作,SourceBuffer在解析的时候,不能再放入片段,所以需要监听updateend

事件,用队列处理异步请求。最后PS:VP9的码流非常清晰,500K就可以达到很好的效果。

参考阅读:

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值