06.11.2010

H.264 Videos für Android mit ffmpeg erstellen

Einleitung

Ffmpeg ist ein tolles Tool um Videos zu konvertieren. Um allerdings h.264 Videos zu encoden, die auch auf Android abspielbar sein sollen, muss man einige Sachen beachten. Das folgende Mini-Tutorial soll zeigen, wie das geht. Mit wahrscheinlich einigen wenigen Änderungen sollten die umgewandelten Videos auch für iPhone und PSP abspielbar sein.

Hinweis: Mir ist bekannt, dass es auch benutzerfreundliche Tools mit grafischer Oberfläche wie z.B. Handbrake gibt. Trotzdem kann es nützlich sein h.264 Videos mit einem Kommandozeilenbefehl konvertieren zu können (z.B. Automatisierung mit Skript). Außerdem benutzen viele dieser Tools im Hintergrund ebenfalls ffmpeg.

Der Befehl in Kürze

$ ffmpeg -i INFILE -acodec libfaac -vcodec libx264 -b 1000k \
-vpre ultrafast -vpre baseline -ab 128k OUT.mp4

oder besser, wenn einem die Qualität wichtiger ist als eine bestimmte Dateigröße:

$ ffmpeg -i INFILE -acodec libfaac -vcodec libx264  \
-vpre faster -vpre baseline -ab 128k -crf 25 OUT.mp4

INFILE muss natürlich mit dem richtigen Dateinamen ersetzt werden.

Systemumgebung

Das Mini-Tutorial bezieht sich auf folgende Systemumgebung:

  • Ubuntu Linux 10.4 LTS
  • ffmpeg 0.6 (selbst kompiliert)
  • x264 core:100 r1659 57b2e56 (0.100.1659 57b2e56) (selbst kompiliert)

Die verwendete Versionen sind schon etwas älter. Es sollte allerdings keine Probleme mit den aktuelleren Versionen geben.

Vorbereitung

Als erstes sollte man überprüfen, ob ffmpeg mit h264 Unterstützung kompiliert wurde. Dies kann man schnell nachgucken, wenn man folgendes in der Shell eingibt:

$ ffmpeg -version

Falls man unter configuration: --enable-libx264 findet, so wurde ffmpeg mit h264 Unterstützung kompiliert.

Seit Ubuntu Linux 9.10 ist dies allerdings nicht mehr der Fall. Darum müssen selbst kompilierte Versionen verwendet werden. Eine gute Anleitung findet man bei ubuntuusers im Wiki .

Erklärung des Befehls

Oben wurden bereits die Kommandzeilenbefehle genannt. Nun folgt die Erklärung. Das erste Argument -i gibt die Input-Datei an, -acodec den Audiocodec, -vcodec den Videocodec, -b die Videobitrate und -ab die Audiobitrate. Soweit alles klar und logisch.

Mit der Option vpre teilt man ffmpeg mit, was für ein Preset es verwenden sollte. Welche Presets es gibt findet man unter /usr/local/share/ffmpeg oder /usr/share/ffmpeg. Mit dem Preset ultrafast wandelt man z.B. das Video sehr schnell um, dafür muss man allerdings Abstriche bei der Dateigröße in Kauf nehmen. Andere Presets sind z.B.:

  • superfast
  • faster
  • fast
  • normal
  • slow
  • slower
  • veryslow
  • ...

Die zweite Presetoption baseline ist wichtig. Der H.264 Codec hat unterschiedliche Profile für verschiedene Endgeräte. Laut der Ubuntudokumentation AndroidVideoEncoding unterstützt das G1 (und anscheinend auch andere Androidsysteme oder andere mobilen Geräte) nur das Baselineprofil. Wenn ein Video kein Bild zeigt sondern man nur den Ton hört, obwohl es mit den H.264 Codec kodiert wurde, ist dies z.B. ein Anzeichen dafür, dass nicht das Baselineprofil verwendet wurde.

Beim zweiten Befehl wurde statt der Bitrate die Option crf (constant rate factor) angegeben. Generell gilt je niedriger der Wert desto besser die Qualität.

Wer mehr Details über crf wissen möchte, dem kann ich den Artikel von der Webseite encodingwissen.de empfehlen. Auf dieser Webseite gibt es sehr viel Hintergrundwissen zum Thema Encoding. Es werden ganz gut die Konzepte erklärt u.a. von h.264, Xvid und DivX.

Ebenfalls empfehlenswert und auch pragmatischer ist der englischer Blogeintrag von Robert Swain.

Tipps

  • Wenn man schnell überprüfen möchte, ob die eingegebenen Parameter in Ordnung sind, hilft die Option -t 90. Damit werden nur 90 Sekunden des Quellvideos kodiert.
  • Bei Kinofilmen gibt es oft die horizontalen schwarzen Balken. Diese stören und machen das Bild kleiner. Abhilfe schafft dort die Option -croptop X und -cropbottom Y, wobei X und Y natürlich mit Zahlen ersetzt werden sollten. Diese geben an wieviele Pixel "abgeschnitten" werden sollen.

Offtopic

Beim Schreiben dieses Mini-Tutorial habe ich mich gefragt, wofür eigentlich ffmpeg steht :) . Wer sich dieselbe Frage gestellt hat hier die Antwort: Laut der Developer-Mailingliste steht ff für fast forward.

1 Kommentar:

  1. ich wollte zwar gar nicht für ein android transcodieren, aber hat mir trotzdem weitergeholfen. vielen dank! :)

    AntwortenLöschen