I'm struggling a bit trying to read/set the fps for my webcam and to read the timestamp for specific frames captured from my webcam. Specifically when I try to use vc.get(cv2.CAP_PROP_POS_MSEC)
, vc.get(cv2.CAP_PROP_FPS)
, vc.get(cv2.CAP_PROP_FRAME_COUNT)
they return respectively -1, 0, -1. Clearly there's something that I'm missing. Can someone help? The code looks like this:
import os
import time
import cv2
import numpy as np
[...]
# Create a new VideoCapture object
vc = cv2.VideoCapture(0, cv2.CAP_DSHOW)
vc.set(cv2.CAP_PROP_FRAME_WIDTH, 1280)
vc.set(cv2.CAP_PROP_FRAME_HEIGHT, 720)
# Initialise variables to store current time difference as well as previous time call value
previous = time.time()
delta = 0
n = len(os.listdir("directory"))
# Keep looping
while True:
timem = vc.get(cv2.CAP_PROP_POS_MSEC)
fps = vc.get(cv2.CAP_PROP_FPS)
total_frames = vc.get(cv2.CAP_PROP_FRAME_COUNT)
print(timem, fps, total_frames)
# Get the current time, increase delta and update the previous variable
current = time.time()
delta += current - previous
previous = current
# Check if 3 (or some other value) seconds passed
if delta > 3:
# Operations on image
# Reset the time counter
delta = 0
_, img = vc.read()
[...]
# press esc to exit
if cv2.waitKey(20) == 27:
break
edit: if I remove cv2.CAP_DSHOW
, it works, but then I cannot use CAP_PROP_FRAME_WIDTH
Apparently the OpenCV backend for cameras on your operating system (DSHOW) does not keep track of frame timestamps.
After a read()
, just use time.perf_counter()
or a sibling function. It'll be close enough, unless you throttle the reading, in which case the frames would be stale.
You could open an issue on OpenCV's github and request such a feature for DSHOW/MSMF. One would expect such a timestamp to represent the time the frame was taken, not the time it was finally read by the user program.