Waiting to capture from VideoCapture


What I wanted to do is make a live video capture VideoCapture cap that only captures every set amount of time ‘X’, where X is typically anywhere between 500ms - 1s. If the difference between two captures currentIMG & previousIMG was high enough, it was supposed to do some kind of processing task and set the previousIMG to the one it just took so that it will be what it compares captures to from that point onward.

However, when attempting that, I noticed that it didn’t actually get what was happening at that moment on waking up. To my knowledge, it just got whatever was “next in the buffer” for the VideoCapture object. This resulted in it just pausing before getting whatever is next in the buffer, rather than skipping all the things it saw in between those two time periods.

Is there a time efficient way to make sure I get whatever the “camera sees” on waking up and not just whatever was in the buffer next?


int main() {

	// open the camera and capture a image
	Mat currentIMG, previousIMG;
	VideoCapture cap;
	cap >> previousIMG;

	struct timespec ts = {ts.tv_sec = 1, ts.tv_nsec = 0};
	for (;;) {
		// wait & then capture an image for 'currentIMG'
		nanosleep(&ts, NULL);
		cap >> currentIMG;

		// check if the difference between the previous
		// and current images (in terms of decimal percentage)
        // exceeds the threshold 
		if (PSNR(currentIMG, previousIMG) > 0.20) {
            // Some kind of task that takes a bit to complete
            imwrite("capturedIMG.png", currentIMG);
            previousIMG = currentIMG.clone();

	// Exit
	return 0;

What I tried so far

  1. Setting the buffer size with cap.set(cv::CAP_PROP_BUFFERSIZE, 1)

I’ve tried setting the buffer size of cap to 1, so I could limit the amount of images inside of the buffer. However, despite getting a 1 back when printing that call and it seeming like it’s supported, it doesn’t actually do anything to solve the issue.

  1. Threaded grab() loop

I’ve tried using a main/worker threads that has one thread pull from the buffer and the other is the main thread that just takes whatever’s left but I haven’t got it to work efficiently as of yet and I feel like there should be an easier way than to work around threading.

related: c++ - OpenCV 4.0 -- Waiting to capture from VideoCapture - Stack Overflow