隨著音視頻業務的快速發展,作為前端工程師,我們團隊也逐步深入到音視頻編解碼領域,涉及到流媒體技術中的文本、圖形、圖像、音頻和視頻多種理論知識的學習,并有機會大規模應用到具體實踐中。
我們自研了Web播放器并支持h.265解碼,保持畫質不變情況下,將碼流降低50%,達到減少帶寬成本,真正做到了h265解碼播放的全域覆蓋。本文主要分享了我們基于實現H.265格式的解封裝、解碼和播放。
背景
H.265又稱HEVC(全稱High Video ,高效率視頻編碼),是ITU-T H.264/MPEG-4 AVC標準的繼任者。相比H.264,H.265擁有更高的壓縮率,也就意味著同樣碼率(又稱比特率是指每秒傳送的比特(bit)數。單位為bps(Bit Per ),比特率越高,每秒傳送數據就越多,畫質就越清晰),H.265的畫質會更清晰,更高的壓縮率就能使用更低的存儲和傳輸成本。
H.264 vs H.265
H.264是當下用的最為廣泛的視頻編碼格式,H.265標準圍繞著現有的視頻編碼標準H.264mov視頻只有聲音沒有圖像,保留原來的某些技術,同時對一些相關的技術加以改進。新技術使用先進的技術用以改善碼流、編碼質量、延時和算法復雜度之間的關系,達到最優化設置。H.265和H.264都是基于塊的視頻編碼技術,主要的差別在于編碼單元的大小以及一些編碼算法細節,H.265將圖像劃分為“編碼樹單元( tree Unit, CTU)”,而不是像H.264那樣的16×16的宏塊。根據不同的編碼設置,編碼樹單元的尺寸可以被設置為64×64或有限的32×32或16×16。一般來說區塊尺寸越大,壓縮效率就越好。具體的算法及相關細節這里不具體展開了,還有一些其他的壓縮算法如因為H.265專利限制而生的開放編碼格式如AV1等,讀者可以參考其他相關文章。
如下圖,可以看到同樣主觀畫面質量,H.265(500K)僅需H.264(800K)一半左右的帶寬碼率。
瀏覽器現狀
如下圖,因為H.265專利及硬解支持情況不完善的原因,主流現代瀏覽器均不兼容H.265編碼的視頻播放(Edge新版本以插件方式支持),但是因為Apple對H.265的支持(這里作者認為這可能是一個很重要的標志,因為技術的發展很多時候不光是這個技術本身所決定的,而是很多因素共同作用的結果,商業也是其中很重要的一個因素),移動端ios 在11.0版本以上支持原生播放。
想要在瀏覽器端播放H.265視頻原生的標簽沒有辦法支持,但是因為視頻格式本身是連續圖像畫面和音頻的集合,參考了的源碼及video標簽內部的實現原理,可以通過 + Web Audio API的結合來模擬實現一個虛擬的video標簽來實現播放器功能。
Demo
因為直播流時效性的緣故,發布了一個播放H.265 mp4視頻(該視頻地址直接在瀏覽器中播放只有聲音而沒有畫面)的在線Demo,讀者可以有一個直觀感受。
地址:
效果
前期調研
播放器整體架構
基于傳統播放器的架構,我們設計的播放器架構如下:
視音頻基礎
因為前端領域對視頻領域的涉及場景不多,一個標簽就可以滿足大部分場景,但是經歷了這幾年直播和短視頻的爆發,視頻的需求和功能也變得越來越復雜,開發之前閱讀了很多視音頻領域相關的書籍和文章,在此先對視音頻基礎進行一個簡單的介紹。
視頻中我們通常說的視頻的格式,比如 .mp4, .mov, .wmv, .m3u8, .flv 等等被稱為。在一個視頻文件中音頻、視頻數據是分開存儲的,使用的壓縮算法也不一樣。其中作為容器主要包含了video數據、audio數據、(用于檢索視音頻格式等信息)。每個格式的封裝格式不一樣,比如FLV格式的基本單元是Tag,而MP4格式的基本單元是Box,輔助的meta信息用于檢索找到對應的原始數據。
而平時聽到的H.264, H.265等視頻編碼標準被稱為codec( and )。一個視頻格式比如mp4可以使用任何標準化的壓縮算法,這些信息都會被包含在一個視頻文件的meta信息中來告訴播放器該用什么編解碼算法來播放。
客戶端播放器
一個傳統的客戶端播放器播放一個視頻流經過了如下各個環節:
拉取數據 => 解封裝 => 音視頻解碼 => 采樣/像素數據發送到設備進行渲染。
對于流媒體,播放器客戶端通過拉流以數據源(音視頻流)為中心,進行管道式的傳輸。在此期間,對視頻流的讀取,轉換,分類,復制等一系列操作處理,以封裝的mp4流為例,需要對流進行解封裝、解碼、渲染等步驟:
瀏覽器video標簽
在探究的過程中,為了了解主流瀏覽器不支持H.265視頻播放的原因,以及瀏覽器端實現播放器原理的了解,通過對瀏覽器官方文檔及video標簽實現源碼的閱讀,整理了一個流程圖。
可以看到瀏覽器內部對視頻流播放的實現,在經過了等數據傳輸管道的處理后利用軟解或者Gpu硬解之后交給視頻設備及音頻設備進行同步及渲染。其中H.265的視頻因為硬解支持情況不完善,軟解可能有性能風險,所以在中被關閉了不支持,在中可以通過參數打開。我們就依照這個思路,利用瀏覽器提供的接口來實現一個模擬的video標簽。
設計過程
開發思路
開發思路按照從簡單到復雜的過程,對任務進行拆分,來完成H.265視頻點播及直播等各個場景的覆蓋,以mp4短視頻出發完成播放流程,再覆蓋直播場景,考慮如網絡抖動、內存控制等復雜因素,再針對直播m3u8等回放文件進行播放并開發視頻seek、倍速等功能。
mp4播放=>flv播放=>hls播放=>加入seek、倍速等功能
可行性分析
解決方案:
方案調整:
MP4點播流播放
方案調整:
FLV直播流播放
方案調整:
當前方案
播放流程
因為支持多種格式解封裝,只需要在在主線程中通過瀏覽器API(通常是fetch方法)拉取原始流數據并放到緩存中,等初始緩存到一個閾值時開啟進行解封裝及解碼;
在子線程()中通過主線程fetch方法觸發的數據回調接收數據存入環形緩沖區(內存環)中;
子線程將讀取到的音頻幀輸送到主線程中,通過Web Audio API緩存音頻數據,根據已解碼的視頻幀緩存隊列循環解碼保證緩存中一直緩存10幀rgba圖像數據;
主線程中根據音頻播放回調的pts消費并渲染視頻圖像;
循環以上操作直到fetch接口返回流已結束。
解碼器編譯
通過工具可以把C語言編寫的庫編譯成wasm并在瀏覽器中應用到視音頻解碼中。
我們的視頻解碼場景和通常的播放器一樣,通過依賴的通用接口來實現解封裝和解碼的工作。先通過編譯庫,再通過靜態庫的方式依賴到解封裝和解碼入口程序中。
測試表現
性能測試
測試視頻
因為flv直播視頻受時效性影響較大,拿720P高清的H.265 mp4視頻作為穩定輸入測試
測試機器
Pro (, 15-inch, Mid 2015)
性能情況
意味著最高能提供720P高清視頻如下幀率視頻流暢播放的能力:
可以看到這兩臺機器中,在非高速運動等普通的如電商場景25fps幀率的高清720p視頻已經能達到生產環境的標準,但是距離原生的速度還有一定距離。
瀏覽器兼容性
主要用到了及的支持,實際測試中主流瀏覽器、、、Edge均能通過兼容性測試。
ToDo
當前的技術方案已經能在大部分機器的主流瀏覽器上流暢的播放720P的高清直播流,但是在Edge瀏覽器及性能稍差的機器上還是存在高清視頻解碼性能不能滿足流暢播放的風險,針對達到速度的目標還有一定距離,尤其是匯編并行計算的支持,在視音頻及大規模數據處理中是很常見的性能優化策略,作者整理了幾個優化的方向,在未來還有更多探索的空間:
未來展望
通過H.265視頻播放將開源視音頻庫的能力及性能的優勢在瀏覽器端視音頻處理上有了一次深入的嘗試。視頻作為一種多媒體形式,相比現有的文字、圖像、音頻都能有更生動及更豐富信息的表現。尤其經過了直播和短視頻的爆發增長后mov視頻只有聲音沒有圖像,成為了一種基礎的多媒體形式,也是網絡及移動端手機性能等技術發展的體現。未來隨著5G及更高性能的硬件設備的發展會被更廣泛的應用到各個領域。瀏覽器在這場視頻革命中也是不可或缺的一個環節,通過這次的探索,為未來瀏覽器端擴展視音頻處理的通用能力提供了想象的空間,同時也在瀏覽器端通過向性能及能力靠近的路上做了一個落地的嘗試,雖然從測試情況看現在的表現還不如,但是隨著標準及技術的演進,為未來對性能要求比較高的圖形圖像及人工智能等相關方向在瀏覽器端處理一定會漸漸被廣泛的應用起來,比如如下幾個方向:
參考后言
本文介紹了我們在Web端H.265播放器上研發的過程和進展,后續還有很多繼續優化和深入的點。對相關知識感興趣的同學歡迎評論交流,我們會請作者和技術同學選擇問題進行答復。
校招進行時
火熱招聘20屆優秀畢業生
歡迎有志之士加入!
掃描二維碼
關注淘寶技術
............