My thoughts on Slackware, life and everything

Tag: video (Page 2 of 2)

Fixing audio sync with ffmpeg

The ffmpeg developers and their libav antipodes are engaged in a healthy battle. Ever since there was a fall-out and the ffmpeg developer community split in two (forking ffmpeg into “libav”), ffmpeg itself has seen many releases which tend to incorporate the good stuff from the other team as well as their own advancements.

Last in series is ffmpeg-0.9 for which I built Slackware packages (if you want to be able to create mp3 or aac sound, get the packages with MP3 and AAC encoding enabled instead.

The package will come in handy if you want to try what I am going to describe next.

Re-sync your movie’s audio.

You probably have seen the issue yourself too: for instance, I have a file “original.avi” which has an audio track (or “stream“) which is slightly out of sync with the video… just enough to annoy the hell out of me. I need to delay the audio by 0.2 seconds to make the movie playback in sync. Luckily, ffmpeg can fix this for you very easily.

Let’s analyze the available streams in the original video (remember, UNIX starts counting at zero):

$ ffmpeg -i original.avi

Input #0, avi, from ‘original.avi’:

Stream #0.0: Video: mpeg4, yuv420p, 672×272 [PAR 1:1 DAR 42:17], 23.98 fps, 23.98 tbr, 23.98 tbn, 23.98 tbc
Stream #0.1: Audio: mp3, 48000 Hz, stereo, s16, 128 kb/s

You see that ffmpeg reports a “stream #0.0” which is the first stream in the first input file (right now we have only one input file but that will change later on) – the video. The second stream, called “stream #0.1“, is the audio track.

What I need is to give ffmpeg the video and audio as separate inputs, instruct it to delay our audio and re-assemble the two streams into one resultant movie file. The parameters which define two inputs where the second input will be delayed for N seconds, goes like this:

$ ffmpeg -i inputfile1 -itsoffset N -i inputfile2

However, we do not have a separate audio and video tracks, we just have the single original AVI file. Luckily, the “inputfile1” and “inputfile2” can be the same file! We just need to find a way to tell ffmpeg what stream to use from which input. Look at how ffmpeg reports the content of input files if you list the same file twice:

$ ffmpeg -i original.avi -i original.avi

Input #0, avi, from ‘original.avi’:

Stream #0.0: Video: mpeg4, yuv420p, 672×272 [PAR 1:1 DAR 42:17], 23.98 fps, 23.98 tbr, 23.98 tbn, 23.98 tbc
Stream #0.1: Audio: mp3, 48000 Hz, stereo, s16, 128 kb/s

Input #1, avi, from ‘original.avi’:

Stream #1.0: Video: mpeg4, yuv420p, 672×272 [PAR 1:1 DAR 42:17], 23.98 fps, 23.98 tbr, 23.98 tbn, 23.98 tbc
Stream #1.1: Audio: mp3, 48000 Hz, stereo, s16, 128 kb/s

You see that the different streams in multiple input files are all numbered uniquely. We will need this defining quality. I colored the numbers with red & purple – these colors will show up in my example commands below.

Our remaining issue is that ffmpeg must be told that it has to use only the video stream of the first inputfile, and only the audio stream of the second inputfile. Ffmpeg will then have to do its magic and finally re-assemble the two streams into a resulting movie file. That resulting AVI file also expects video as the first stream, and audio as the second stream, just like our original AVI is laid out. Movie players will get confused otherwise.

Ffmpeg has the “map” parameter to specify this. I have looked long and hard at this parameter and its use… it is not easy for me to follow the logic. A bit like the git version control system, which does not fit into my brain conceptually, either. But perhaps I can finally explain it properly, to myself as well as to you, the reader.

Actually, we need two “map” parameters, one to map the input to the output video and another to map the input to the output audio. Map parameters are specified in the order the streams are going to be added to the output file. Remember, we want to delay the audio, so inherently the audio track must be taken from the second inputfile.

In the example below, the first “-map 0:0” parameter specifies how to create the first stream in the output. We need the first stream in the output to be video. The “0:0” value means “first_inputfile:first_stream“.

The second “-map 1:1” parameter specifies where ffmpeg should find the audio (which is going to be the second stream in the output). The value “1:1” specifies “second_inputfile:seccond_stream.

$ ffmpeg -i original.avi -itsoffset 0.2 -i original.avi -map 0:0 -map 1:1

There is one more thing (even though it looks like ffmpeg is smart enough to do this without explicitly telling so). I do not want any re-encoding of the audio or video to happen, so I instruct ffmpeg to “copy” the audio and video stream without intermediate decoding and re-encoding. The “‘-acodec copy” and “-vcodec copy” parameters take care of this.

We now have the information to write a ffmpeg commandline which takes audio and video streams from the same file and re-assembles the movie with the audio stream delayed by 0.2 seconds. The resulting synchronized movie is called “synced.avi” and the conversion takes seconds, rather than minutes:

$ ffmpeg -i original.avi -itsoffset 0.2 -i original.avi -map 0:0 -map 1:1  -acodec copy -vcodec copy synced.avi

Cheers, Eric

Watching multimedia in Slackware’s browser

While I was sitting in my chair with little room for escape (I sprained my lower back yesterday when trying to lift something and can barely move) I thought, I need to do something useful while being constrained.

So, I created some new packages and wrote a few blog posts – this one being the last, because sitting in this chair is becoming equally painful.

What packages? You can already find them in my repository or its mirrors. They are dconf (new package altogether) and updates to gnome-mplayer as well as gecko-mediaplayer for which I did not yet have Slackware 13.37 packages.

And why exactly these three?

I was not too satisfied with the state of viewing embedding media clips in a web browser on Slackware. In the past, I used to check out the new movie trailers on Apple.com, In Slackware, that has never been possible I think. The VLC browser plugin crashes more than that it works, and the mplayerplug-in program which uses MPlayer to show the embedded video did not work reliably. I had built the gecko-mediaplayer browser plugin for earlier versions of Slackware – it uses gnome-mplayer to display embeeded media – but that too never worked with the Apple trailers and it had some of the same quirks that mplayerplug-in also had (all too natural since gnome-mplayer is a continuation of the abandoned mplayerplug-in by the same author).

But today, I grabbed the latest sources and built packages. And lo and behold! I can view Apple’s trailers!

Now, why did I mention that dconf package? Well, it turns out that gnome-mplayer which should not depend on any Gnome library, in fact does depend on an “application settings storage backend” – which is Gnome’s gconf… which is not part of Slackware. So, my Slackware package has gconf support disabled, but that only lead me to the next issue – my firefox kept crashing after installing the gecko-mediaplayer & gnome-mplayer packages.

Easy to spot the cause: you only need to run either firefox or gnome-mplayer from the console and you’ll see the following error message:

GLib-GIO-ERROR **: Settings schema ‘apps.gnome-mplayer.preferences’ is not installed
aborting…

That error was fixed by adding the following command to gnome-mplayer’s post-installation script.

glib-compile-schemas /usr/share/glib-2.0/schemas

But we are not there yet. Without a settings backend to store the app’s preferences (your preferences), many of the preference settings that you change do not survive an application restart. Running gnome-mplayer from the commandline shows why:

GLib-GIO-Message: Using the ‘memory’ GSettings backend.  Your settings will not be saved or shared with other applications.

This is where the dconf package enters. Let me quote: “Dconf’s main purpose is to provide a backend to GSettings on platforms that don’t already have configuration storage systems.” It’s a small and efficient program without dependencies, and after installing dconf, our gnome-mplayer no longer complains. All its preferences are now being stored on disk.

Looking back on the weekend which is almost over now, I have performed a number of related plumbing activities: I upgraded my MPlayer package to a recent snapshot – you can grab that and use it to upgrade Slackware’s version of MPlayer with mine. Plus, I have not one, but two graphical front-ends for the mplayer binary: my repository now has the entirely new UMPlayer (universal multimedia player) which has a Qt4 interface, and an updated gnome-mplayer whose GUI is based on the GTK widget set. The choice is yours! But you should definitely give UMPlayer a trial run if you are a regular YouTube visitor – it has an awesome YouTube search & play feature that does not require a webbrowser.

Eric

VLC media player

Are you one of these people who puts Slackware on a computer and then immediately follows up with the installation of another media player than Xine?

Well, I am one of these people. I have been using MPLayer a lot – it builds relatively easily and because it uses Windows codec DLL’s it supports a multitude of audio and video formats. But it is not cross-platform, and it does not give me a happy experience when I use MPlayer to watch DVD’s (the way it handles DVD menus is clumsy at best). And why do I still have to use these Windows codecs when I am running Linux??

The videolan project addresses my issues with MPlayer. Once started as a student project at the French École Centrale Paris it is now an international development effort. The videolan flagship product is VLC (it used to be called the VideoLan Client). VLC is a cross-platform media player which supports many multimedia formats as well as input- and output devices through a plugin architecture. The project went through some tough times when many of the core developers left around two years ago. Ever since, the 0.8.6.x versions have matured so that the current version is stable and great to use. Around the same time, development on a re-designed version of VLC – using Qt4 instead of wxWidgets as it’s GUI – was started.

It is probably due to the fact that the remaining developers plus those who joined the team in the past two years had to figure out VLC’s architecture that it took them so long to produce a version of the 0.9.x series that is stable enough to be useable.

I have had a package for the VLC 0.8.6 series in my repository for some time now, and have been using this alongside MPlayer. I have videos on my hard drive that play fine in MPLayer while VLC will just choke on it, so unfortunately I can not just ditch the MPLayer. The VLC developers tell me that this is a sign of a badly encoded video, and that VLC is not going to try and make the best of it like MPlayer (successfully) does. I think that is just too bad, because this philosophy prevents VLC from being the best media player all around.

Anyway… I had to give that rant a place. Let’s continue with the actual post.

Now that vlc 0.9.1 has been released as source only (the developers do not consider it stable enough to release official binary packages) I decided to upload a Slackware package for it. I have been building betas for many months now, and was not impressed at all by it’s terrible instability, hard lock-ups, and lack of media support. But surpsisingly, the 0.9.1 release shows that an enormous amount of work has been done in the past month, and this version is actually enjoyable. I invite everyone who wants to find out how well it runs, to download my package at one of these locations:

and tell me what you think of it.

Also, you may want to re-build the package in case you already have the Qt4 libraries installed – for instance when you have KDE4.x on your system. The static Qt4 library in the VLC package adds a full 8 MB to it’s size. When you want to make use of the system Qt4 instead in order to slim down the VLC package, you need to run the following commandlines (as root) to download build script and sources, and compile these into a Slackware package:

# lftp -c “open http://slackware.org.uk/ ; cd 3rd-party/alien/restricted_slackbuilds/vlctest/ ; mirror build”

# cd build

# STATIC_QT4=NO sh vlc.SlackBuild

Note: if any of the required source tarballs are missing from your system, the script will download them automatically. You will find the “vlc-0.9.1-i486-1alien.tgz” Slackware package in the /tmp directory after the compilation has finished.

Enjoy! Eric

Newer posts »

© 2024 Alien Pastures

Theme by Anders NorenUp ↑