javascript
使用基于 WebRTC 的 JavaScript API 在浏览器环境里调用本机摄像头
HTML5,JavaScript 和現(xiàn)代瀏覽器這套三駕馬車的組合,使得傳統(tǒng)的 Web 應用較之過去能實現(xiàn)更多更豐富的同用戶交互的功能。攝像頭如今已成為智能手機的標配,前端 Web 應用也出現(xiàn)了越來越多的打開本機攝像頭,掃描條形碼,二維碼等需求。
本文介紹兩種通過 JavaScript 實現(xiàn)在瀏覽器環(huán)境里調(diào)用設(shè)備攝像頭的開發(fā)技術(shù)。
方法1:基于現(xiàn)代瀏覽器支持的 WebRTC API 實現(xiàn)
我采用該思路實現(xiàn)了一個簡單的 Web 頁面,全部源代碼維護在如下的 Github 代碼倉庫里:
https://github.com/wangzixi-diablo/WebAppCollection/tree/main/WebContent/camera
首先看看運行該 Web 應用的效果。
通過筆記本電腦訪問,瀏覽器會彈出窗口詢問用戶是否允許該應用訪問設(shè)備上的攝像頭:
點擊允許之后,應用下方區(qū)域就會實時顯示我的攝像頭正對著的區(qū)域的圖像:
點擊“拍照”按鈕后,攝像頭顯示的圖像就會被固化在該按鈕下方,并且以圖片的方式自動保存到本地。
在我的三星手機上訪問該鏈接,首先一樣要授權(quán)該應用使用攝像頭:
對準我電腦面前一個異形手辦進行拍照:
自動生成一張圖片并保存到手機上:
幾個關(guān)鍵的實現(xiàn)點說明:
(1) JavaScript 之所以通過瀏覽器能夠識別到設(shè)備可用攝像頭(包括可用的音頻輸入和輸出設(shè)備),是因為現(xiàn)代瀏覽器支持的一組名為 WebRTC(Web Real Time Communication,網(wǎng)頁即時通信)的 API. 這個 API 能幫助 Web 應用開發(fā)人員通過簡單的 JavaScript 編程就能實現(xiàn)功能豐富的實時多媒體應用,而無需學習多媒體的數(shù)字信號處理知識。Web 應用的使用者也無需下載額外的插件。
用 JavaScript 進行設(shè)備可用多媒體設(shè)備的檢測,核心代碼如下:
navigator.mediaDevices.enumerateDevices().then(gotDevices).catch(handleError);這句代碼前半段 navigator.mediaDevices.enumerateDevices() 是瀏覽器支持的原生 API,這是一個異步調(diào)用,返回一個 promise 對象:
等到該異步調(diào)用的結(jié)果可供應用程序使用之后,我們通過鏈式調(diào)用 then 傳入的回調(diào)函數(shù) gotDevices 被觸發(fā),輸入的參數(shù)就是 navigator.mediaDevices.enumerateDevices() 調(diào)用的返回值。在調(diào)試器里看看這個返回值的明細:
從調(diào)試器里得知 enumerateDevices 這個函數(shù)返回了我筆記本電腦上一系列可用的音視頻設(shè)備,這些信息和我通過操作系統(tǒng)里看到的設(shè)備信息一致:
(2) 我的 html 頁面里定義了一個 HTML5 原生支持的 video 標簽, 用于顯示通過設(shè)備攝像頭觀察到的圖像。
但是我們還需要把設(shè)備攝像頭同這個 video 標簽關(guān)聯(lián)起來。方式是給這個標簽的 dom 對象的srcObject 屬性賦一個 MediaStream (媒體數(shù)據(jù)流)對象。
這個 MediaStream 對象從哪里來?同理,通過鏈式調(diào)用navigator.mediaDevices.getUserMedia(constraints) 得到:
(3) 點擊拍照按鈕后,自動生成圖片并下載到本地的功能在按鈕的 click 事件響應函數(shù)里實現(xiàn)。首先調(diào)用 canvas 標簽對應 Context 的 API drawImage 將顯示攝像頭內(nèi)容的 video 標簽當前顯示的內(nèi)容繪制到 canvas 標簽頁上,然后用此內(nèi)容生成格式為 jpeg 的圖片,下載到本地。
方法2:使用 SAP UI5 自定義控件
這種方式本質(zhì)上同方法一異曲同工,只不是封裝性更好,將方法1 描述的步驟,封裝成一個 SAP UI5 可重用控件,方便使用 SAP UI5 這個前端框架進行開發(fā)的前端程序員直接使用。
關(guān)于 SAP UI5 這個企業(yè)級前端開發(fā)框架的介紹,參考筆者之前的 InfoQ 文章:面向企業(yè)級前端應用的開發(fā)框架 UI5 的發(fā)展簡史介紹。
先回憶方法1 技術(shù)實現(xiàn)的要點:
(1) 在 web 應用的 HTML 頁面里定義 HTML5 用于顯示視頻的原生標簽: video
(2) 使用 WebRTC 的 API,獲取設(shè)備攝像頭對應的 MediaStream 對象,再將這個對象實例賦給 video 標簽對應的 DOM對象的 srcObject 屬性.
以上兩步實現(xiàn)之后,我們通過攝像頭觀察到的視頻圖像,就能實時顯示在 web 應用的 video 標簽里了。至于將某一時間點里 video 標簽里顯示的視頻內(nèi)容保存成圖片并下載,其對應的 JavaScript 代碼對于所有的前端框架并沒有太大的不同,本文略過。
因此,使用 SAP UI5 開發(fā),我們無非得重復以上兩個步驟。
SAP UI5 應用最常用的視圖格式為 XML 視圖。我們直接在 XML 視圖里加上 HTML 原生的 video 或者 div 標簽,會發(fā)生什么?
404 錯誤,UI5 框架加載不了 div.js 這個腳本文件。
筆者以前還在 SAP 成都研究院 CRM Fiori 應用開發(fā)團隊工作時,曾經(jīng)寫過一個 SAP UI5 框架代碼的學習教程,里面有兩篇文章,詳細介紹了 SAP UI5 XML 視圖運行時的渲染原理:
簡單地說,就是 SAP UI5 里有個 XMLTemplateProcessor.js 的實現(xiàn),運行時當 XML 視圖的源文件被瀏覽器加載解析成 DOM 后,它會對 DOM 樹進行深度優(yōu)先遍歷,對遇到的每一個 UI5 標簽,加載其實現(xiàn)文件(如果是在 UI5 調(diào)試模式下),然后創(chuàng)建這個標簽對應的實例。
回到本文的例子,我寫到 SAP UI5 XML 視圖里的 div 標簽被當成了一個 SAP UI5 XML 的控件,所以 UI5 框架自動去找這個根本不存在的 div 控件的實現(xiàn)文件,當然找不到了。
知道問題出在哪里,解決的思路自然就有了。自己把 HTML5 原生標簽 video 封裝成 UI5 控件不就行了?
SAP UI5 開源社區(qū)里已經(jīng)有一個封裝好的 library:
https://github.com/tiagobalmeida/openui5-camera
先看這個例子在筆記本電腦上訪問的效果:
點擊頁面上顯示的攝像頭拍攝的內(nèi)容,能自動保存成一張圖片。
手機上的顯示效果:
然后再來看這個 library 的實現(xiàn)原理。
這個 camera 自定義 UI5 控件實現(xiàn)的層級結(jié)果如下:
SAP UI5 自定義控件的實現(xiàn)包括三個 JavaScript 文件:
-
library.js:定義這個控件抬頭級別的控制信息,比如名稱,版本號,依賴等。
-
Camera.js:實現(xiàn)了將 WebRTC API 獲得的 MediaStream 對象實例綁定到控件封裝的 video 元素上的步驟。
- CameraRender.js:負責將這個自定義控件在XML視圖里的標簽 Camera 渲染成原生的video和canvas標簽的組合。
SAP UI5 的每一個控件都有一個與之對應的渲染類,用于完成 XML 視圖里 UI5 的標簽到 HTML5 原生標簽的轉(zhuǎn)換:
如何使用這個自定義控件呢?
在 XML 視圖里使用如下定義即可:
<cam:Cameraid="idCamera"width="800"height="600"snapshot=".onSnapshot" />總結(jié)
本文介紹了基于 WebRTC 技術(shù)使用 JavaScript 調(diào)用本機攝像頭的解決方案。WebRTC 可以為基于開放標準的應用程序添加實時通信功能,支持在對等點之間發(fā)送視頻、語音和通用數(shù)據(jù),允許開發(fā)人員構(gòu)建強大的語音和視頻通信解決方案。
WebRTC 可用于所有現(xiàn)代瀏覽器以及所有主流操作系統(tǒng)的本地客戶端。WebRTC 背后的技術(shù)是作為一個開放的 Web 標準實現(xiàn),并且可以在所有主流瀏覽器中作為常規(guī) JavaScript API 使用。
本文兩個例子在 Windows 10 操作系統(tǒng)的 Chrome 瀏覽器里實現(xiàn)并通過測試。對于原生客戶端,如 Android 和 iOS 應用程序,可以使用提供相同功能的 WebRTC 庫。
希望本文介紹的知識點對大家采取 JavaScript 實現(xiàn)瀏覽器環(huán)境里調(diào)用本機攝像頭的需求能有所幫助,感謝閱讀。
總結(jié)
以上是生活随笔為你收集整理的使用基于 WebRTC 的 JavaScript API 在浏览器环境里调用本机摄像头的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 冯诺依曼结构计算机包括哪五大部分?
- 下一篇: gradle idea java ssm