You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Colab运行YOLOv4代码时无法打开摄像头的问题求助

解决Colab中调用本地摄像头进行YOLOv4裁剪保存的问题

原因说明

Colab运行在云端服务器上,无法直接访问你本地电脑的摄像头设备(/dev/video0),所以用--video 0会触发设备找不到的报错。

解决步骤

1. 在Colab中获取本地摄像头权限并捕获内容

新建代码单元格,运行以下代码调用本地摄像头,授权后可捕获单张图片或扩展为视频流:

from IPython.display import display, Javascript
from google.colab.output import eval_js
from base64 import b64decode
import cv2
import numpy as np

# 捕获单张图片
def take_photo(filename='photo.jpg', quality=0.8):
  js = Javascript('''
    async function takePhoto(quality) {
      const div = document.createElement('div');
      const capture = document.createElement('button');
      capture.textContent = 'Capture';
      div.appendChild(capture);

      const video = document.createElement('video');
      video.style.display = 'block';
      const stream = await navigator.mediaDevices.getUserMedia({video: true});

      document.body.appendChild(div);
      div.appendChild(video);
      video.srcObject = stream;
      await video.play();

      google.colab.output.setIframeHeight(document.documentElement.scrollHeight, true);
      await new Promise((resolve) => capture.onclick = resolve);

      const canvas = document.createElement('canvas');
      canvas.width = video.videoWidth;
      canvas.height = video.videoHeight;
      canvas.getContext('2d').drawImage(video, 0, 0);
      stream.getVideoTracks()[0].stop();
      div.remove();
      return canvas.toDataURL('image/jpeg', quality);
    }
    ''')
  display(js)
  data = eval_js('takePhoto({})'.format(quality))
  binary = b64decode(data.split(',')[1])
  with open(filename, 'wb') as f:
    f.write(binary)
  return filename

# 可选:捕获短视频(10帧)保存为avi
def capture_short_video(filename='input_video.avi', duration_frames=10):
  js = Javascript('''
    async function getVideoStream() {
      const video = document.createElement('video');
      video.style.display = 'block';
      const stream = await navigator.mediaDevices.getUserMedia({video: true});
      video.srcObject = stream;
      await video.play();
      google.colab.output.setIframeHeight(document.documentElement.scrollHeight, true);
      return {
        video: video,
        stream: stream
      };
    }
    async function captureFrame(video) {
      const canvas = document.createElement('canvas');
      canvas.width = video.videoWidth;
      canvas.height = video.videoHeight;
      canvas.getContext('2d').drawImage(video, 0, 0);
      return canvas.toDataURL('image/jpeg', 0.8);
    }
    ''')
  display(js)
  stream_obj = eval_js('getVideoStream()')
  
  # 初始化视频写入器
  frame_width = eval_js('stream_obj.video.videoWidth')
  frame_height = eval_js('stream_obj.video.videoHeight')
  fourcc = cv2.VideoWriter_fourcc(*'XVID')
  out = cv2.VideoWriter(filename, fourcc, 10.0, (frame_width, frame_height))

  # 捕获指定帧数
  for _ in range(duration_frames):
    data = eval_js('captureFrame(stream_obj.video)')
    binary = b64decode(data.split(',')[1])
    np_arr = np.frombuffer(binary, np.uint8)
    frame = cv2.imdecode(np_arr, cv2.IMREAD_COLOR)
    out.write(frame)
  
  # 停止流并释放资源
  eval_js('stream_obj.stream.getVideoTracks()[0].stop()')
  out.release()
  return filename

运行后按提示授权摄像头,执行take_photo()可获取单张图片,执行capture_short_video()可获取临时视频文件。

2. 修改YOLOv4调用命令

  • 处理单张图片:用detect.py替代detect_video.py,命令如下:
!python detect.py --weights ./checkpoints/yolov4-416 --size 416 --model yolov4 --image ./photo.jpg --crop
  • 处理视频:先通过上述函数生成input_video.avi,再运行:
!python detect_video.py --weights ./checkpoints/yolov4-416 --size 416 --model yolov4 --video ./input_video.avi --output ./detections/results2.avi --crop

3. 查看裁剪结果

处理完成后,可通过Colab左侧文件管理器查看./detections/crop目录下的裁剪图片,也用以下代码直接显示:

from PIL import Image
import matplotlib.pyplot as plt

# 替换为实际裁剪图片文件名
img = Image.open('./detections/crop/person_0.jpg')
plt.imshow(img)
plt.axis('off')
plt.show()

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.22 02:45:35