11
votes

I am creating a short video from a sequence of 100 images using ffmpeg. There are several articles that helped me put together a command, but the one I'm using is directly taken from ffmpeg images-to-video script anyone?.

The following command produces a video file that plays well in all video players I have (OS X).

cat input/*.jpg | ffmpeg -f image2pipe -r 10 -vcodec mjpeg -i - out.mp4

But if I change it to,

cat input/*.jpg | ffmpeg -f image2pipe -r 1 -vcodec mjpeg -i - out.mp4

It plays well in all but VLC media player. VLC displays the initial 1 to 3 images, then just freezes on the frame. I've tested a few different frame rates, and it seems the cutoff that breaks the video playback in VLC lies somewhere between 1.125 and 1.175.

Any advice on what I'm dealing with here would be much appreciated.

3
Complete console outputs missing. You could add an output -r with a value that is supported by your players. ffmpeg will then duplicate frames to match the requested output frame rate.llogan
I think it's a bug in vlc.... I can reproduce the problemdsign
I have the same problem when making a video of a graph changing with time. Tested 0.5 fps and 1 fps with x264, mpeg4 and gif using avconf and moviepy (with backend ffmpeg).Simon Streicher

3 Answers

3
votes

Use both -framerate and -r

E.g., to have a final video that looks like 1FPS:

ffmpeg -framerate 1 -pattern_type glob -i '*.png' \
    -c:v libx264 -r 30 -pix_fmt yuv420p out.mp4

This is mentioned on the wiki at: http://trac.ffmpeg.org/wiki/Slideshow#Framerates

It sets the output framerate to 30, which VLC can handle, and copies each images 30 times, so that the output video appears to be at 1 FPS.

VLC is then able to play the video normally.

See also: https://unix.stackexchange.com/questions/68770/converting-png-frames-to-video-at-1-fps

Tested on Ubuntu 16.10, VLC 2.2.4, ffmpeg 3.0.5, in a directory with 10 PNGs.

ffplay

I would also try to play the video with ffplay from ffmpeg, I would expect it to be more robust and be able to handle such framerates. It is very bare bones, but it should be fine for the type of test video that you are likely to be using at 2 FPS. TODO test it out.

2
votes

It's a long known bug in VLC: https://trac.videolan.org/vlc/ticket/3625 (https://trac.videolan.org/vlc/ticket/214)

It has been reported by many users with various thresholds, but from what I found and experienced myself, the threshold is somewhere around a couple of FPS.

Currently I am sadly looking at frozen first frame of a 2 FPS video that won't play in the current version of VLC (2.2.4) I remember it working on some 1.1.x version (even though the bug was reported much earlier) but after update to 2.x it stopped working for me.

Me and my colleague have actually compared the behavior with the very same video files (2 FPS) some time ago and while I could play all of them without problems with 1.1.x (I think it was 1.1.1 but I am not 100% sure anymore), he couldn't play any of them with 2.x. After he downgraded VLC to 1.1.x, he could play them as well.

So maybe downgrade is the way to go, if you're desperate to use VLC and will not miss anything from 2.x. Otherwise I'd say save yourself the painful hours of fiddling with VLC settings and simply use a different player.

Update: This now seems to be fixed in VLC 3.0.4 (see https://trac.videolan.org/vlc/ticket/214) I did not test it myself though.

Update #2: The bug has been reopened as apparently it was not fixed (or at least not properly) and the problem can still happen.

1
votes

This is a bug in VLC (which still exists in version 3.0.6). After some experiments I realized that VLC crashes for videos with FPS less than 10. So all videos with 10 FPS or more shouldn't be a problem. So there is currently no clean way to get a video with 1 FPS which is playable in VLC (don't give up, keep reading).

One workaround is -as shown in the answer above- to fake the effect of 1 FPS by duplicating the images (when we actually have an FPS equals to 10 or more, which is ok for VLC).

Example: if you have a folder with 12 images, and you would like to generate a video with 1 FPS (which is playable in VLC), then you need to duplicate each image multiple times (let's say 10 times), and then tell FFMPEG to generate a 10 FPS video. In this way we will get a video with a total frames of 120, where each image will be played for 1 seconds (as it is duplicated 10 times), which is simply a fake for 1 FPS.

I prefer to use fps parameter rather than -r (which is shown in another answer) which may in some case be problematic (according to the official documentation).

ffmpeg -framerate 1 -i "img (%d).jpg" -c:v libvpx-vp9 -vf "fps=10,format=yuv420p" out.mkv

As the input -framerate is lower than the output fps, FFMPEG will duplicate frames to reach your desired output frame rate (which is 10 according to the command above).

It is also important to notice that the order of -framerate and -vf fps is important, as this configuration will be applied to the next mentioned video (in- or output). That is according to the official docs:

options are applied to the next specified file. Therefore, order is important...