You need to enable JavaScript to run this app. Vue.js项目中如何从摄像头流逐帧提取画面并通过WebSocket发送
优惠活动
大模型
产品
解决方案
定价
更多

Vue.js项目中如何从摄像头流逐帧提取画面并通过WebSocket发送

Vue.js实现摄像头实时逐帧提取与WebSocket传输方案

实现核心逻辑

原生HTML中用document.getElementById获取视频元素的操作,在Vue中替换为ref绑定获取DOM/组件实例即可,原有帧提取的Canvas绘制逻辑可以完全复用,不受框架影响。

具体实现步骤

  1. 给video-js-record组件绑定ref
    修改模板中的组件代码,添加ref属性用于后续获取组件内的视频实例:
<video-js-record
  ref="videoRecorder"
  @recordingStarted="onVideoRecording"
  @recordingEnded="onRecordingEnded"
></video-js-record>
  1. 扩展data变量存储采集状态
    在现有data中新增两个变量,用于控制采集定时任务和存储Canvas实例:
data() {
  return {
    // 原有变量保持不变
    countDown: 10,
    showVideo: false,
    timeShow: false,
    // 新增帧采集相关变量
    frameCaptureTimer: null,
    captureCanvas: null
  }
}
  1. 实现帧采集与发送方法
    在methods中新增两个方法,负责逐帧提取和WebSocket发送:
// 启动帧采集
startFrameCapture() {
  // 从videoJsRecord组件中获取原生video元素,根据你的组件实际暴露的实例调整属性名
  const videoElement = this.$refs.videoRecorder.$el.querySelector('video')
  // 初始化Canvas
  this.captureCanvas = document.createElement('canvas')
  this.captureCanvas.width = videoElement.videoWidth
  this.captureCanvas.height = videoElement.videoHeight
  const ctx = this.captureCanvas.getContext('2d')
  
  // 按自定义间隔采集,不受页面渲染帧率限制,调整间隔数值可控制采集帧率
  // 例:30帧/秒对应间隔约33ms,60帧/秒对应间隔约16ms
  this.frameCaptureTimer = setInterval(() => {
    // 绘制当前视频帧到Canvas
    ctx.drawImage(videoElement, 0, 0, this.captureCanvas.width, this.captureCanvas.height)
    // 转成Blob二进制数据发送(比base64性能更好、带宽占用更低)
    this.captureCanvas.toBlob((blob) => {
      // 通过WebSocket发送帧数据
      this.$socket.emit('videoFrame', {
        segmentId: this.dataSegmentId,
        frame: blob,
        timestamp: Date.now()
      })
    }, 'image/jpeg', 0.8) // 可调整图片格式和质量参数
  }, 33)
},

// 停止帧采集
stopFrameCapture() {
  if (this.frameCaptureTimer) {
    clearInterval(this.frameCaptureTimer)
    this.frameCaptureTimer = null
  }
  this.captureCanvas = null
}
  1. 关联录制生命周期回调
    在现有的录制开始、结束回调中调用对应的采集控制方法:
onVideoRecording() {
  this.timeShow = true
  this.showVideo = false
  this.countDownTimer()
  // 启动帧采集
  this.startFrameCapture()
},

async onRecordingEnded(player) {
  // 停止帧采集
  this.stopFrameCapture()
  // 原有逻辑保持不变
  this.showVideo = true
  this.timeShow = false
  this.countDown = 10
  // ... 原有视频上传逻辑
}

注意事项

  • 若你的videoJsRecord组件已经暴露了原生video实例,可直接通过实例属性获取,不需要手动querySelector查询
  • 可根据业务需求调整采集间隔、图片格式、压缩质量参数,平衡传输带宽和画面清晰度
  • 发送大体积帧数据时建议开启WebSocket二进制传输模式,进一步降低传输开销

内容的提问来源于stack exchange,提问作者Aimen Wajahat

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.12 19:15:03