Sunday, July 24, 2011

Using FFmpeg to
Create a Slide-Show Video

I worked on this problem all day
yesterday. I've been trying to
create a slide-show video accompanied
by sound.

I want to upload my video to YouTube
once I've finished creating it. First,
though, I had to create the video. FFmpeg
is my chosen tool.

Here is what I tried first:

ffmpeg -i sound.wav -i image.gif movie.mpg

The above command line did not work. However,
I learned a lot by having it fail. Mostly I
learned to avoid false assumptions.

My sound file was 12 seconds long. As you
can see, the above command line has only one
image and one sound file.

I figured that FFmpeg would interpret
the above command line the only way that I
would consider to be reasonable. I figured
it would throw my one image on the screen
and then run my video for the length of the
sound file.

In other words, I thought FFmpeg would stretch
the time my one and only image stayed on the screen
to match the length of my audio file. Single
images do not have a duration but a sound file
does. So why not stretch the viewing time of
the image to match the sound?

Of course, I was thinking like a human being
rather than a computer. In life, that's
the totally right thing to do.

It's the wrong thing to do If you're trying
to tell a computer what to do. When talking
to a human being, think human. When talking
to a computer, think computer.

The thing I overlooked is the fact that FFmpeg
is primarily designed to create movies, not
sound tracks. Therefore, the movie trumps the
sound.

The above FFmpeg command line truncated my
sound. I'm surprised I was able to hear any
sound at all. I heard about one second of
sound.

I suspect what happened is that my one image
in the above command line became the one frame
in my movie. Thinking like a computer,
this is a totally reasonable thing to do. Take
one image and turn it into a one frame movie.

When the one frame is done, the movie is done.
That's what I think happened.

The reason I'm surprised I heard the sound at
all is because I never saw my one frame. I only
heard my one second of sound.

Here are the statistics that FFmpeg output after
completing execution of the above command line:

frame = 1
fps = 0
time = 12.4

The above statistics give me some insight into
what really happened. Probably my player got
confused. I fed my video player a video that
is 12.4 seconds long but that runs at zero
frames per second. Does this make any sense?

Not to my video player, apparently.

The fact that I only heard one second of audio
is probably due to the fact that I created a
video that totally confused my player. Zero
frames per second is not a very comprehensible
frame rate.

The next thing I tried is this:

ffmpeg -i track01.wav -i ./image%03d.gif  track01.mpg

The above command worked!

Notice these 4 characters:

%03d

That's a C Language formatting string
from the printf function. Basically
it means expect 3 numbers.

With 3 numbers expected, I have to create
more than one image file. When I do create
multiple image files, I name them like this:

image001.gif
image002.gif
image003.gif

Since FFmpeg seems to default to 25 frames
per second output, I will need 300 frames
to match precisely 12 seconds of audio.
12 seconds X 25 frames/second = 300 frames.

Therefore, my first file will be called this:

image001.gif

My last file will be called this:

image300.gif

Each file represents one frame in my movie.

I finally found the key to making this thing
work. I need to assume 25 frames per second
video and I need to create as many frames as
necessary to fill up the audio track with frames.

Of course, there may be a better way. However,
this is what I'e found so far.

Ed Abbott

No comments:

Post a Comment