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.

How can I convert a video file to a sequence of images, for example one frame every N seconds. Can mplayer or ffmpeg do this? I have used MPlayer to grab screenshots manually but I would like to automate this for a long video.

share|improve this question
add comment

8 Answers 8

up vote 12 down vote accepted
mplayer -vo jpeg -sstep 5 file.avi

will save a frame as a jpeg file every 5 seconds.

However, it will not stop at the end of the file, it will continue producing copies of the last frame. To avoid this, find the duration of the video in seconds, using another player, or with mplayer:

mplayer -vo null -ao null -frames 0 -identify file.avi

and look for a line like "ID_LENGTH=147.00".

Subtract 2 from the length, and use this value for the -endposoption. For example, for a 147 second video:

mplayer -vo jpeg -sstep 5 -endpos 145 file.avi
share|improve this answer
    
this sounds like an mplayer bug. nice workaround. –  quack quixote Apr 29 '10 at 17:04
add comment

With ffmpeg, you can do the following:

ffmpeg -ss -4 -i test.avi -s:v 320x240 -frames:v 1 -an test.jpg

This command generates a 320×240 sized JPG thumbnail at the 4th second in the video. Put this in a script that changes the time and file name and you're done.

Long version: Creating video thumbnails using ffmpeg

share|improve this answer
    
This seems to do what I want, but with one problem. It will process the file from the start on each iteration, getting exponentially slow. –  Liam Apr 27 '10 at 14:42
    
@Liam - Does it help if you leave the offset time alone (set it at 1) and use the -ss position flag to seek further into the file instead? -ss Seek to given time position in seconds. hh:mm:ss[.xxx] syntax is also supported –  Nifle Apr 29 '10 at 7:53
1  
@liam: put the -ss before the -i so that the seek happens before the input video gets decoded. this should speed it up. source –  quack quixote Apr 29 '10 at 17:03
1  
There's a better, much faster way to do it with ffmpeg. See my answer below. –  stib Mar 15 at 9:47
    
stib's solution is the best IMO. –  Griffin Jun 2 at 7:48
add comment

With VLC 1.1.0 and above, you can use the scene video filter:

vlc C:\video\to\process.mp4 --rate=1 --video-filter=scene --vout=dummy --start-time=10 --stop-time=11 --scene-format=png --scene-ratio=24 --scene-prefix=snap --scene-path=C:\path\for\snapshots\ vlc://quit

The above saves 1 out of every 24 frames (--scene-ratio=24), starting at 00:00:10 and ending at 00:00:11.

Just tested and confirmed this works with VLC 2.0.3 on a fresh Windows 8 installation (I have no additional video plugins or software).

Full documentation: http://wiki.videolan.org/How_to_create_thumbnails

share|improve this answer
add comment

If you are after a kind of contact sheet and if you are working with a Unix-like OS, you can use this elaborate script, called to the point Video Contact Sheet *NIX, short vcs.

In the background it also uses vlc (by default) or mplayer, hence can handle a lot of video formats. It automates the process of capturing still images from the movie and compose these to an image with some header and footer. You can choose e.g. how many captures you want or alternatively the time differences between them.

For a interval of 10 minutes, the invocation is like that:

vcs -i 10m input.avi

Check the full list of commandline options for some other tweaks.

Here is an example contact sheet, taken from the homepage:

enter image description here

share|improve this answer
add comment

It's very simple with ffmpeg, and it can output one frame every N seconds without extra scripting. To export as an image sequence just use myimage_%04d.png or similar as the output. The %0xd bit is converted to a zero-padded integer x digits long - the example I gave gets output as myimage_0000.png myimage_0001.png etc.. You can use lots of still image formats, png, jpeg, tga, whatever (see ffmpeg -formats for a full list).

Ok so to export as an image sequence we can use an image format as the output with a sequential filename, but we don't want to export every single frame. So simply change the frame rate of the output to whatever we want using the -r n option where n is the number of frames per second. 1 frame per second would be -r 1, one frame every four seconds would be -r 0.25, one frame every ten seconds would be -r 0.1 and so on.

So to put it all together, this is how it would look to save one frame of input.mov every four seconds to output_0000.png, output_0001.png etc.:

ffmpeg -i input.mov -r 0.25 output_%04d.png

Change the %xd to however many digits you need, e.g. if the command would create more than 10,000 frames change the %04d to %05d. This also works for input files that are image sequence. Read more here.

Also note that if you're trying to do this on Windows you need to escape the % signs with %, so where you see % change it to %%.

share|improve this answer
add comment

You could also try this

from the VLC command line...

vlc "C:\YOUR\file\path\file.avi" -V image --image-out-prefix=capname --image-out-ratio=60

file.avi is the video you want to capture from, capname is the prefix of the saved images, you might want to play around with the ratio (60 means that 1 out of 60 images is captured) You can add more commands, for example --image-out-format jpeg will save your caps as jpegs instead of of pngs, --snapshot-path lets you choose where to save your caps.

Source of above

share|improve this answer
    
I got this message: The command line options couldn't be loaded, check that they are valid. –  Liam Apr 28 '10 at 9:45
    
On Ubuntu, I got this message: unknown option or missing mandatory argument `--image-out-prefix=capname' –  Liam Apr 28 '10 at 9:54
add comment

VirtualDub can do this for you

File -> Export -> Image sequence

enter image description here

share|improve this answer
    
Will this save every frame as an image? –  Liam Apr 27 '10 at 15:32
    
yes, every frame. –  Shevek Apr 27 '10 at 16:25
    
I need to skip most frames, outputting all frames will use up too much storage space. I need just one frame every few seconds. –  Liam Apr 28 '10 at 9:56
add comment

You can skip frames in VirtualDub. Just use "Decimate By" option located at Video -> Frame Rate menu. For example if you set "Decimate By 100" then use File -> Export -> Image sequence, it will save only every 100th frame.

share|improve this answer
add comment

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.