Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

I use FFmpeg to extract a keyframe at the 3rd minute. This means that it is the 3*60*25 th frame (assuming 25 FPS). Now, often this frame is not a keyframe.

I want to extract a frame closest to the above frame but ensure that it is a keyframe. This means the frame may occur a few seconds before or after the third minute of the video.

I have looked everywhere without any luck! I am doing this on Linux, so if you are using a FFmpeg with something specially installed or bundled, let me know!

share|improve this question

2 Answers 2

Using -ss parameter with select filter would work.

Something similar to:

ffmpeg -ss 180 -i yourvideo.mp4 -vf select="eq(pict_type\,I)" -vframes 1 thumbnails.jpeg
share|improve this answer
    
I think it is a fair attempt! Why would you down vote it? agree i missed -vframes 1 –  d33pika Jan 17 '13 at 7:43
    
The important part is the concept using -ss and the select filter to pick only I frames. the OP can workout a solution form there. I do not have to spoon feed an answer! –  d33pika Jan 17 '13 at 7:46
    
I have tried it. It does generate an image!, the position of -ss before or after -i is indeed a choice one has to make. I think before is faster, I am assuming that OP is ok with finding a Key frame after 3 minutes, that is a big assumption I admit. –  d33pika Jan 17 '13 at 8:02
    
Okay, I tested it again with the options placed like that (also changing PICT_TYPE_I to I), and it worked now as expected, +1 anyway (I removed a few obsolete options that don't matter in this case) –  slhck Jan 17 '13 at 8:06
1  
Did you look at this: superuser.com/questions/538112/… , I have shared what I use to pick good thumbnails from a video. –  d33pika Jan 29 '13 at 5:43

If you assume that the closest I-frame to 00:03:00 appears before that timestamp, you'll have to do some guessing, since the GOP length (the number of frames between each I-frame) isn't the same for each video. If you know your GOP length, e.g. 125 frames, then start 5 seconds before that, at 00:02:55, for example.

Note that this doesn't have to be a fixed length. Good encoders will place an I-frame at scene cuts rather than fixed points to achieve better compression and reliability.

So, let's shift the input by the amount of time we calculated before, using -itsoffset.

We specify the select filter to get us only I-frames, and -vframes to only receive one frame. Finally, write that to a .jpg file.

ffmpeg -itsoffset -00:02:55 -i in.mp4 -filter:v select='eq(pict_type\,I)' -vframes 1 out.jpg

I tested this with a video that originally has a P-frame at 00:03:00, and I received the 13th frame after that, which is the start of a new scene—an I-frame.

share|improve this answer

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.