一、getUserMedia API简介
getUserMedia API为用户提供访问硬件设备媒体(摄像头、视频、音频、地理位置等)的接口,基于该接口,开发者可以在不依赖任何浏览器插件的条件下访问硬件媒体设备。
getUserMedia API最初是navigator.getUserMedia,目前已被最新Web标准废除,变更为navigator.mediaDevices.getUserMedia(),但浏览器支持情况不如旧版API普及。
MediaDevices.getUserMedia()方法提示用户允许使用一个视频和/或一个音频输入设备,例如相机或屏幕共享和/或麦克风。如果用户给予许可,就返回一个Promise对象,MediaStream对象作为此Promise对象的Resolved[成功]状态的回调函数参数,相应的,如果用户拒绝了许可,或者没有媒体可用的情况下PermissionDeniedError或者NotFoundError作为此Promise的Rejected[失败]状态的回调函数参数。注意,由于用户不会被要求必须作出允许或者拒绝的选择,所以返回的Promise对象可能既不会触发resolve也不会触发reject。
参考官方API:https://developer.mozilla.org/zh-CN/docs/Web/API/MediaDevices/getUserMedia
手机版本支持情况:
二、页面代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>拍照</title>
</head>
<body>
<video id="video" width="640" height="480" autoplay="autoplay"></video>
<!--拍照按钮-->
<div>
<button id="capture">拍照</button>
</div>
<!--描绘video截图-->
<canvas id="canvas" width="640" height="480"></canvas>
<script>
let video = document.getElementById("video");
let canvas = document.getElementById("canvas");
let context = canvas.getContext("2d");
// 老的浏览器可能根本没有实现 mediaDevices,所以我们可以先设置一个空的对象
if (navigator.mediaDevices === undefined) {
navigator.mediaDevices = {};
}
// 一些浏览器部分支持 mediaDevices。我们不能直接给对象设置 getUserMedia
// 因为这样可能会覆盖已有的属性。这里我们只会在没有getUserMedia属性的时候添加它。
if (navigator.mediaDevices.getUserMedia === undefined) {
navigator.mediaDevices.getUserMedia = function (constraints) {
// 首先,如果有getUserMedia的话,就获得它
var getUserMedia = navigator.webkitGetUserMedia || navigator.mozGetUserMedia;
// 一些浏览器根本没实现它 - 那么就返回一个error到promise的reject来保持一个统一的接口
if (!getUserMedia) {
return Promise.reject(new Error('getUserMedia is not implemented in this browser'));
}
// 否则,为老的navigator.getUserMedia方法包裹一个Promise
return new Promise(function (resolve, reject) {
getUserMedia.call(navigator, constraints, resolve, reject);
});
}
}
//默认使用前摄像头,强制使用后置摄像头如下设置
// let constraints = {video: { facingMode: { exact: "environment" } }};
let constraints = {video: true};
navigator.mediaDevices.getUserMedia(constraints)
.then(function (stream) {
// 旧的浏览器可能没有srcObject
if ("srcObject" in video) {
video.srcObject = stream;
} else {
// 防止在新的浏览器里使用它,应为它已经不再支持了
video.src = window.URL.createObjectURL(stream);
}
video.onloadedmetadata = function (e) {
video.play();
};
})
.catch(function (err) {
console.log(err.name + ": " + err.message);
});
//注册拍照按钮的单击事件
document.getElementById("capture").addEventListener("click", function () {
//绘制画面
context.drawImage(video, 0, 0, 640, 480);
});
</script>
</body>
</html>
上面代码完成后可以直接在浏览器里使用http://localhost:8080查看。或者使用127.0.0.1进行本地查看。但是若是想要设置其他的ip地址,例如:192.168.0.11 等IP地址则无法访问。
原因:getUserMedia除本地地址外,只支持安全的协议访问。也就是说需要用https才能访问,下面讲解如何配置https。
三、https配置
1、使用jdk提供的keytoo工具生成秘钥
打开命令行,输入下列代码:
keytool -genkey -alias tomcat -keyalg RSA -keystore ./server.keystore
进入命令后按下列输入内容:
运行完毕后会在当前路径下得到一个名为server.keystore的秘钥文件。
2、将秘钥加入springboot工程
将秘钥拷贝到项目根路径。注意:跟路径指的是工程的第一层路径,请注意位置。
3、配置springboot的配置文件application.properties,加入下列代码:
server.port=8443
server.ssl.key-store=server.keystore
server.ssl.key-alias=tomcat
server.ssl.enabled=true
server.ssl.key-store-password=123456
server.ssl.key-store-type=JKS
4、启动项目,访问路径 https://localhost:8443/。
**注意协议和端口号**
会看到如下错误提示,这是因为我们自己配置的秘钥(证书)没有官方注册,无法被浏览器识别。可以点高级 -> 继续前往 。
这时能正常访问则说明我们的https配置完毕。可以替换成其他IP地址测试能正常使用摄像头了。