从多个USB摄像头捕获帧 - OpenCV,C ++

时间:2014-07-17 00:38:28

标签: c++ opencv vector camera usb

我试图从连接到USB集线器的几个USB摄像头捕获单个帧。我写了一些我认为应该有用的东西,但它没有:(。最终结果根据参数生成正确数量的图像,但除了最终结果之外的所有图像都是"空白&#34 ;

#include <opencv2/highgui/highgui.hpp>

#include <stdio.h>
#include <iostream>
using namespace cv;


int main(int argc, char** argv){

  int numberOfCameras = atoi(argv[1]);
  std::vector<Mat> frames (numberOfCameras-1);

  for(int i=0; i<numberOfCameras; i++){
    VideoCapture cap(i);
    cap.set(CV_CAP_PROP_FRAME_WIDTH,320);
    cap.set(CV_CAP_PROP_FRAME_HEIGHT,240);
    Mat frame; cap >> frame;

    frames.push_back(frame);
  }

  for(int i=0; i<numberOfCameras; i++){
    string fileName = std::to_string(i) + ".jpg";
    std::cout << fileName << std::endl;
    imwrite(fileName, frames[i]);
  }
}

这里发生了什么?我对C ++和类型语言都很陌生。我误解了矢量的使用吗?以上是完成任务的最佳方法吗?

我将连接几台摄像机(总共50台),并对于在内存中存储50帧的影响感到好奇。我甚至可以在那么多相机上打开电话捕捉吗?

3 个答案:

答案 0 :(得分:4)

来自网络摄像头的帧是特殊的,因为它们指向视频捕捉/驱动程序内的(静态)内存。

因为您在循环中创建并销毁了VideoCapture,所以存储在向量中的帧将无效(它们指向的内存已消失)

为了使您的计划有效,您需要在存储之前克隆()框架(因此它保留了自己的像素副本)

frames.push_back(frame.clone()); 

答案 1 :(得分:2)

很可能你受到硬件的限制。 USB摄像头有可能从USB总线获取尽可能多的带宽,因此使用USB集线器连接多个可能不是一个好主意。

首先尝试仅连接两个摄像头,然后暂时将设备从设备中取出。如果你很幸运,你的系统有两个独立的USB总线,你可以通过尝试以各种可能的方式连接摄像机电缆找到它们。检查您的主板/笔记本电脑手册,看它是否有单独的总线。您还可以找到适用于您的操作系统的教程,了解如何查看它们是否存在于系统中。

如果你有两辆公共汽车但仍然无法从两个摄像头获取图像,则问题可能在你的代码中。您可以在此SO post

中阅读更多内容

答案 2 :(得分:2)

在我正在做的一个项目中,我曾尝试同时使用四个USB摄像头,但它没有用。

我只设法同时连接两台摄像机。

您基本上有两个选择:

1-玩杂耍相机,即捕获一个相机,读取一帧,然后将其释放并移动到下一个相机....

2-始终抓住一台摄像机(对您来说最重要的摄像机)并按照(1)中的规定处理剩下的摄像机。

虽然,您可以尝试将外部电源连接到USB集线器,这可能会帮助您同时捕获三个摄像头,但我非常怀疑您将能够使用OpenCV捕获四个以上的摄像头,无论什么

我尝试用不同的相机,不同的(单独的)USB端口和不同的USB集线器来做到这一点。我可以获得的最大值是四个不同的摄像头,每个摄像头都连接到不同的USB端口,并且它并不总是有效。

注意事项:功耗,带宽和OpenCV自身的局限性。

BTW:我在配备4GB内存的Intel i5笔记本电脑上使用OpenCV 2.4.8和Windows 7 64位。