注:只在微信QQ内置浏览器(水果机暂不支持)、Chrome浏览器(安卓机)、Safari浏览器下测试过
// 判断Android还是IOS
var u = navigator.userAgent;
var isAndroid = u.indexOf('Android') > -1 || u.indexOf('Adr') > -1;
var isiOS = !!u.match(/\(i[^;]+;( U;)? CPU.+Mac OS X/);
// 摄像头调起失败
var onError = function(error){
alert('Webcam Error\nName: '+error.name + '\nMessage: '+error.message);
}
// 摄像头调起成功
var onSuccess = function(stream){
var video = document.createElement('video');
video.style.width = document.documentElement.clientWidth + 'px';
video.style.height = document.documentElement.clientHeight + 'px';
video.srcObject = stream;
// to start the video, when it is possible to start it only on userevent. like in android
video.body.addEventListener('click', function(){
video.play();
});
// wait until the video stream is ready
var interval = setInterval(function(){
if(!video.videoWidth){
return;
}
document.body.appendChild(video);
clearInterval(interval);
}, 1000/50);
}
// check API is available
if(navigator.mediaDevices === undefined || navigator.mediaDevices.enumerateDevices === undefined || navigator.mediaDevices.getUserMedia === undefined){
if( navigator.mediaDevices === undefined ){
var fctName = 'navigator.mediaDevices';
}
else if( navigator.mediaDevices.enumerateDevices === undefined ){
var fctName = 'navigator.mediaDevices.enumerateDevices';
}
else if( navigator.mediaDevices.getUserMedia === undefined ){
var fctName = 'navigator.mediaDevices.getUserMedia';
}
else{
console.assert(false);
}
onError({
name: '',
message: 'WebRTC issue-! '+fctName+' not present in your browser'
})
}
// get available devices
navigator.mediaDevices.enumerateDevices().then(function(devices){
// 如果是水果机
if(isiOS){
navigator.mediaDevices.getUserMedia({
audio: false,
video: {
facingMode: 'environment'
}
}).then(onSuccess).catch(onError);
}
// 如果是安卓机
else{
var videoSourceId;
var exArray = [];
for(var i = 0; i < devices.length; i++){
var deviceInfo = devices[i];
// 判断是否是相机设备
if(deviceInfo.kind == "videoinput"){
exArray.push(deviceInfo.deviceId);
// 判断是否是后置摄像头
if(deviceInfo.label.split(', ')[1] == "facing back") {
videoSourceId = deviceInfo.deviceId;
}
}
}
// deviceInfo.label为空
if (!videoSourceId) {
switch (exArray.length) {
// 单摄像头
case 1:
videoSourceId = exArray[0];
break;
// 多摄像头
case 2:
videoSourceId = exArray[1];
break;
default:
break;
}
}
navigator.mediaDevices.getUserMedia({
audio: false,
video: {
optional: [{sourceId: videoSourceId}]
}
}).then(onSuccess).catch(onError);
}
}).catch(onError);
网上大多数的demo都是调用 Navigator.getUserMedia(),但实际上支持iOS11调用摄像头的是 MediaDevices.getUserMedia()。
经测试,发现facingMode: "environment"
属性对安卓系统无效,于是只能用类似
MediaStreamTrack.getSources 函数的方法,感觉不是很严谨呢 _(:3」∠)_
2018.04.20更新
经测试,安卓机已不再支持 MediaStreamTrack.getSources 函数方法,并且从
mediaDevices.enumerateDevices 函数获取的所有 devices[i].label 值为空,不再包含 "facing back" 字段。
欢迎小伙伴留言讨论~