用两个相机捕获(OpenCV,Python)

5 投票
3 回答
17930 浏览
提问于 2025-04-17 09:07

我正在尝试在OpenCV中同时从两台摄像头捕捉画面(使用Python和Windows 7)。我从一台摄像头捕捉得很好,你会注意到我对图像做了一些奇怪的处理,但这不重要。下面是我尝试使用两台摄像头的代码:

import cv
import time
cv.NamedWindow("camera", 1)
cv.NamedWindow("camera2", 1)
capture = cv.CaptureFromCAM(0)
capture2 = cv.CaptureFromCAM(1)
while True:
    img = cv.GetMat(cv.QueryFrame(capture))
    img2 = cv.GetMat(cv.QueryFrame(capture2))
    dst_image = cv.CloneMat(img)
    dst_image2 = cv.CloneMat(img2)
    cv.ConvertScale(img, dst_image, 255, -59745.0)
    cv.ConvertScale(img2, dst_image2, 255, -59745.0)
    cv.ShowImage("camera", dst_image)
    cv.ShowImage("camera2", dst_image2)
    if cv.WaitKey(10) == 27:
        cv.DestroyWindow("camera")
        cv.DestroyWindow("camera2")
        break

代码其实很简单。不过它并不奏效。当我尝试从第二台摄像头创建画面时(循环中的第二行代码),系统告诉我捕捉到的画面是空的。我使用的摄像头是罗技的,而且是同一型号。

顺便说一下,我也找不到在Python中统计连接的摄像头数量的命令,如果有人能告诉我该怎么做,我会非常感激。 --Ashley

补充说明: 可能还需要知道的是,Windows经常会提示我选择想要使用的摄像头。我似乎无法避免这种情况。此外,我下载了一些安全类软件,可以成功同时运行两台摄像头。那不是开源软件。所以显然,这是可行的。

3 个回答

0

如果你在Windows上编程,为什么不试试VideoCapture模块呢?这个模块非常简单好用,输出的结果是一个PIL格式的图片。你之后还可以把它转换成一个二维数组。

2

这里有一段简单的代码:

import VideoCapture
cam0 = VideoCapture.Device(0)
cam1 = VideoCapture.Device(1)
im0 = cam0.getImage()
im1 = cam1.getImage()

im0 和 im1 是用 PIL 库处理的图片。你现在可以使用 scipy 库把它们转换成数组,方法如下:

import scipy as sp
imarray0 = asarray(im0)
imarray1 = asarray(im1)

imarray0 和 imarray1 是 numpy 的二维数组,你可以进一步用 openCV 的函数来处理这些数组。

4

我之前也遇到过两个Lifecam Studio网络摄像头的问题。经过一些研究,我觉得这个问题可能是因为USB总线的带宽超载了。只要我做了以下两件事,两个摄像头就都能正常工作:1.) 降低分辨率(每个摄像头设置为320 x 240),或者2.) 降低帧率(在800 x 600的情况下大约99毫秒)。下面是让我成功运行的代码:

import cv

cv.NamedWindow("Camera 1")
cv.NamedWindow("Camera 2")
video1 = cv.CaptureFromCAM(0)
cv.SetCaptureProperty(video1, cv.CV_CAP_PROP_FRAME_WIDTH, 800)
cv.SetCaptureProperty(video1, cv.CV_CAP_PROP_FRAME_HEIGHT, 600)

video2 = cv.CaptureFromCAM(1)
cv.SetCaptureProperty(video2, cv.CV_CAP_PROP_FRAME_WIDTH, 800)
cv.SetCaptureProperty(video2, cv.CV_CAP_PROP_FRAME_HEIGHT, 600)

loop = True
while(loop == True):
    frame1 = cv.QueryFrame(video1)
    frame2 = cv.QueryFrame(video2)
    cv.ShowImage("Camera 1", frame1)
    cv.ShowImage("Camera 2", frame2)
    char = cv.WaitKey(99)
    if (char == 27):
        loop = False

cv.DestroyWindow("Camera 1")
cv.DestroyWindow("Camera 2")

撰写回答