一定部署到https域名上,否则无法调用摄像头权限!!!

效果图

定义Data

 data () {return {dialogTableVisible:false,videoWidth: 500,videoHeight: 400,imgSrc: '',thisCancas: null,thisContext: null,thisVideo: null,ImgFile:'',//返回的图片文件}},
调用摄像头权限
getCompetence () {this.$nextTick(function () {var _this = this;this.thisCancas = document.getElementById('canvasCamera');this.thisContext = this.thisCancas.getContext('2d');this.thisVideo = document.getElementById('videoCamera');// 旧版本浏览器可能根本不支持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 || navigator.getUserMedia;// 有些浏览器不支持,会返回错误信息// 保持接口一致if (!getUserMedia) {return Promise.reject(new Error('getUserMedia is not implemented in this browser'))}// 否则,使用Promise将调用包装到旧的navigator.getUserMediareturn new Promise(function (resolve, reject) {getUserMedia.call(navigator, constraints, resolve, reject)})}}var constraints = { audio: false, video: { width: this.videoWidth, height: this.videoHeight, transform: 'scaleX(-1)' } };navigator.mediaDevices.getUserMedia(constraints).then(function (stream) {// 旧的浏览器可能没有srcObjectif ('srcObject' in _this.thisVideo) {_this.thisVideo.srcObject = stream} else {// 避免在新的浏览器中使用它,因为它正在被弃用。_this.thisVideo.src = window.URL.createObjectURL(stream)}_this.thisVideo.onloadedmetadata = function (e) {_this.thisVideo.play()}}).catch(err => {console.log(err)})});},

绘制图片,生成一个base64文件

setImage(){var _this = this;// 点击,canvas画图_this.thisContext.drawImage(_this.thisVideo, 0, 0, _this.videoWidth, _this.videoHeight);// 获取图片base64链接var image = this.thisCancas.toDataURL('image/png');_this.imgSrc = image;},

base64文件转文件流

dataURLtoFile (dataurl, filename) {var arr = dataurl.split(',');var mime = arr[0].match(/:(.*?);/)[1];var bstr = atob(arr[1]);var n = bstr.length;var u8arr = new Uint8Array(n);while (n--) {u8arr[n] = bstr.charCodeAt(n)}return new File([u8arr], filename, { type: mime })},

上传文件流至后台(form提交)

handleUpdata(){//已form提交if (this.imgSrc!==''){let file = this.imgSrc; // 把整个base64给filelet type = "image/jpeg"; // 定义图片类型(canvas转的图片一般都是png,也可以指定其他类型)let time=(new Date()).valueOf();//生成时间戳let name = time + ".jpg"; // 定义文件名字(例如:abc.png , cover.png)let conversions = this.dataURLtoFile(file, name); // 调用base64转图片方法let parms=new FormData();parms.append('file',conversions);let url='*********';//你的接口this.axios.post(url,parms,{headers: {'Content-Type': 'multipart/form-data'}}).then(res=>{console.log(res);this.ImgFile=res.data;}).catch(err=>{this.$notify.error({title: '上传失败',message: err.msg});})}},

关闭摄像头

stopNavigator () {this.thisVideo.srcObject.getTracks()[0].stop()},
 

离开页面时关闭摄像头

 beforeDestroy () {this.stopNavigator()}

附上源码:

<template><div><el-button@click="onTake"icon="el-icon-camera"size="small">拍照上传</el-button><el-dialogtitle="拍照上传":visible.sync="visible"@close="onCancel"width="1065px"><div class="box"><video id="videoCamera" class="canvas" :width="videoWidth" :height="videoHeight" autoPlay></video><canvas id="canvasCamera" class="canvas" :width="videoWidth" :height="videoHeight"></canvas></div><div slot="footer"><el-button@click="drawImage"icon="el-icon-camera"size="small">拍照</el-button><el-buttonv-if="open"@click="getCompetence"icon="el-icon-video-camera"size="small">打开摄像头</el-button><el-buttonv-else@click="stopNavigator"icon="el-icon-switch-button"size="small">关闭摄像头</el-button><el-button@click="resetCanvas"icon="el-icon-refresh"size="small">重置</el-button><el-button@click="onCancel"icon="el-icon-circle-close"size="small">取消</el-button><el-button@click="onUpload":loading="loading"type="primary"icon="el-icon-upload2"size="small">上传</el-button></div></el-dialog></div>
</template><script>//拍照上传组件//父组件通过函数 getImg 获取照片路径,如 @getImg="getImg"const Address = require('../utils/url');//图片上传地址export default {name: "TakePhotos",data() {return {imgSrc: "",visible: false,//弹窗loading: false,//上传按钮加载open: false,//控制摄像头开关thisVideo: null,thisContext: null,thisCancas: null,videoWidth: 500,videoHeight: 400}},methods: {onTake() {this.visible = true;this.getCompetence();},onCancel() {this.visible = false;this.resetCanvas();this.stopNavigator();},//base64转成文件后上传onUpload() {if (this.imgSrc) {const file = this.imgSrc; // 把整个base64给fileconst time = (new Date()).valueOf();//生成时间戳const name = time + ".png"; // 定义文件名字(例如:abc.png , cover.png)const conversions = this.dataURLtoFile(file, name); // 调用base64转图片方法const data = new FormData();data.append('file', conversions);const options = {method: "POST",   //请求方法body: data,   //请求体headers: {'Accept': 'application/json'},};this.loading = true;fetch(Address.UPLOAD, options).then((response) => {return response.json();}).then((responseText) => {this.loading = false;if (responseText.code === 0) {this.imgSrc = responseText.data.src;this.$emit('getImg', responseText.data.src);//传递给父组件this.onCancel();this.$notify({title: '上传成功',message: responseText.msg,type: 'success'});}}).catch((error) => {this.loading = false;this.$notify.error({title: '上传失败',message: error.msg,});})}else {this.$notify({title: '警告',message: '请点击拍照',type: 'warning'});}},// 调用摄像头权限getCompetence() {//必须在model中render后才可获取到dom节点,直接获取无法获取到model中的dom节点this.$nextTick(() => {const _this = this;this.open = false;//切换成关闭摄像头this.thisCancas = document.getElementById('canvasCamera');this.thisContext = this.thisCancas.getContext('2d');this.thisVideo = document.getElementById('videoCamera');// 旧版本浏览器可能根本不支持mediaDevices,我们首先设置一个空对象if (navigator.mediaDevices === undefined) {navigator.mediaDevices = {}}// 一些浏览器实现了部分mediaDevices,我们不能只分配一个对象// 使用getUserMedia,因为它会覆盖现有的属性。// 这里,如果缺少getUserMedia属性,就添加它。if (navigator.mediaDevices.getUserMedia === undefined) {navigator.mediaDevices.getUserMedia = function (constraints) {// 首先获取现存的getUserMedia(如果存在)let getUserMedia = navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.getUserMedia;// 有些浏览器不支持,会返回错误信息// 保持接口一致if (!getUserMedia) {return Promise.reject(new Error('getUserMedia is not implemented in this browser'))}// 否则,使用Promise将调用包装到旧的navigator.getUserMediareturn new Promise(function (resolve, reject) {getUserMedia.call(navigator, constraints, resolve, reject)})}}const constraints = {audio: false,video: {width: _this.videoWidth, height: _this.videoHeight, transform: 'scaleX(-1)'}};navigator.mediaDevices.getUserMedia(constraints).then(function (stream) {// 旧的浏览器可能没有srcObjectif ('srcObject' in _this.thisVideo) {_this.thisVideo.srcObject = stream} else {// 避免在新的浏览器中使用它,因为它正在被弃用。_this.thisVideo.src = window.URL.createObjectURL(stream)}_this.thisVideo.onloadedmetadata = function (e) {_this.thisVideo.play()}}).catch(err => {this.$notify({title: '警告',message: '没有开启摄像头权限或浏览器版本不兼容.',type: 'warning'});});});},//绘制图片drawImage() {// 点击,canvas画图this.thisContext.drawImage(this.thisVideo, 0, 0, this.videoWidth, this.videoHeight);// 获取图片base64链接this.imgSrc = this.thisCancas.toDataURL('image/png');},//base64转文件dataURLtoFile(dataurl, filename) {let arr = dataurl.split(',');let mime = arr[0].match(/:(.*?);/)[1];let bstr = atob(arr[1]);let n = bstr.length;let u8arr = new Uint8Array(n);while (n--) {u8arr[n] = bstr.charCodeAt(n)}return new File([u8arr], filename, {type: mime})},//清空画布clearCanvas(id) {let c = document.getElementById(id);let cxt = c.getContext("2d");cxt.clearRect(0, 0, c.width, c.height);},//重置画布resetCanvas() {this.imgSrc = "";this.clearCanvas('canvasCamera');},//关闭摄像头stopNavigator() {if (this.thisVideo && this.thisVideo !== null) {this.thisVideo.srcObject.getTracks()[0].stop();this.open = true;//切换成打开摄像头}},},beforeDestroy() {this.stopNavigator()}}
</script><style scoped>.box {display: flex;justify-content: space-between;}.canvas {border: 1px solid #e8e8e8;}
</style>

vue+elementUI实现调用PC摄像头拍照上传图片(谷歌火狐测试可用,其他自测)相关推荐

  1. Vue 调用PC摄像头拍照

    项目需求:可以本地上传头像,也可以选择拍摄头像上传. 组件: Camera组件:实现 打开.关闭摄像头.绘制.显示图片.用于上传 CameraDialog组件:使用ElementUI dialog组件 ...

  2. vue+springboot实现调用本地摄像头拍照上传后端使用百度ocr识别身份证信息

    提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档 文章目录 一.前端 二.后端 总结 提示:以下是本篇文章正文内容,下面案例可供参考 一.前端 1.首先进入页面打开摄像头 2.点击手动 ...

  3. php h5 调用摄像头_利用html5调用本地摄像头拍照上传图片

    [php]代码库html5概念啥的就不废话了,不知道的 百度, 谷歌一堆..今天学了学html5中的Canvas结合新增的标签来获取本地摄像头,在html5之前,要在浏览器获取本地摄像头只有通过插件( ...

  4. js调用pc摄像头实现拍照、录视频等,新版Chrome无访问http页面无法打开麦克风、摄像头

    js调用pc摄像头实现拍照.录视频等,新版Chrome无访问http页面无法打开麦克风.摄像头 新版Chrome配置 vue环境下的前端 function部分 ##由于没有https环境,只有http ...

  5. 在微信小程序中 调用前置摄像头拍照 后置摄像头拍照扫码

    1.需求:点击扫码按钮,扫描二维码识别单号    实现:  <view class="getcode" bindtap="scanCode"> &l ...

  6. html 调用pc摄像头,HTML调用PC摄像头

    使用HTML5中的canvas和video技术实现调用PC摄像头 1.[代码][HTML]代码 HTML5调用电脑摄像头实例 window.addEventListener("DOMCont ...

  7. HTML调用PC摄像头【申明:来源于网络】

    HTML调用PC摄像头[申明:来源于网络] ---- 地址:http://www.oschina.net/code/snippet_2440934_55195 <!DOCTYPE html> ...

  8. H5调用手机摄像头拍照,如何压缩后上传

    H5调用手机摄像头拍照后,怎样压缩再上传? 实际的压缩功能,就是利用canvas画布功能,将图片进行裁剪后保存图片的base64数据流,然后上传. 案例全部代码,示下: <!DOCTYPE ht ...

  9. JS调用本地摄像头拍照(兼容各大浏览器及IE8+)

    最近做的项目遇到了个难题,使用video+canvas+getUserMedia()写的调用本地摄像头拍照不兼容IE. 原因:IE8及以下不支持HTML5标签:video和canvas:IE11及以下 ...

最新文章

  1. 一款直击痛点的优秀http框架,让我超高效率完成了和第三方接口的对接
  2. php百度自动推送代码,怎么设置百度自动推送代码安装教程-百度自动推送好处解析...
  3. springboot+druid+mybatis-Plus 配置详解
  4. 快速编辑 Shell 命令行
  5. 从JDK 12删除原始字符串文字
  6. 云服务器搭建虚拟主机教程,云服务器搭建虚拟主机教程
  7. 男女洗澡前后区别,太形象了!(文末送书)
  8. 怎样对计算机窗口进行截图,Windows10:如何对计算机屏幕上的内容进行屏幕截图...
  9. BIM族库下载——Revit配景族
  10. Blender的一些使用小结,在辣椒酱基础上加了点,会持续更新
  11. Oracle开发专题之:OLAP 函数 (rows 2 preceding / unbounded preceding)
  12. 试喷一下今年的国家最高科学技术奖
  13. 上古卷轴5:重制版Skyrim Together用MO无法替换游戏菜单Menu图像LOGO的问题解决
  14. 战斗在 VUCA 时代
  15. 2022.11.11 英语背诵
  16. 蓝牙音箱电路板原理图_一文看懂音响电路图及工作原理
  17. 取消耳机孔的 4 年后,苹果居然把耳机卖到了四千块
  18. mysql 1067_mysql启动错误1067进程意外终止的解决方法
  19. 计算机网络主机访问网址(建立HTTP)过程
  20. 破解 expression blend 3 + sketchflow 注册码

热门文章

  1. 一分钟解决HbuilderX运行到微信开发者工具时报错提示:fail to open IDE
  2. 如何制作引人注目的PPT幻灯片
  3. JS特性检测,检测元素上是否有指定属性或当前浏览器是否支持某元素或某属性
  4. 使用JavaScript制作动态网页
  5. 计算机系统结构——非线性流水线调度
  6. B端产品经理与C端产品经理
  7. RestTemplate上传图片
  8. 有关ARM RTC时钟使用心得
  9. HDU 4741 Save Labman No.004(计算几何)
  10. 若依ruoyiAOP切面用于数据过滤和权限处理实例