vue2项目 H5页面调用摄像头拍照

直接上代码:

<template>
  <div>
    <button @click="openCamera">打开摄像头</button>
    <button @click="takePhoto">拍照</button>
    <video ref="video" width="640" height="480"></video>
    <canvas ref="canvas" width="640" height="480" style="display: none;"></canvas>
    <img :src="photoDataUrl" alt="拍照的图片">
  </div>
</template>
export default {
  data() {
    return {
      //拍的照片存储的容器
      photoDataUrl: '',
      stream: null,
      videoElement: null,
      canvasElement: null,
    };
  },
  mounted() {
    //通过 ref 获取到的 video 元素赋值给组件实例的 videoElement 属性
    this.videoElement = this.$refs.video;
    //通过 ref 获取到的 canvas 元素赋值给组件实例的 canvasElement 属性
    this.canvasElement = this.$refs.canvas;
  },
  methods: {
    openCamera() {
        /* 
        调用了 navigator.mediaDevices.getUserMedia 方法
        该方法请求用户授权访问本地设备(例如摄像头、麦克风等) 并返回一个 Promise 对象。
        调用该方法时,代码传入一个配置对象,指定要访问的设备类型
        例如 { video: true } 表示要获取视频流。调用 then 方法来处理成功的情况
        */
      navigator.mediaDevices.getUserMedia({ video: true })
        .then((stream) => {
          //将视频流赋值给 Vue 实例的 stream 属性
          this.stream = stream;
          //视频流绑定到 HTML5 的 video 元素上,使用 srcObject 属性来实现,并调用 play 方法播放视频
          this.videoElement.srcObject = stream;
          this.videoElement.play();
          //通过以上的这样的操作,即可实现摄像头视频流的捕获和展示。
        })
        .catch((error) => {
          console.error('打开摄像头失败:', error);
        });
    },
    takePhoto() {
      //首先获取了 Canvas 元素的上下文对象 context:
      const context = this.canvasElement.getContext('2d');
      //通过 context.drawImage 方法将视频元素中当前帧的图像绘制到 Canvas 中:
      /* 
          this.videoElement 表示视频元素
          0 和 0 表示图像在 Canvas 中的起始坐标
          this.canvasElement.width 和 this.canvasElement.height 表示图像在 Canvas 中的宽度和高度。
          这一步是实现了将当前摄像头所捕获的图像绘制到 Canvas 中,以便后续可以处理图像。
      */
      context.drawImage(this.videoElement, 0, 0, this.canvasElement.width, this.canvasElement.height);

      // 将拍照的图片转换为base64格式
      this.photoDataUrl = this.canvasElement.toDataURL('image/jpeg');

      // 调用 getTracks() 方法遍历摄像头视频流的所有轨道,并逐一停止它们,这样就关闭了摄像头:
      this.stream.getTracks().forEach((track) => {
        track.stop();
      });

      // 发送照片数据给后台
      this.uploadPhoto(this.photoDataUrl);
    },
    uploadPhoto(photoDataUrl) {
      // 将照片数据上传给后台
      axios.post('/upload', { photo: photoDataUrl })
        .then((response) => {
          console.log('照片上传成功');
        })
        .catch((error) => {
          console.error('照片上传失败:', error);
        });
    },
  },
};

猜你喜欢

转载自blog.csdn.net/weixin_53322542/article/details/134403649