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


17

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

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

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



查看使用ffprobe然后对输出进行后期处理以获得索引吗?
dstob

@dstob您能否进一步解释您的意思?因为我是ffmpeg的新手。
Faten Khalifa 2015年

@LordNeckbeard视频帧中的帧号,例如。视频的第一帧将位于索引0,我想知道视频帧中每个关键帧的索引。
Faten Khalifa

您是否希望将帧号打印在缩略图上(在图像本身上)?
llogan 2015年

Answers:


21

就像提到的@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但对输出的解析将有所不同。虽然不知道如何执行重命名。


显示此错误:'grep'不被识别为内部或外部命令,可操作程序或批处理文件。
Faten Khalifa 2015年

2
那是因为您使用的是Windows。就像我说的那样,此答案假定使用Linux或Unix。您的问题没有更加具体。您可以在Windows上使用Cygwin或Windows的类似GNU / Linux层实现相同的目的。
slhck

这是巨大的帮助,谢谢。一项更正:我认为您的第一个命令中的索引偏离了三倍,因为每一行都有一行[FRAME]和一行。[/FRAME]pict_type
杰克·奥康纳

2
@ JackO'Connor如果使用-of csv选项,则每帧只有一行ffprobe。不过,您所描述的是默认输出格式。
slhck

0

如果您希望按照最初所述使用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或更改以适合缩略图删除。


在Windows 7 CMD中,此操作在\处失败。将\更改为^会导致:I“失败。您有在Windows上运行的版本吗?
ChrisJJ
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.