WebRTC 之數據採集—認識 MediaDevices

音視頻開發老舅 發佈 2022-09-20T11:27:46.837710+00:00

WebRTC 是一些列用於實時通信的 API 集合,使用 WebRTC API 可以快速搭建實時音視頻應用。WebRTC 雖然是 web API,但是它也提供了 native 工具庫,在 native 程序中引入 WebRTC 可以實現多端通信。

WebRTC 是一些列用於實時通信的 API 集合,使用 WebRTC API 可以快速搭建實時音視頻應用。WebRTC 雖然是 web API,但是它也提供了 native 工具庫,在 native 程序中引入 WebRTC 可以實現多端通信。因此 WebRTC 是實時音視頻應用必備的底層技術。

瀏覽器的 WebRTC API 提供了三部分能力:

  • MediaDevices
  • PeerConnections
  • DataChannels

其中 MediaDevices 負責數據採集,PeerConnections 負責音視頻流傳輸,DataChannels 提供了數據通道。

本篇為 WebRTC 系列第一篇,這篇文章主要看一下 MediaDevices 部分。與其他 native 端不同,在 WebRTC 之前瀏覽器沒有調用攝像頭麥克風等用戶媒體的能力,因此對瀏覽器端 WebRTC 而言,MediaDevices 是必不可少的一部分。

在瀏覽器中我們通過 window.navigator.mediaDevices 來獲取 MediaDevices 對象,看下 mediaDevices 對象上的幾個重要方法:

【免費】FFmpeg/WebRTC/RTMP/NDK/Android音視頻流媒體高級開發-學習視頻教程-騰訊課堂

C++音視頻開發學習資料點擊莬費領取→音視頻開發(資料文檔+視頻教程+面試題)(FFmpeg+WebRTC+RTMP+RTSP+HLS+RTP)

getUserMedia

getUserMedia 是 WebRTC 中最重要的 API,它給瀏覽器訪問用戶音視頻的能力,它是瀏覽器訪問用戶媒體信息的唯一方式,因此即使在非實時音視頻場景,只要涉及到用戶攝像頭和麥克風的操作都離不開這個 API。

使用 getUserMedia:

navigator.mediaDevices.getUserMedia({ audio: true, video: true })

調用 API 後瀏覽器會向用戶請求需要的攝像頭麥克風權限,此函數會返回 Promise,當用戶同意授權後開始採集,resolve 採集到的 MediaStream,想要在本地預覽 MediaStream 很簡單,只需要創建一個 video 標籤,把 MediaStream 賦值給 video 的 srcObject 即可:

<video id="preview"></video>
<script>
        const preview = document.getElementById('preview');
        navigator.mediaDevices.getUserMedia({ video: true, audio: true }).then(
                stream => preview.srcObject = stream;
        );
</script>

getUserMedia 的參數是 MediaStreamConstraints 類型,它可以指定採集到流的條件,可以只採集音頻或視頻軌道,可以指定視頻大小,指定採集設備等,詳見文檔。

採集到的 MediaStream 對象實際上是由多條軌道(tracks)組成的,video、audio 分別有自己的軌道,使用 getVideoTracks,getAudioTracks 可以分別獲取視頻音頻軌道,也可以使用 getTracks 獲取全部軌道。

音視頻軌道對象為 MediaStreamTrack,在音視頻應用中,雖然我們最終看到的是以一個帶有音頻和視頻的 video 資源,但是實際上從採集到處理音視頻都是分開的,因此在這裡我們可以對音視頻的處理和發送都是針對 MediaStreamTrack 對象來做的,我們可以把 track 數據傳入其他處理程序如 MediaStreamTrackProcessor 等,也可以把 track 傳入 PeerConnections 進行發送。

getDisplayMedia

getDisplayMedia 用於屏幕錄製或共享的場景,它採集的是用戶屏幕的數據,桌面、應用、標籤頁等都可以作為採集對象,採集到的數據封裝位一個 MediaStream 對象,可供後續處理。getDisplayMedia 的使用方法和 getUserMedia 非常相似:

<video id="preview"></video>
<script>
        const preview = document.getElementById('preview');
        navigator.mediaDevices.getDisplayMedia({ video: true, audio: true }).then(
                stream => preview.srcObject = stream;
        );
</script>

這裡依舊使用一個 video 作為預覽窗口,當調用 getDisplayMedia 時瀏覽器會彈出共享內容選擇窗口,當用戶選擇共享區域後 resolve 採集到的 MediaStream ,這裡比較特殊的一點是 getDisplayMedia 至少需要有一個 video 軌道數據。之後拿到 MediaStream 對象就可以根據需要執行後續的操作。

【免費】FFmpeg/WebRTC/RTMP/NDK/Android音視頻流媒體高級開發-學習視頻教程-騰訊課堂

C++音視頻開發學習資料點擊莬費領取→音視頻開發(資料文檔+視頻教程+面試題)(FFmpeg+WebRTC+RTMP+RTSP+HLS+RTP)

enumerateDevices

enumerateDevices 可以獲取可用的媒體輸入和輸出設備列表信息,在實際應用中,用戶設備上看有多個攝像頭和麥克風,這時可以通過 enumerateDevices 拿到全部的設備信息,每個設備有一個 id 標識,這個 id 可以作為 getUserMedia 的參數傳入來指定採集設備。

devicechange

devicechange 是一個事件,可以通過 ondevicechange 或 addEventlistener 來監聽,當用戶的設備信息發生變化時會觸發,可以在 devicechange 後重新獲取設備列表更新設備信息。

以上幾個就是 mediaDevices 中比較重要的方法。mediaDevices API 是構建多媒體應用的基礎 API,它們提供了瀏覽器訪問攝像頭麥克風和屏幕錄製的能力,給 web 端應用帶來了更多可能。

關鍵字: