Capturing grey screen from camera using OpenCV
I have a problem with capturing image from my web cam (built in hp dv5). The only result is grey screen. Here's the code:
#include "StdAfx.h"
#include "cv.h"
#i开发者_运维百科nclude "highgui.h"
#include <stdio.h> // A Simple Camera Capture Framework
int main() {
CvCapture* capture;
for (int i = -1;i < 100;i++) {
capture = cvCaptureFromCAM( i );
if( !capture ) {
fprintf( stderr, "ERROR: capture is NULL \n" );
} else {
break;
}
}
//cvSetCaptureProperty( capture, CV_CAP_PROP_FPS,15);
//cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_WIDTH, 160 );
//cvSetCaptureProperty( capture, CV_CAP_PROP_FRAME_HEIGHT, 120 );
// Create a window in which the captured images will be presented
cvNamedWindow( "mywindow", CV_WINDOW_AUTOSIZE ); // Show the image captured from the camera in the window and repeat
while( 1 ) { // Get one frame
IplImage* frame = cvQueryFrame( capture );
cvGrabFrame(capture);
frame = cvRetrieveFrame(capture);
if( !frame ) {
fprintf( stderr, "ERROR: frame is null...\n" );
getchar();
break;
} else {
fprintf( stderr, "OK\n" );
}
cvShowImage( "mywindow", frame ); // Do not release the frame!
//If ESC key pressed, Key=0x10001B under OpenCV 0.9.7(linux version), //remove higher bits using AND operator
int c = cvWaitKey(100);
} // Release the capture device housekeeping
cvReleaseCapture( &capture );
cvDestroyWindow( "mywindow" );
return 0;
}
It's modified code from OpenCV's wiki. I know that finding the camera in this way its crazy but it didn't work with -1 or 0. I added some additional properties (commented already) but it didn't work anyway. Thanks in advance :) Greetings, Chris
I encapsulate the image capturing into a class 'Capture', maybe you could give it a try. Below are main.cpp, capture.h and capture.cpp, enjoy it :)
main.cpp
#include "capture.h"
#include <string>
using namespace std;
int main(int argc, char* argv[]) {
// --- read file --- //
//Capture capture("test.wmv", windowSize, windowSize);
// --- read camera --- //
CvSize windowSize = cvSize(640, 480);
Capture capture(2, windowSize, windowSize);
while (1) {
capture.captureNext();
for (int i = 0; i < capture.channelNum; ++i) {
ostringstream oss;
oss << i;
string winName = "WINDOW-" + (oss.str());
cvShowImage(winName.c_str(), capture.channelframeList[i]);
}
int c = cvWaitKey(30);
if ( (char) c == 27 ) { // 'Esc' to terminate
break;
}
}
return 0;
}
caputure.h
#ifndef _CAPTURE_H_
#define _CAPTURE_H_
#include <cv.h>
#include <cxcore.h>
#include <highgui.h>
#include <string>
#include <vector>
#include <iostream>
using namespace std;
enum VIDEO_TYPE {
CAMMERA = 0,
VIDEOFILE
};
class Capture {
public:
Capture(int num, CvSize dispSize, CvSize resolutionSize);
Capture(string fileName, CvSize dispSize, CvSize resolutionSize);
int channelNum;
vector<IplImage*> channelframeList;
void captureNext();
~Capture();
private:
string m_fileName;
vector<CvCapture*> m_channelList;
CvSize m_resolutioSize;
CvSize m_displaySize;
void initChannelList(VIDEO_TYPE type);
void initChannelImgList(CvSize sz);
IplImage* getNextVideoFrame(CvCapture* pCapture);
};
#endif
capture.cpp
#include "capture.h"
Capture::Capture(int num, CvSize dispSize, CvSize resolutionSize) {
channelNum = num;
m_fileName = "";
m_resolutioSize = resolutionSize;
m_channelList.resize(channelNum);
channelframeList.resize(channelNum);
initChannelList(CAMMERA);
initChannelImgList(dispSize);
}
Capture::Capture(string fileName, CvSize dispSize, CvSize resolutionSize) {
channelNum = 1;
m_fileName = fileName;
m_resolutioSize = resolutionSize;
m_channelList.resize(channelNum);
channelframeList.resize(channelNum);
initChannelList(VIDEOFILE);
initChannelImgList(dispSize);
}
void Capture::captureNext() {
for (int i = 0; i < channelNum; ++i) {
IplImage* nextFrame = getNextVideoFrame(m_channelList[i]);
IplImage* channelFrame = channelframeList[i];
cvResize(nextFrame, channelFrame);
}
}
void Capture::initChannelList(VIDEO_TYPE type) {
if (type == CAMMERA) {
for (int i = 0; i < channelNum; ++i) {
m_channelList[i] = cvCreateCameraCapture(i);
//set resolution
cvSetCaptureProperty(m_channelList[i], CV_CAP_PROP_FRAME_WIDTH, m_resolutioSize.width);
cvSetCaptureProperty(m_channelList[i], CV_CAP_PROP_FRAME_HEIGHT, m_resolutioSize.height);
if ( !(m_channelList[i]) ) {
cout << "failed to initialize video capture" << endl;
exit(EXIT_FAILURE);
}
}
} else if (type == VIDEOFILE) {
const char* fileNameChar = m_fileName.c_str();
m_channelList[0] = cvCreateFileCapture(fileNameChar);
if ( !(m_channelList[0]) ) {
cout << "failed to initialize video capture" << endl;
exit(EXIT_FAILURE);
}
}
}
void Capture::initChannelImgList(CvSize sz) {
for (int i = 0; i < channelNum; ++i)
channelframeList[i] = cvCreateImage(sz, 8, 3);
}
IplImage* Capture::getNextVideoFrame(CvCapture* pCapture) {
IplImage* nextFrame = cvQueryFrame(pCapture);
if (!nextFrame) {
cout << "failed to get a video frame" << endl;
exit(EXIT_FAILURE);
}
return nextFrame;
}
Capture::~Capture() {
for (int i = 0; i < channelNum; ++i) {
cvReleaseImage( &(channelframeList[i]) );
cvReleaseCapture(&m_channelList[i]);
}
}
I was getting a grey screen when trying to use the camera and the Python wrapper for OpenCV inside Windows.
Tracing through with the debugger I found that it was spotting 2 camera interfaces called "Google Camera Adapter 0" and "Google Camera Adapter 1".
I was able to fix the camera input by:
- Going to "Add/Remove programs" and uninstalling "Google Talk Plugin"
- Unplugging the Webcam and plugging it back in again so that new drivers were installed.
It now works fine for me.
(Note that I do not know whether step 1 was important, and it may cause other things to break, so I would recommend you try step 2 first...)
That's the wrong approach to solve your problem. So here I go: first, isolate which camera_id is currently working. Which one is it? -1 , 0 , 1 ?
Second: please check the return of the functions, I beg you! If something is wrong, you'll never know.
CvCapture* capture = NULL;
if ((capture = cvCaptureFromCAM(-1)) == NULL)
{
fprintf(stderr, "ERROR: capture is NULL \n");
return -1;
}
cvNamedWindow("mywindow", CV_WINDOW_AUTOSIZE);
cvQueryFrame(capture); // Sometimes needed to get correct data
while (1)
{
IplImage* frame = cvQueryFrame(capture); // check return
{
fprintf( stderr, "ERROR: cvQueryFrame failed\n");
break;
}
// At this point you already have the frame! There's no need to
// repeat the thing 10x with cvGrabFrame and cvRetrieveFrame.
// You are probably sabotaging yourself doing this multiple times.
cvShowImage("mywindow", frame); // Do not release the frame!
int key = cvWaitKey(10);
if (key == 0x1b)
break;
}
cvReleaseCapture(&capture);
cvDestroyWindow("mywindow");
return 0;
精彩评论