I've browsed the internet for this very intensively, but I didn't find what I needed, only variations of it which are not quite the thing I want to use.
I've got several videos in different lengths and I want to extract 20 images out of every video from start to the end, to show the broadest impression of the video.
So one video is 16m 47s long => 1007s in total => I have to make one snapshot of the video every 50 seconds.
So I figured using the -r switch of ffmpeg with the value of 0.019860973 (eq 20/1007) but ffmpeg tells me that the framerate is too small for it...
The only way I figured out to do it would be to write a script which calls ffmpeg with a manipulated -ss switch and using -vframes 1 but this is quite slow and a little bit off for me since ffmpegs numerates the images itself...
Any suggestions or directions?
Thanks, Vapire
In general, ffmpeg processes frames as they come, so anything based on the total duration/total number of frames requires some preprocessing.
I'd recommend writing a short shell script to get the total number of frames using something like
and then use the
select
video filter to pick out the frames you need. So the ffmpeg command would look something likeexcept that instead of every hundredth frame,
100
would be replaced by the number calculated in the shell script to give you 20 frames total.You could try convert video to N number of images ?
Update:
Or extract frame every 2 seconds:
Update:
To get the video duration:
Then, depends on your programming language, you convert it into seconds. For example, in PHP, you could do it like this:
where $time is the video duration. The you can execute $duration_in_seconds / 20
I was having the same problem and came up with this script which seems to do the trick:
To use it, save it as a .sh file and run it using the following parameters to export 20 frames:
This will give you the specified number of frames distributed equally throughout the video.
I know I'm a bit late to the party, but I figured this might help:
For everyone having the issue where ffmpeg is generating an image for every single frame, here's how I solved it (using blahdiblah's answer):
First, I grabbed the total number of frames in the video:
Then I tried using select to grab the frames:
But, no matter what the mod(n,100) was set to, ffmpeg was spitting out way too many frames. I had to add -vsync 0 to correct it, so my final command looked like this:
(where 100 is the frame-frequency you'd like to use, for example, every 100th frame)
Hope that saves someone a little trouble!
i had a similar question, namely how to extract ONE frame halfway a movie of unknown length. Thanks to the answers here, I came up with this solution which works very well indeed, I thought posting the php code would be useful:
I was trying to find the answer to this question too. I made use of radri's answer but found that it has a mistake.
produces a frame every 2 seconds because -r means frame rate. In this case, 0.5 frames a second, or 1 frame every 2 seconds.
With the same logic, if your video is 1007 seconds long and you need only 20 frames, you need a frame every 50.53 seconds. Translated to frame rate, would be 0.01979 frames a second.
So your code should be
I hope that helps someone, like it helped me.