调用摄像头+切换+截图
<template> <div> <div class="video-list"> <div class="video-container" v-for="(item, index) in cameraList" :key="index"> <div class="videoBoxError" v-if="!isCamera"> <img src="@/assets/images/exam/icon_sxtyc.png" > <p>摄像头调用异常,请按说明调试设备</p> </div> <video :id="'video' + index" v-if="isCamera"></video> </div> </div> <div v-if="showBtn"> <el-button style="margin-bottom: 10px;" v-for="(item, index) in cameraList" :key="index">{{'摄像头'+(index+1)}}</el-button> </div> <canvas id="canvas" style="display: none;width:250px;height:250px"></canvas> </div> </template> <script> export default { name: 'videoSetting', props: { value: { type: Number, default: () => 99999 }, width: { type: Number, default: () => 0 }, height: { type: Number, default: () => 0 }, showBtn: { type: Boolean, default: () => true } }, data() { return { cameraList: [], isCamera: false } }, watch: { value: { handler() { this.getDevices().then(() => { this.main() }) } } }, created() { this.getDevices().then(() => { this.main() }) }, beforeDestroy() { //this.close(); }, methods: { main () { this.cameraList.forEach((camera, index) => { let domId = `video${index}`; let video = document.getElementById(domId) this.enableCamera(camera.id, video) }) }, enableCamera (deviceId, video) { this.getUserMedia(this.setConstraints(deviceId), (stream) => { video.srcObject = stream; video.onloadedmetadata = (e) => { video.play(); this.isCamera = true; } }, error => { this.isCamera = false; console.log(`访问用户媒体设备失败${error.name}, ${error.message}`) }) }, getDevices () { return new Promise((resolve, reject) => { if (!navigator.mediaDevices || !navigator.mediaDevices.enumerateDevices) { this.isCamera = false; window.alert("不支持 mediaDevices.enumerateDevices()") } navigator.mediaDevices.enumerateDevices().then(devices => { console.log(devices) this.isCamera = true; this.cameraList = [] devices.forEach((device, index) => { if (device.kind && device.kind === 'videoinput') { if(this.cameraList.length < this.value){ this.cameraList.push({ id: device.deviceId, label: device.label }) } } }) resolve() }).catch((err) => { this.isCamera = false; console.log(err.name + ": " + err.message) reject() }) }) }, getUserMedia (constraints, success, error) { if (navigator.mediaDevices.getUserMedia) { //最新的标准API navigator.mediaDevices.getUserMedia(constraints).then(success).catch(error) } else if (navigator.webkitGetUserMedia) { //webkit核心浏览器 navigator.webkitGetUserMedia(constraints, success, error) } else if (navigator.mozGetUserMedia) { //firfox浏览器 navigator.mozGetUserMedia(constraints, success, error) } else if (navigator.getUserMedia) { //旧版API navigator.getUserMedia(constraints, success, error) } }, /** @desc 摄像头配置项通用配置 */ setConstraints (deviceId) { return { audio: false, video: { width: this.width, height: this.height, deviceId: deviceId } } }, takePhoto () { //let videoId = `video${idx}`; let videoId = 'video0'; let videoDom = document.getElementById(videoId); // 使用canvas进行拍照 let canvas = document.getElementById('canvas'); let ctx = canvas.getContext('2d'); ctx.drawImage(videoDom, 0,0,250, 250); return canvas.toDataURL("image/png"); }, close: function () { this.cameraList.forEach((camera, index) => { let domId = `video${index}`; let video = document.getElementById(domId); //关闭摄像头 video.srcObject.getTracks()[0].stop(); }) console.log("摄像头已关闭") }, closeRouter: function () { return new Promise((resolve, reject) => { if(this.isCamera){ this.cameraList.forEach((camera, index) => { let domId = `video${index}`; let video = document.getElementById(domId); //关闭摄像头 video.srcObject.getTracks()[0].stop(); }) console.log("摄像头已关闭"); resolve(); }else{ resolve(); } }) } } } </script> <style scoped> .videoBoxError{ width: 600px; height: 350px; background: #3f4043; margin-left: 30px; margin-bottom: 10px; } .videoBoxError img{ width: 60px; margin-top: 90px; } .videoBoxError p{ color: #5f6063; font-size: 16px; margin-top: 15px; } </style>