OpenCV / Python:使用VideoCapture读取特定帧

时间:2015-11-11 12:53:31

标签: python python-2.7 opencv

有没有办法使用VideoCapture()方法获取特定的框架?

我目前的代码是:

import numpy as np
import cv2

cap = cv2.VideoCapture('video.avi')

This是我的参考教程。

6 个答案:

答案 0 :(得分:30)

谢谢GPPK。

视频参数应以整数形式给出。每个标志都有自己的值。有关代码,请参阅here

正确的解决方案是:

 'exampleEnter-exampleEnterActive': {
   opacity: 1,
   transition: opacity 500ms ease-in
 }

答案 1 :(得分:23)

是的,它非常直接:

id dg cs
1  s  1
1  v  0
2  s  0
2  v  1
2  s  1
2  s  0
3  s  1
3  s  1
3  v  1

' frame_number'是0 ... amount_of_frames范围内的整数。注意:你应该设置' frame_number-1'强制阅读框架#frame_number'。它没有很好地记录,但测试显示了VideoCapture模块的行为。

' RES'是布尔运算结果,可以用它来检查框架是否被成功读取。 人们可以通过以下方式获得帧数:

id dg cs output
1  s  1  True
1  v  0  False
2  s  0  False
2  v  1  False
2  s  1  False
2  s  0  False
3  s  1  True
3  s  1  True
3  v  1  False

答案 2 :(得分:16)

如果您想要一个精确的帧,您可以将VideoCapture会话设置为该帧。自动调用该帧可以更加直观。 "正确"解决方案要求您输入已知数据:如fps,length和whatnot。您需要知道的以下代码就是您想要呼叫的帧。

import numpy as np
import cv2
cap = cv2.VideoCapture(video_name) #video_name is the video being called
cap.set(1,frame_no); # Where frame_no is the frame you want
ret, frame = cap.read() # Read the frame
cv2.imshow('window_name', frame) # show frame on window

如果要按住窗口,请按退出:

while True:
    ch = 0xFF & cv2.waitKey(1) # Wait for a second
    if ch == 27:
        break

答案 3 :(得分:5)

例如,要开始阅读视频的第15帧,您可以使用:

frame = 15
cap.set(cv2.CAP_PROP_POS_FRAMES, frame-1)

答案 4 :(得分:4)

设置特定的帧

从VideoCaptureProperties(docs)的文档中可以看到,在VideoCapture中设置帧的方式是:

frame = 30
cap.set(cv2.CAP_PROP_POS_FRAMES, frame)

请注意,您不必传递给函数frame - 1,因为如文档所述,标志CAP_PROP_POS_FRAMES表示要解码的帧的基于“ 0的索引/ captured next”。

一个完整的例子是我想每秒读取一帧:

import cv2

cap = cv2.VideoCapture('video.avi')

# Get the frames per second
fps = cap.get(cv2.CAP_PROP_FPS) 

# Get the total numer of frames in the video.
frame_count = cap.get(cv2.CAP_PROP_FRAME_COUNT)

frame_number = 0
cap.set(cv2.CAP_PROP_POS_FRAMES, frame_number) # optional
success, image = cap.read()

while success and frame_number <= frame_count:

    # do stuff

    frame_number += fps
    cap.set(cv2.CAP_PROP_POS_FRAMES, frame_number)
    success, image = cap.read()

设置特定时间

在上面链接的文档中,可以看到在VideoCapture中设置特定时间的方式是:

milliseconds = 1000
cap.set(cv2.CAP_PROP_POS_MSEC, milliseconds)

就像在完整示例之前每秒读取一帧一样,可以这样实现:

import cv2

cap = cv2.VideoCapture('video.avi')

# Get the frames per second
fps = cap.get(cv2.CAP_PROP_FPS) 

# Get the total numer of frames in the video.
frame_count = cap.get(cv2.CAP_PROP_FRAME_COUNT)

# Calculate the duration of the video in seconds
duration = frame_count / fps

second = 0
cap.set(cv2.CAP_PROP_POS_MSEC, second * 1000) # optional
success, image = cap.read()

while success and second <= duration:

    # do stuff

    second += 1
    cap.set(cv2.CAP_PROP_POS_MSEC, second * 1000)
    success, image = cap.read()

答案 5 :(得分:0)

另外,我想说的是,使用 CAP_PROP_POS_FRAMES 属性并不总是能给你正确的结果。尤其是当您处理 mp4 (H.264) 等压缩文件时。

就我而言,当我为 .mp4 文件调用 cap.set(cv2.CAP_PROP_POS_FRAMES, frame_number) 时,它返回 False,但是当我为 .avi 文件调用它时,它返回 True。 决定使用此“功能”时要考虑。

very-hit 建议使用 CV_CAP_PROP_POS_MSEC 属性。

阅读this thread了解更多信息。