我正在使用OpenCV4和Python3打开一个摄像头,抓取帧并在窗口中显示它们,就像第一个代码教程提供的here一样。然而,抓取不同的帧需要不同的时间:有时需要0.01秒来抓取,有时需要0.33秒,这会在窗口中显示帧时产生延迟。
有没有一种方法可以在抓取帧的时候强制一个固定的时间,这样我就可以毫无延迟地看到视频了?我认为OpenCV就是这样,因为当我使用默认的windows摄像头查看器查看视频时,它会正常显示视频。
我已经尝试过使用time.sleep()
等待一段时间,然后再抓取帧。但这无济于事。
import numpy as np
import cv2
cap = cv2.VideoCapture(0)
while(True):
# Capture frame-by-frame
ret, frame = cap.read()
# Display the resulting frame
cv2.imshow('frame',gray)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
# When everything done, release the capture
cap.release()
cv2.destroyAllWindows()
发布于 2019-06-26 04:53:53
一种可能的方法是在循环中设置时间戳,并跟踪显示最后一帧的时间。例如,只有一段时间过去后,您才会显示帧。同时,您不断地读取帧以保持缓冲区为空,以确保您拥有最新的帧。您不希望使用time.sleep()
,因为它会冻结程序,而不会将缓冲区保留为空。一旦时间戳命中,您将显示帧并重置时间戳。
import cv2
import time
cap = cv2.VideoCapture(0)
# Timeout to display frames in seconds
# FPS = 1/TIMEOUT
# So 1/.025 = 40 FPS
TIMEOUT = .025
old_timestamp = time.time()
while(True):
# Capture frame-by-frame
ret, frame = cap.read()
if (time.time() - old_timestamp) > TIMEOUT:
# Display the resulting frame
cv2.imshow('frame',frame)
if cv2.waitKey(1) & 0xFF == ord('q'):
break
old_timestamp = time.time()
# When everything done, release the capture
cap.release()
cv2.destroyAllWindows()
发布于 2019-12-28 06:50:08
我最近偶然发现了这个问题。我没有使用OpenCV的帧捕获,而是设置了一个单独的进程-使用ffmpeg捕获它们并将其写入到ramdisk。
Python的watchdog使我能够在更新时获得通知,并启动OCR过程。
事实证明,在控制捕获方面,它更快、更有效,而且粒度很大。
发布于 2020-03-26 23:13:00
正常工作时,此应用程序将在read()调用时挂起,直到流式网络摄像头的下一帧可用。流畅的显示取决于是否能够在少于1/FPS秒的时间内执行添加到循环中的任何内容。它还取决于摄像头是否符合UVC,并可能取决于编码算法为MJPEG,这是大多数网络摄像头的情况。但是,您看到的延迟高达1/3秒的事实很奇怪,因为这是mpeg或其他帧间编码器的典型GOP周期。
如果上述情况都不适用于您的情况,那么我怀疑问题是与平台相关的,而不是OCV问题。您是否尝试过在另一个系统上复制此问题?
https://stackoverflow.com/questions/56759785
复制相似问题