使用 ffmpeg 从视频中提取关键帧的索引

使用 ffmpeg 从视频中提取关键帧的索引

我正在使用 ffmpeg 从视频中提取关键帧。这是命令:

ffmpeg -i test2.mp4 -vf select='eq(pict_type\,I)' -vsync 2 -s 160x90 -f image2 thumbnails-%02d.jpeg

如何获取视频中提取的每个关键帧的索引?例如,对于第一个 I 帧,索引为 0,对于第二个,索引为 24,等等。

答案1

就像@dstob提到的那样,您可以使用它ffprobe来获取I帧及其相关信息。ffprobe附带一些下载页面上的静态构建并且也可以从源代码构建。

假设您使用的是 Linux/Unix:

提取帧和帧类型

ffprobe -select_streams v -show_frames \
-show_entries frame=pict_type \
-of csv bbb480.avi \
| grep -n I | cut -d ':' -f 1

grep命令过滤I其中的行,并计算其索引(使用选项-n)。该cut命令仅选择输出的第一列(索引)。请注意,此索引以 1 为基数,而不是以 0 为基数。

根据索引重命名输出文件

您实际上可以将这些索引传送到列表中:

ffprobe -select_streams v -show_frames \
-show_entries frame=pict_type \
-of csv bbb480.avi \
| grep -n I | cut -d ':' -f 1 > frame_indices.txt

然后列出所有缩略图:

ls -1 thumbnails*.jpeg > thumbnails.txt

然后将两者粘贴在一起:

paste thumbnails.txt frame_indices.txt > combined.txt

列表现在包含缩略图的名称和索引。根据该名称执行重命名:

while read -r thumbnail index; do
  newIndex=$(echo $index - 1 | bc) # subtract 1 from the index
  mv -- "$thumbnail" "thumbnail-$newIndex.jpeg"  # rename file
done < combined.txt

以上将重命名thumbnail-01.jpegthumbnail-0.jpeg。请注意,输出索引上没有零填充。如果您想将其零填充为 5 位数字,请使用printf

newIndex=$(printf '%05d' $(echo $index - 1 | bc))

在 Windows 上,您可以执行完全相同的操作,ffprobe但解析输出的方式不同。不过不知道如何在那里执行重命名。

答案2

如果您希望按照最初说明的方式使用 FFMPEG,您可以列出全部或部分列表以及使用以下内容创建 jpg:

ffmpeg.exe \
  -i "C:\Users\UserName\Desktop\jpegs and list\VideoName.mp4" \
  -t 15 \
  -vf select="eq(pict_type\,PICT_TYPE_I)" \
  -vsync 2 \
  -s 160x90 \
  -f image2 thumbnails-%02d.jpeg \
  -loglevel debug 2>&1| for /f "tokens=4,8,9 delims=. " %d in ('findstr "pict_type:I"') do echo %d %e.%f>>"keyframe_list.txt"

-t 15无时间限制地删除或更改以适应。删除-s 160x90 -f image2 thumbnail-%02d.jpeg或更改以适应缩略图删除。

相关内容