Storing and retrieving IplImages from vector? - c++

I want to store IplImage's ( grabbed from a video file) into a vector and then playback from this iplimage vector.
#include <iostream>
#include "highgui.h"
using namespace std;
int main()
{
CvCapture* capture=cvCreateFileCapture("D:\\Video\\Hands tracking.avi");
vector<IplImage*> imagesNames[2];
//playing video
while(1)
{
IplImage* img=cvQueryFrame(capture);
cvShowImage("Video Opencv example nd testing purpose",img);
imagesNames[0].push_back(img);
char c = cvWaitKey(30);
if(c==27) break;
}
cvDestroyWindow( "Video Opencv example nd testing purpose" );
cvReleaseCapture(&capture);
// play back grabbed IplImages
for(unsigned i=0; imagesNames[0].size();i++)
{
cvShowImage("PlayBack from IplImages vector",imagesNames[0][i]);
char c = cvWaitKey(30);
if(c==27) break;
}
return 0;
}
But the playback part of the above program is not working and showing error at runtime.

#include <iostream>
#include "highgui.h"
using namespace std;
int main()
{
CvCapture* capture=cvCreateFileCapture("D:\\Video\\Hands tracking.avi");
vector<IplImage*> imagesNames;
//playing video
while(1)
{
IplImage* img=cvQueryFrame(capture);
cvShowImage("Video Opencv example nd testing purpose",img);
imagesNames.push_back(img);
char c = cvWaitKey(30);
if(c==27)
break;
}
cvDestroyWindow( "Video Opencv example nd testing purpose" );
cvReleaseCapture(&capture);
// play back grabbed IplImages
for(unsigned i=0; i < imagesNames.size();i++)
{
cvShowImage("PlayBack from IplImages vector",imagesNames[i]);
char c = cvWaitKey(30);
if(c==27)
break;
}
return 0;
}

Related

imshow is not working

I used a for loop for reading 300 frames and for accumulating them.I gave an imshow command inside to print the frames continuously but they are not printed during the for loop is processing but it comes as a single image
Here's my code:
enter code here
#include<iostream>
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include<stdlib.h>
#include<stdio.h>
using namespace cv;
using namespace std;
int main()
{
char k;
int learningframes=300;
VideoCapture cap(0);
if(cap.isOpened()==0)
{
cout<<"ERROR";
return -1;
}
//while(1)
//{
Mat frame;
cap>>frame;
Mat frameaccF,frameacc,framethr32,framehsv,framethr;
frameaccF=Mat::zeros(frame.size(),CV_32FC1);
for(int i=0;i<=learningframes;i++)
{
cap>>frame;
imshow("nn",frame);
cvtColor(frame,framehsv,CV_BGR2HSV);
inRange(framehsv,Scalar(0,30,0),Scalar(50,150,255),framethr);
framethr.convertTo(framethr,CV_32F);
accumulate(framethr,frameaccF);
}
frameaccF=frameaccF/300;
frameaccF.convertTo(frameaccF,CV_8U);
imshow("frame",frame);
imshow("frameacc",frameaccF);
waitKey(0);
//if(k=='q')
//break;
//}
return 0;
}
You need to put the waiKey() inside the for loop
for(int i=0;i<=learningframes;i++)
{
cap>>frame;
imshow("nn",frame);
cvtColor(frame,framehsv,CV_BGR2HSV);
inRange(framehsv,Scalar(0,30,0),Scalar(50,150,255),framethr);
framethr.convertTo(framethr,CV_32F);
accumulate(framethr,frameaccF);
waitKey(0);
}

Video Grabbing doesn't work OpenCV

I am using this piece of code to grab frames off a video :
#include <stdio.h>
#include <stdlib.h>
#include <opencv/cv.h>
#include <opencv/highgui.h>
#include <iostream>
using namespace cv;
using namespace std;
int main (int argc, char** argv)
{
//initializing capture from file
CvCapture * capture = cvCaptureFromAVI ("/home/<some_file>.avi");
//Capturing a frame
IplImage* img = 0;
if(!cvGrabFrame(capture)) //capture a frame
{
cout << Could not grab a frame\n\7";
exit(0);
}
img=cvRetrieveFrame(capture); //retrieve the captured frame
//free resources
cvReleaseCapture(&capture);
}
Which is returning :
Could not grab a frame
Additional details :
I had used code to save webcam video feed to the file from which i want to grab frames .
I used this code :
#include <opencv2/opencv.hpp>
#include <opencv2/highgui/highgui.hpp>
int main( int argc, char** argv ) {
CvCapture* capture;
capture = cvCreateCameraCapture(0);
assert( capture != NULL );
IplImage* bgr_frame = cvQueryFrame( capture );
CvSize size = cvSize(
(int)cvGetCaptureProperty( capture,
CV_CAP_PROP_FRAME_WIDTH),
(int)cvGetCaptureProperty( capture,
CV_CAP_PROP_FRAME_HEIGHT)
);
cvNamedWindow( "Webcam", CV_WINDOW_AUTOSIZE );
CvVideoWriter *writer = cvCreateVideoWriter( "/Users/user/Desktop/OpenCV_trial/OpenCV_trial/vidtry.AVI",
CV_FOURCC('D','I','V','X'),
30,
size
);
while( (bgr_frame = cvQueryFrame( capture )) != NULL )
{
cvWriteFrame(writer, bgr_frame );
cvShowImage( "Webcam", bgr_frame );
char c = cvWaitKey( 33 );
if( c == 27 ) break;
}
cvReleaseVideoWriter( &writer );
cvReleaseCapture( &capture );
cvDestroyWindow( "Webcam" );
return( 0 );
}
Does anyone know where I might be going wrong ? I am running OpenCV-2.4.3 on a Beagleboard -xM with Ubuntu Quantal.
I am not quite sure what your exactly question is, but if you want to grab frames from a video, you should at least have a loop.
A reason for your error could be, that your video file is not available. Have you tried another one? The full path of the file? Or put the file directly into your working directory and check it.
Another reason could be a problem with the first frame (this sometimes happens). So try to remove your exit and enclose your code with a loop over all frames.
Here is an example that shows the given video file (Consider to use the C++-interface):
#include <opencv/cv.h>
#include <opencv/highgui.h>
#include <iostream>
using namespace cv;
using namespace std;
int main (int argc, char** argv)
{
//initializing capture from file
Mat img;
VideoCapture capture("a.avi");
if(!capture.isOpened())
{
cout<<"Could not open video!\n";
return 1;
}
while(true)
{
//Capturing a frame
capture >> img;
if(!img.empty())
{
imshow("Video",img);
}
else
{
cout <<"Could not grab a frame\n";
break;
}
if(waitKey(5) >= 0)
break;
}
return 0;
}
This program runs on my PC if the file "a.avi" is in the current working directory of the program.

Why is there only 414bytes in my mp4 file? (Xcode)(C++)

I designed a program that can record video from webcam by using OpenCV. However, when I check the saved file, I found out that there is only 414 bytes in it.
#include "cv.h"
#include "cxcore.h"
#include "highgui.h"
#include <iostream>
#define NUM_FRAME 300
using namespace std;
int main()
{
CvCapture* capture=cvCaptureFromCAM(-1);
CvVideoWriter* video=0;
IplImage* frame=NULL;
int n;
if(!capture)
{
cout<<"Can not open the camera."<<endl;
return -1;
}
else
{
frame=cvQueryFrame(capture);
video=cvCreateVideoWriter("camera.mp4", CV_FOURCC('D', 'I', 'V', 'X'), 10, cvSize(frame->width,frame->height),1);
if(video)
{
cout<<"VideoWriter has created."<<endl;
}
cvNamedWindow("Camera Video",1);
int i = 0;
while(i <= NUM_FRAME)
{
frame=cvQueryFrame(capture);
if(!frame)
{
cout<<"Can not get frame from the capture."<<endl;
break;
}
n=cvWriteFrame(video,frame);
cout<<n<<endl;
i++;
if(cvWaitKey(2)>0)
break;
}
cvReleaseVideoWriter(&video);
cvReleaseCapture(&capture);
}
return 0;
}
Here is codes of my program. Is anything wrong with the code?
there's no divx codec installed on your machine.
in this case, VideoWriter only writes the mp4 header, and fails silently.
"Is anything wrong with the code ?"
not really. but you should not use the old c-api (IplImages, cv*Functions) any more. it won't be supported in the very near future.

OpenCV - getting pixel data from camera device

I am using OpenCV 2.4.6. I have found over the Internet some example of getting frame from a camera. It works well (it displays my ugly face onto the screen). However, I absolutely cannot get pixel data from the frames. I've found some topic here: http://answers.opencv.org/question/1934/reading-pixel-values-from-a-frame-of-a-video/ but it doesn't work for me.
Here is the code - in the commented parts I pointed out what is wrong.
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
using namespace cv;
int main() {
int c;
IplImage* img;
CvCapture* capture = cvCaptureFromCAM(1);
cvNamedWindow("mainWin", CV_WINDOW_AUTOSIZE);
while(1) {
img = cvQueryFrame(capture);
uchar* data = (uchar*)img->imageData; // access violation
// this does not work either
//Mat m(img);
//uchar a = m.data[0]; // access violation
cvShowImage("mainWin", img);
c = cvWaitKey(10);
if(c == 27)
break;
}
}
Could you give me some suggestions, please?
I suggest using the newer Mat structure instead of IplImage since your question is tagged with C++ tag. For your task you can use a data member of Mat - it points to internal Mat storage. For example Mat img; uchar* data = img.data;. Here's a full example
#include <opencv2/core/core.hpp>
#include <opencv2/highgui/highgui.hpp>
using namespace cv;
int main() {
int c;
Mat img;
VideoCapture capture(0);
namedWindow("mainWin", CV_WINDOW_AUTOSIZE);
bool readOk = true;
while(capture.isOpened()) {
readOk = capture.read(img);
// make sure we grabbed the frame successfully
if (!readOk) {
std::cout << "No frame" << std::endl;
break;
}
uchar* data = img.data; // this should work
imshow("mainWin", img);
c = waitKey(10);
if(c == 27)
break;
}
}

delay in ouput of combined c++ program

i have two programs in c++. one is to communicate with arduino(pgm1),while the other is an openCV program reading a webcam(pgm2). independently, they work at moral speed.
if we open them simultaneously in different terminals they work perfect.i wanted to join them as a single program, i tried a program (pgm3). i can get images perfectly in real time.. but the data from arduino delays about 7-10 seconds. unfortunately i know only c/c++/embedded c. so kindly refer me a solution in any one of these languages
pgm1
#include<iostream>
#include<fstream>
using namespace std;
int main()
{
char ch;
ifstream f;
f.open("/dev/ttyACM0");
while (f.get(ch))
{
cout<<ch;
if(ch=='#')
cout<<endl;
}
return 0;
pgm2
#include "opencv2/objdetect.hpp"
#include "opencv2/highgui.hpp"
#include "opencv2/imgproc.hpp"
#include <iostream>
#include <stdio.h>
using namespace std;
using namespace cv;
/** Function Headers */
String window_name = "webcam c170 preview";
/** #function main */
int main( void )
{
VideoCapture capture;
Mat frame;
capture.open( 1 );
if ( ! capture.isOpened() ) { printf("--(!)Error opening video capture\n"); return -1; }
while ( capture.read(frame) )
{
if( frame.empty() )
{
printf(" --(!) No captured frame -- Break!");
break;
}
//-- 3. show frames
imshow( window_name, frame );
int c = waitKey(30);
if( (char)c == 27 ) { break; } // escape
}
return 0;
}
}
pgm3
#include "opencv2/objdetect.hpp"
#include "opencv2/highgui.hpp"
#include "opencv2/imgproc.hpp"
#include <iostream>
#include <stdio.h>
#include<fstream>
using namespace std;
using namespace cv;
void spi_read(void);
/** Global variables */
char ch;
ifstream f;
String window_name = "webcam c170 preview";
/** #function main */
int main( void )
{
VideoCapture capture;
Mat frame;
f.open("/dev/ttyACM0");
capture.open( 1 );
if ( ! capture.isOpened() ) { printf("--(!)Error opening video capture\n"); return -1; }
while ( capture.read(frame) )
{
if( frame.empty() )
{
printf(" --(!) No captured frame -- Break!");
break;
}
//-- 3. show frames
imshow( window_name, frame );
int c = waitKey(30);
if( (char)c == 27 ) { break; } // escape
spi_read();
}
return 0;
}
void spi_read()
{
String str_spi;
do
{
f.get(ch);
str_spi=str_spi+ch;
}while(ch!='#');
cout<<str_spi<<endl;
}
Do not just merge to code into one function - of course it will cause your second program to "delay" - because its starts to execute after ur previos code is done.
You should create separate thread to simulate ur pgm1/pgm2 programs and then maybe process data received by them in ur main thread - depending on your needs.
Most straighforward solution using boost/thread:
void do_what_pgm1_does() {..}
void do_what_pgm2_does() {..}
int main()
{
boost::thread t1(do_what_pgm1_does);
boost::thread t2(do_what_pgm2_does);
t1.join();
t2.join();
}
this will give you similar execution as you had with 2 processes.