使用 ffmpeg 提取特定帧的列表

Extract list of specific frames using ffmpeg

我正在尝试在视频上使用 ffmpeg 来提取特定帧的列表,用它们的帧号表示。所以假设我只想从 'test_video.mp4' 中提取一帧,确切地说是帧号 150。我可以使用下面的命令

ffmpeg -i test_video.mp4 -vf "select=gte(n\, 150)" -vframes 1 ~/test_image.jpg

但是如果我想要精确的帧列表怎么办,例如 [100, 110, 127, 270, 300]?我一直在查看此页面 (https://ffmpeg.org/ffmpeg-filters.html#select_002c-aselect),可以看到有一些方法可以根据帧编号、时间戳等的奇偶校验来提取多个帧,但我找不到执行所需操作的语法做。

理想情况下,我会根据命名约定 out_image%03d.jpg 提取给定帧的列表,其中 %03d 被给定的帧编号替换,尽管时间戳也可以。

有办法吗?

一个非常幼稚的回答...

#! /bin/sh -e
# framegrab v0.1

frames=""
filename=""
printf '%s' "$frames" |
sed 's:\[\|\]::g; s:[, ]\+:\n:g' |
xargs printf '%03d\n' |
xargs -IFRAME ffmpeg -i "$filename" -vf "select=eq(n\,FRAME)" -vframes 1 out_imageFRAME.jpg

用你的参数列表调用它:

 framegrab '[100, 110, 127, 270, 300]' test_video.mp4

使用

ffmpeg -i in.mp4 -vf select='eq(n\,100)+eq(n\,184)+eq(n\,213)' -vsync 0 frames%d.jpg

FFmpeg 主要是定时视频的处理器,即具有周期率(例如帧率或采样率)的媒体。它假定输出应与源的速率相同。如果提供的框架不足,除非被告知不要复制,否则它会复制。添加了 -vsync 0,在本例中,它告诉它抑制重复。