I am trying to read multiple image files named like 001.jpg, 002.jpg, 003.jpg and onwards by using OpenCV on Linux and displaying them in a window after some delay. Here is my code -
int main(int argc, char ** argv){
cv::VideoCapture cam("/home/bikz05/Desktop/dataset/%03d.jpg");
if (!cam.isOpened())
cout << "Capture is not opened";
cv::Mat image;
const string Window = "Image Number";
namedWindow(Window, CV_WINDOW_NORMAL);
while(true) {
cam >> image;
if (!image.data) {
std::cout << "Preview Ends" << std::endl;
break;
}
cv::imshow(Window, image);
waitKey(1000);
}
return 0;
}
In the first line of the main function, I even tried using
cv::VideoCapture cam("/home/bikz05/Desktop/dataset/001.jpg");
I even tried to place the images in the same folder as the binary, even that didn't help.
In both the cases, it displays only the first image and then the program exits. Note, it doesn't finish.
P.S. - The answers provided on Stack Exchange and opencv.org did not produce the intended result.
The code as you have written has several problems, but if you are going to read images from the disk, use cv::imread() instead of cv::VideoCapture:
std::string filename = "/home/bikz05/Desktop/dataset/001.jpg";
const std::string Window = "Image Number";
cv::namedWindow(Window, CV_WINDOW_NORMAL);
while (true)
{
cv::Mat image = cv::imread(filename.c_str());
if (!image.data)
{
std::cout << "!!! File not found: " << filename << std::endl;
break;
}
cv::imshow(Window, image);
cv::waitKey(1000);
// And before the loop ends, update filename with the next image:
// filename = ???;
}
I haven't tested this, but I'm sure you get the idea.
use glob as in glob(folderpath, vectorOfimages) then access each of the images as vectorOfimages[i].
vectorOfimages is
vector<String>
and folderpath is a String.
I had the same problem and videoCapture does not solve it.
Related
Below code works perfectly well when used in the program that is build as an EXE, but the same code opens a blank window when used in a DLL
Mat image;
VideoCapture capture;
capture.open(0);
if(capture.isOpened())
{
cout << "Capture is opened" << endl;
for(;;)
{
capture >> image;
if(image.empty())
break;
imshow("Sample", image);
if(waitKey(10) >= 0)
break;
}
}
capture.open(0) returns 0.
Other than this, it does not write any error to the console, nor the control enters the catch block.
Could you help me debug this issue?
I have written a program to display a stored video file using opencv. I attached the code below. I am not getting any errors while building it but no output is displayed.
int main(int argc, char *argv[])
{
if (argc <= 1)
{
printf("Usage: %s video\n", argv[0]);
return -1;
}
VideoCapture capture(argv[1]);
namedWindow("display",cv::WINDOW_AUTOSIZE);
capture.set(cv::CAP_PROP_FRAME_WIDTH, 640);
capture.set(cv::CAP_PROP_FRAME_HEIGHT, 480);
if(!capture.isOpened())
{
printf("Failed to open the video\n");
return -1;
}
int i;
for(i=0;i<390;i++)
{
Mat frame;
capture >> frame; // get a new frame from camera
cout << "frame =" << endl << " " << frame << endl << endl;
imshow("display",frame);
}
}
I included the cout line at the end to check if the frame is getting any value or not. So a got a number of values in a matrix, but the video window is not appearing.
You have to add a very small delay after imshow by using waitKey.
imshow("display",frame);
waitKey(10); //Wait 10 milliseconds before showing next frame.
I have a simple OpenCV application that takes a video stream from the webcam, and when the spacebar is pressed it captures the current image and freezes on that image. When I try to use the cv::imwrite() method to save the picture to disk, it does not work. The code successfully compiles but it does not save the image. It is returning a false value as well from the call. I am not sure if this is an issue of type of image or something else, but I seem to be stumped.
Here is the code for my current cpp class:
#include <iostream>
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/highgui/highgui.hpp"
using namespace std;
using namespace cv;
Mat picture;
char key;
class FacialRec {
};
int main() {
//Starting the video
VideoCapture videoCapture(0);
if (!videoCapture.isOpened()) {
cout << "Unable to open video file." << endl;
return 1;
}
namedWindow("Webcam", CV_WINDOW_AUTOSIZE);
while(true) {
Mat frame;
videoCapture.retrieve(frame);
bool success = videoCapture.read(frame);
if (!success) {
cout << "Could not read from video file" << endl;
return 1;
}
imshow("Webcam", frame);
key = waitKey(30);
if (key == 27) { //escape key pressed: stop program
cout << "ESC pressed. Program closing..." << endl;
break;
}else if (key == ' ') { //spacebar pressed: take a picture
picture = frame;
key = -1;
while (true) {
imshow("Webcam", picture);
key = waitKey(30);
if (key == 27 || key == 32) {
cout << "ESC or SPACE pressed. Returning to video..." << endl;
break;
}
if (key == 115) {
//trying to save to current directory
bool maybe = imwrite("/testimage.jpg", picture);
// maybe bool is always getting value of 0, or false
cout << "s was pressed. saving image " << maybe << endl;
}
}
}
}
return 0;
}
You are attempting to write testimage.jpg to the / directory. The executing program probably doesn't have sufficient permissions to write to that directory. Based on your comment, you probably want
//trying to save to current directory
bool maybe = imwrite("./testimage.jpg", picture);
Since . denotes the current working directory.
OpenCV sometimes has problems to write to a .jpg image. Try to change that to .png or .bmp to see if that makes a difference in your case.
If you have further issues with writing images, you can debug them in OpenCV by adding this few lines of code to display them and see if they are valid:
// Create a window for display.
namedWindow( "Display window", WINDOW_AUTOSIZE );
// Show our image inside it.
imshow( "Display window", picture );
// Wait for a keystroke in the window
waitKey(0);
A few suggestions.
try a different file format.
does your IDE defiantly know your target folder / home path directory?
Is your image definitely valid? does it show when you imshow()?
Does anyone know how to get OpenCV to grab all the frames from a video file?
I've been trying to just grab frames from video files (.wmv files, in particular), but on most videos, I end up with "nan" as my framerate and it only gets a single frame from my video and doesn't think there are any more. However, on at least one video, it succeeds and gets the right framerate. I tried to manually set the frame rate, but this did not work.
One thing to note is that it seems like the videos where it doesn't work are very short (~5 seconds long). However, I have not thoroughly tested this theory as I don't have very many videos (only ~10 videos).
The minimum code necessary to reproduce this is below:
int main(int argc, char** argv)
{
VideoCapture capture;
char* video = argv[1];
int flag = arg_parse(argc, argv);
capture.open(video);
//capture.set(CV_CAP_PROP_FPS, 25); // Trying to set frame rate.
std::cout << "frame rate: " << capture.get(CV_CAP_PROP_FPS) << std::endl;
if(!capture.isOpened()) {
fprintf(stderr, "Could not initialize capturing..\n");
return -1;
}
while(true) {
Mat frame;
int i, j, c;
// get a new frame
capture >> frame;
std::cout << "GOT FRAME!" << std::endl;
if(frame.empty()) {
std::cout << "breaking..." << std::endl;
break;
}
}
return 0;
}
Thanks so much!
I am trying to write the recording from my webcam into a file. For this purpose I am using the following code. I am getting an exit code of 2, all the time. Can someone help me figure out what is the problem?
I have previously used a similar function call to write frames from one video file into a new one, where it worked. Can't understand what is the problem in this case.
Code Snippet follows:
int main(int argc, char *argv[]){
cv::Mat frame;
cv::VideoCapture cap(0);
cv::BackgroundSubtractorGMG bg;
bg.numInitializationFrames=120;
bg.decisionThreshold = 0.95;
bg.maxFeatures = 10;
double fps = cap.get(CV_CAP_PROP_FPS);
CvSize frameSize;
frameSize.height = cap.get(CV_CAP_PROP_FRAME_HEIGHT);
frameSize.width = cap.get(CV_CAP_PROP_FRAME_WIDTH);
VideoWriter VW1("resultbuff.avi",CV_FOURCC('M','P','E','G'), fps, frameSize, 1);
VideoWriter VW2("recordingbuff.avi",CV_FOURCC('M','P','E','G'), fps, frameSize, 1);
VideoWriter VW3("finalResult.avi",CV_FOURCC('M','P','E','G'), fps, frameSize, 1);
if (!VW1.isOpened())
{
std::cout << "!!! Output video could not be opened" << std::endl;
return 2;
}
if (!VW2.isOpened())
{
std::cout << "!!! Output video could not be opened" << std::endl;
return 3;
}
if (!VW3.isOpened())
{
std::cout << "!!! Output video could not be opened" << std::endl;
return 4;
}
As mentioned, the program exits with code 2.
Okay, I found the answer. It was an error with the dlls. I was running the program in debug mode and the openCV dlls linked were for the release mode.