首頁  >  文章  >  web前端  >  HTML5如何實現視訊直播功能

HTML5如何實現視訊直播功能

不言
不言原創
2018-06-12 11:56:2238378瀏覽

最近視訊直播比較火,發現目前WEB 上主流的視訊直播方案有HLS 和RTMP,行動WEB 端目前以HLS 為主,PC端則以RTMP 為主實時性較好,接下來將圍繞這兩種視訊串流協定來展開H5直播主題分享,以下透過本文給大家分享HTML5視訊直播思維詳解,一起看看吧

 前言

前不久抽空對目前比較火的視訊直播,做了下研究與探索,了解其整體實現流程,以及探討行動端HTML5直播可行性方案。

發現目前WEB 上主流的視訊直播方案有HLS 和RTMP,行動WEB 端目前以HLS 為主(HLS有延遲性問題,也可以藉助video.js 採用RTMP),PC端則以RTMP為主即時性較好,接下來將圍繞這兩種視訊串流協定展開H5直播主題分享。

一、視訊串流協定HLS與RTMP

#1. HTTP Live Streaming

HTTP Live Streaming(簡稱HLS)是一個基於HTTP 的視訊串流協議,由Apple 公司實現,Mac OS 上的QuickTime、Safari 以及iOS 上的Safari 都能很好的支援HLS,高版本Android 也增加了對HLS 的支援。一些常見的客戶端如:MPlayerX、VLC 也都支援 HLS 協定。

HLS 協定是基於HTTP,而一個提供HLS 的伺服器需要做兩件事:

編碼:以H.263 格式對影像進行編碼,以MP3 或HE-AAC 對聲音進行編碼,最終打包到MPEG-2 TS(Transport Stream)容器之中;分割:把編碼好的TS 文件等長切分成後綴為ts 的小文件,並生成一個.m3u8 的純文本索引文件;瀏覽器使用的是m3u8 檔。 m3u8 跟音訊清單格式 m3u 很像,可以簡單的認為 m3u8 就是包含多個 ts 檔案的播放清單。播放器依序逐一播放,全部放完再請求一下 m3u8 文件,獲得包含最新 ts 文件的播放清單繼續播,周而復始。整個直播過程就是依靠一個不斷更新的 m3u8 和一堆小的 ts 檔案組成,m3u8 必須動態更新,ts 可以走 CDN。一個典型的m3u8 檔案格式如下:

#EXTM3U
#EXT-X-STREAM-INF:PROGRAM-ID=1, BANDWIDTH=200000
gear1/prog_index.m3u8
#EXT-X-STREAM-INF:PROGRAM-ID=1, BANDWIDTH=311111
gear2/prog_index.m3u8
#EXT-X-STREAM-INF:PROGRAM-ID=1, BANDWIDTH=484444
gear3/prog_index.m3u8
#EXT-X-STREAM-INF:PROGRAM-ID=1, BANDWIDTH=737777
gear4/prog_index.m3u8

可以看到HLS 協定本質還是一個個的HTTP 請求/ 回應,所以適應性很好,不會受到防火牆影響。但它也有一個致命的弱點:延遲現象非常明顯。如果每個 ts 依照 5 秒來切分,一個 m3u8 放 6 個 ts 索引,那麼至少就會帶來 30 秒的延遲。如果減少每個 ts 的長度,減少 m3u8 中的索引數,延遲確實會減少,但會帶來更頻繁的緩衝,對服務端的請求壓力也會倍增。所以只能根據實際情況找到一個折中的點。

對於支援HLS 的瀏覽器來說,直接這樣寫就能播放了:  

634240a5901e6a50af1bf103ffff6583a6a9c6d3f311dabb528ad355798dc27d

注意:HLS 在PC 端只支援safari瀏覽器,類似chrome瀏覽器使用HTML5 video  

標籤無法播放m3u8 格式,可直接採用網路上一些較成熟的方案,如:sewise-player、MediaElement、videojs-contrib-hls、jwplayer。

2. Real Time Messaging Protocol

Real Time Messaging Protocol(簡稱 RTMP)是 Macromedia 開發的一套視訊直播協議,現在屬於 Adob​​​​e。這套方案需要建造專門的 RTMP 串流服務如 Adob​​​​e Media Server,並且在瀏覽器中只能使用 Flash 實作播放器。它的即時性非常好,延遲很小,但無法支援行動裝置 WEB 播放是它的硬傷。

雖然無法在iOS的H5頁面播放,但對於iOS原生應用程式是可以自己寫解碼去解析的, RTMP 延遲低、即時性較好。瀏覽器端,HTML5 video

標籤無法播放 RTMP 協定的視頻,可以透過 video.js 來實現。

89746fa42e6639624db223658efe656b
81fadcec8b2d77dd041bb7285e564d7e
3d9ab59ae1bd658ff8a687eb40826d0f
a6a9c6d3f311dabb528ad355798dc27d
ed2103ecac15361885615b704a6477d52cacc6d41bbb37262a98f745aa00fbf0
3f1c4e4b6b16bbbd69b2ee476dc4f83a
videojs.options.flash.swf = ‘video.swf’;
videojs(‘example_video_1′).ready(function() {
this.play();
});
2cacc6d41bbb37262a98f745aa00fbf0

3. 視訊串流協定HLS與RTMP比較

二、直播形式

#目前直播展示形式,通常以YY直播、映客直播這種頁居多,可看到其結構可分成三層:  

① 背景影片層 

② 追蹤、評論模組 

③ 讚動畫

而現行H5類似直播頁面,實現技術難點不大,其可透過實作方式分為:  

① 底部視訊背景使用video視訊標籤實現播放 

② 追蹤、評論模組利用WebScoket 來即時發送和接收新的訊息透過DOM 和CSS3 實現 

③ 讚利用CSS3 動畫

了解完直播形式之後,接下來整體了解直播流程。

三、直播整體流程  

#直播整體流程大致可分為:

視訊擷取端:可以是電腦上的影音輸入裝置、或手機端的相機、或麥克風,目前以行動裝置手機影片為主。

直播串流視訊服務端:一台Nginx伺服器,擷取視訊錄製端傳輸的視訊串流(H264/ACC編碼),由伺服器端進行解析編碼,推送RTMP /HLS格式影片串流至影片播放端。 

影片播放端:可以是電腦上的播放器(QuickTime Player、VLC),手機端的native播放器,還有就是 H5 的video標籤等,目前還是以手機端的native播放器為主。

(web前端學習交流群:328058344 禁止閒聊,非喜勿進!)

四、H5 錄製影片

#對於H5視訊錄製,可以使用強大的webRTC (Web Real-Time Communication)是一個支援網頁瀏覽器進行即時語音對話或視訊對話的技術,缺點是只在PC 的Chrome 上支援較好,行動裝置支援不太理想。

使用 webRTC 錄製影片基本流程  

① 呼叫 window.navigator.webkitGetUserMedia()  

取得使用者的PC攝影機影片資料。 

② 將取得到視訊串流資料轉換成 window.webkitRTCPeerConnection  

(一種視訊串流資料格式)。 

③ 利用 WebScoket  

將視訊串流資料傳送至服務端。

注意:

雖然Google一直在推WebRTC,目前已有不少成型的產品出現,但是大部分行動端的瀏覽器還不支援webRTC(最新iOS 10.0也不支援) ,所以真正的錄影還是要靠客戶端(iOS,Android)來實現,效果會好一些。

WebRTC支援度

WebRTC支援度

iOS原生應用程式呼叫相機錄製影片流程

① 音視頻的採集,利用AVCaptureSession和AVCaptureDevice可以收集到原始的音視頻資料流。

② 對視訊進行H264編碼,對音訊進行AAC編碼,在iOS中分別有已經封裝好的編碼庫(x264編碼、faac編碼、ffmpeg編碼)來實現對音訊視訊的編碼。

③ 將編碼後的音、視訊資料進行組裝封包。

④ 建立RTMP連線並上推到服務端。

    五、搭建Ng

#五、建置Nginx Rtmp直播串流服務

安裝nginx、nginx-rtmp-module

① 先clone nginx專案到本地:

brew tap homebrew/nginx

#② 執行安裝nginx-rtmp-module

brew install nginx-full –with-rtmp-module

2. nginx.conf設定文件,設定RTMP、HLS

查找到nginx.conf設定檔(路徑/usr /local/etc/nginx/nginx.conf),設定RTMP、HLS。

① 在http節點之前加入rtmp 的設定內容:

#② 在http中加入hls 的設定

    #

3. 重启nginx服务

重启nginx服务,浏览器中输入 http://localhost:8080,是否出现欢迎界面确定nginx重启成功。

nginx -s reload

六、直播流转换格式、编码推流

当服务器端接收到采集视频录制端传输过来的视频流时,需要对其进行解析编码,推送RTMP/HLS格式视频流至视频播放端。通常使用的常见编码库方案,如x264编码、faac编码、ffmpeg编码等。鉴于 FFmpeg 工具集合了多种音频、视频格式编码,我们可以优先选用FFmpeg进行转换格式、编码推流。

1.安装 FFmpeg 工具

brew install ffmpeg

2.推流MP4文件

视频文件地址:/Users/gao/Desktop/video/test.mp4

推流拉流地址:rtmp://localhost:1935/rtmplive/home,rtmp://localhost:1935/rtmplive/home

//RTMP 协议流
ffmpeg -re -i /Users/gao/Desktop/video/test.mp4 -vcodec libx264 -acodec aac -f flv rtmp://10.14.221.17:1935/rtmplive/home
//HLS 协议流
ffmpeg -re -i /Users/gao/Desktop/video/test.mp4 -vcodec libx264 -vprofile baseline -acodec aac -ar 44100 -strict -2 -ac 1 -f flv -q 10 rtmp://10.14.221.17:1935/hls/test

注意:  

当我们进行推流之后,可以安装VLC、ffplay(支持rtmp协议的视频播放器)本地拉流进行演示

3.FFmpeg推流命令

① 视频文件进行直播

ffmpeg -re -i /Users/gao/Desktop/video/test.mp4 -vcodec libx264 -vprofile baseline -acodec aac -ar 44100 -strict -2 -ac 1 -f flv -q 10 rtmp://192.168.1.101:1935/hls/test
ffmpeg -re -i /Users/gao/Desktop/video/test.mp4 -vcodec libx264 -vprofile baseline -acodec aac -ar 44100 -strict -2 -ac 1 -f flv -q 10 rtmp://10.14.221.17:1935/hls/test

② 推流摄像头+桌面+麦克风录制进行直播

ffmpeg -f avfoundation -framerate 30 -i “1:0″ \-f avfoundation -framerate 30 -video_size 640x480 -i “0” \-c:v libx264 -preset ultrafast \-filter_complex ‘overlay=main_w-overlay_w-10:main_h-overlay_h-10′ -acodec libmp3lame -ar 44100 -ac 1 -f flv rtmp://192.168.1.101:1935/hls/test

更多命令,请参考:

FFmpeg处理RTMP流媒体的命令大全  

FFmpeg常用推流命令

七、H5 直播视频播放

移动端iOS和 Android 都天然支持HLS协议,做好视频采集端、视频流推流服务之后,便可以直接在H5页面配置 video 标签播放直播视频。

<video controls preload=“auto” autoplay=“autoplay” loop=“loop” webkit-playsinline>
<source src=“http://10.14.221.8/hls/test.m3u8″ type=“application/vnd.apple.mpegurl” />
<p class=“warning”>Your browser does not support HTML5 video.</p>
</video>

八、总结

本文从视频采集上传,服务器处理视频推流,以及H5页面播放直播视频一整套流程,具体阐述了直播实现原理,实现过程中会遇到很多性能优化问题。

① H5 HLS 限制必须是H264+AAC编码。  

② H5 HLS 播放卡顿问题,server 端可以做好分片策略,将 ts 文件放在 CDN 上,前端可尽量做到 DNS 缓存等。  

③ H5 直播为了达到更好的实时互动,也可以采用RTMP协议,通过video.js 实现播放。

以上就是本文的全部内容,希望对大家的学习有所帮助,更多相关内容请关注PHP中文网!

相关推荐:

使用HTML5实现网页音乐播放器

HTML5 video播放器全屏(fullScreen)实现的方法

以上是HTML5如何實現視訊直播功能的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn