不会吧不会吧!现在都2023年了竟然还有人在用ie浏览器!
文章内容有点长 耐心看完,基本上能遇到的问题 都记录在这里了;
问题1: 调用摄像头并兼容ie浏览器
用户调用摄像头一般使用navigator.mediaDevices,在ie浏览器这个对象获取为undefined,所以ie就不能使用navigator.mediaDevices;
想在ie浏览器中正常调用摄像头并拍照,可以借用jquery-webcam-plugin插件。它是一个封装了摄像头功能的Jquery插件。
jquery-webcam-plugin插件官方说是同时兼容谷歌、ie等浏览器,但是实际开发中我发现在谷歌浏览器并能用;最后只能写两套代码同时兼容多端浏览器,不知道是不是是我还没研究很明白的原因,如果有小伙伴开发能使用可以留言互相学习下。
下面是同时兼容谷歌和ie的代码,具体样式可以根据自己的项目需要进行自调;
页面需要同时引入jquery和jquery.webcam.min.js
关于这两个插件jquery.webcam-plugin官方demo中都有
<div class="main">
<div style="display: flex">
<div id="webcam"></div>
<div style="margin-left: 20px;float: right">
<div class="imgBox ieimgBox" style="background-image: url('{$photo.photo ?? ''}')"></div>
<canvas id="canvas" height="240" width="320" style="display: none"></canvas>
</div>
</div>
</div>
<form id="add-form" class="form-horizontal" role="form" data-toggle="validator" method="POST" action="">
<div class="video-box">
<div>
<video id="video" width="200" height="200" autoplay></video>
<img class="imgBox" src="{$photo.photo}" style="vertical-align: top;" />
</div>
<input type="hidden" name="photo" id="photo">
</div>
<div class="form-group layer-footer noprint">
<div class="col-xs-12 col-sm-8">
<button type="button" class="btn btn-info" id="snap">拍照</button>
</div>
</div>
</form>
<script>
var pos = 0;
var ctx = null;
var cam = null;
var image = null;
var filter_on = false;
var filter_id = 0;
function changeFilter() {
if (filter_on) {
filter_id = (filter_id + 1) & 7;
}
}
// 兼容ie的核心方法
function ieFn() {
jQuery("#webcam").webcam({
width: 320,
height: 240,
mode: "callback",
swffile: "./jscam_canvas_only.swf",
onTick: function(remain) {},
onSave: function(data) {
var col = data.split(";");
var img = image;
if (false == filter_on) {
for(var i = 0; i < 320; i++) {
var tmp = parseInt(col[i]);
img.data[pos + 0] = (tmp >> 16) & 0xff;
img.data[pos + 1] = (tmp >> 8) & 0xff;
img.data[pos + 2] = tmp & 0xff;
img.data[pos + 3] = 0xff;
pos+= 4;
}
} else {
var id = filter_id;
var r,g,b;
var r1 = Math.floor(Math.random() * 255);
var r2 = Math.floor(Math.random() * 255);
var r3 = Math.floor(Math.random() * 255);
for(var i = 0; i < 320; i++) {
var tmp = parseInt(col[i]);
/* Copied some xcolor methods here to be faster than calling all methods inside of xcolor and to not serve complete library with every req */
if (id == 0) {
r = (tmp >> 16) & 0xff;
g = 0xff;
b = 0xff;
} else if (id == 1) {
r = 0xff;
g = (tmp >> 8) & 0xff;
b = 0xff;
} else if (id == 2) {
r = 0xff;
g = 0xff;
b = tmp & 0xff;
} else if (id == 3) {
r = 0xff ^ ((tmp >> 16) & 0xff);
g = 0xff ^ ((tmp >> 8) & 0xff);
b = 0xff ^ (tmp & 0xff);
} else if (id == 4) {
r = (tmp >> 16) & 0xff;
g = (tmp >> 8) & 0xff;
b = tmp & 0xff;
var v = Math.min(Math.floor(.35 + 13 * (r + g + b) / 60), 255);
r = v;
g = v;
b = v;
} else if (id == 5) {
r = (tmp >> 16) & 0xff;
g = (tmp >> 8) & 0xff;
b = tmp & 0xff;
if ((r+= 32) < 0) r = 0;
if ((g+= 32) < 0) g = 0;
if ((b+= 32) < 0) b = 0;
} else if (id == 6) {
r = (tmp >> 16) & 0xff;
g = (tmp >> 8) & 0xff;
b = tmp & 0xff;
if ((r-= 32) < 0) r = 0;
if ((g-= 32) < 0) g = 0;
if ((b-= 32) < 0) b = 0;
} else if (id == 7) {
r = (tmp >> 16) & 0xff;
g = (tmp >> 8) & 0xff;
b = tmp & 0xff;
r = Math.floor(r / 255 * r1);
g = Math.floor(g / 255 * r2);
b = Math.floor(b / 255 * r3);
}
img.data[pos + 0] = r;
img.data[pos + 1] = g;
img.data[pos + 2] = b;
img.data[pos + 3] = 0xff;
pos+= 4;
}
}
if (pos >= 0x4B000) {
ctx.putImageData(img, 0, 0);
pos = 0;
}
},
onCapture: function () {
webcam.save();
jQuery("#flash").css("display", "block");
jQuery("#flash").fadeOut(100, function () {
jQuery("#flash").css("opacity", 1);
});
},
debug: function (type, string) {
},
onLoad: function () {
}
});
}
// 兼容谷歌的核心方法
function chromeFn() {
const video = document.getElementById('video');
navigator.mediaDevices.getUserMedia({ video: true })
.then(function (stream){
video.srcObject = stream;
})
.catch(function (err){
console.error('Error accessing camera', err);
});
}
captureFn()
// 初始加载判断兼容
function captureFn() {
if(navigator.mediaDevices === undefined){
ieFn()
var ieDom = document.getElementsByClassName('main')[0]
var chromwDom = document.getElementsByClassName('video-box')[0]
ieDom.setAttribute("style",'display: block')
chromwDom.setAttribute("style",'display: none')
}else{
chromeFn()
var ieDom = document.getElementsByClassName('main')[0]
var chromwDom = document.getElementsByClassName('video-box')[0]
ieDom.setAttribute("style",'display: none')
chromwDom.setAttribute("style",'display: block')
}
}
window.addEventListener("load", function() {
jQuery("body").append("<div id=\"flash\"></div>");
var canvas = document.getElementById("canvas");
if (canvas.getContext) {
ctx = document.getElementById("canvas").getContext("2d");
ctx.clearRect(0, 0, 320, 240);
var img = new Image();
img.src = "/image/logo.gif";
img.onload = function() {
ctx.drawImage(img, 129, 89);
}
image = ctx.getImageData(0, 0, 320, 240);
}
}, false);
const snap = document.getElementById('snap');
snap.addEventListener('click', function(){
if(navigator.mediaDevices === undefined){
webcam.capture();
changeFilter()
var canvas = document.getElementById("canvas");
const dateUrl = canvas.toDataURL('image/png')
$('#photo').val(dateUrl);
// ie用的背景展示拍照的图片 可以方便对拍照图片进行剪裁,解决图片变形问题
$('.ieimgBox').css("background-image", "url(" + dateUrl +")");
}else{
const canvas = document.createElement('canvas');
const context = canvas.getContext('2d');
canvas.width = video.videoWidth;
canvas.height = video.videoHeight;
context.drawImage(video, 0, 0, canvas.width, canvas.height);
const dataURL = canvas.toDataURL('image/png');
$('.imgBox').attr('src', dataURL)
$('#photo').val(dataURL);
}
});
</script>
问题2:ie浏览器借助flash调用摄像头,如何去掉每次进入都提示允许的弹窗
咱们利用jquery-webcam-plugin插件兼容ie浏览器调用摄像头,每次进入页面都会提示让你 Adobe Flash Player设置 点击完允许 下次进来还弹
解决步骤:
⚠️注意:前提是你的电脑上安装的有Adobe Flash Player插件,jquery-webcam-plugin插件也是借用flash进行调用摄像头的
1、打开控制面板 找到Flash Player,并双击打开(可以在控制面板右上方直接搜索就出来了)
2、存储一栏,选中“允许站点在此计算机上保存信息 ”
3、在摄像头和麦克风一栏,点击进入“站点的摄像头和麦克风设置管理界面”,将需要访问摄像头的网站的https访问模式和其他模式都设置为允许
4、保存,重新打开页面就可以了。
问题3: 如何让Chrome浏览器允许http网站打开摄像头和麦克风
navigator.mediaDevices调用摄像头,在谷歌浏览器本地运行正常,发布到线上运行却提示Uncaught TypeError: Cannot read property 'getUserMedia' of undefined 这个错误,经过查阅资料才知道这和浏览器的安全策略有关,出于安全考虑,浏览器是不允许随便开启摄像头的,只有在https协议下方可开启。
解决办法,需要配置浏览器,允许访问才可以
谷歌浏览器打开 chrome://flags/#unsafely-treat-insecure-origin-as-secure
设置完浏览器底部会有Relaunch按钮,点击重新启动浏览器(一定要记得重新启动浏览器),就可以实现http协议下正常启动摄像头了(前提摄像头是允许模式下)
创作不易,且看且珍惜,有问题留言讨论