Video+Audio aufnehmen unter Linux
Montag, 16. Januar 2006, 15:45 UhrDa habe ich ja nun eine Webcam, die sogar unter Linux (Ubuntu) läuft. Naiv wie ich manchmal bin, dachte ich mir, dass es doch eigentlich ganz einfach sein muss, damit ein Filmchen aufzunehmen. “Bestimmt gibt’s da schon jede Menge Programme für”, dachte ich mir. Naja.
Also, es gibt camorama. Das zeigt auch wunderbar an, was die Kamera gerade sieht. Allerdings kann man damit kein Video aufnehmen, sondern nur JPG-Schnappschüsse.
Ok, nächster Versuch: Cupid. Da sieht zumindest schonmal die Beschreibung gut aus. Leider hat es nicht nur eine ziemlich unbenutzbare Benutzungsoberfläche (man sollte sich schon mit Videocodecs auskennen, um da durchzublicken), sondern es tut auch nicht mit meiner Kamera.
Nachdem das also alles nichts war, habe ich mich an einen Eintrag neulich auf planet debian erinnert, in dem Ross Burton genau so ein Tool sucht und mal so eben nebenbei erwähnt, dass eine GStreamer-Pipeline es ja vermutlich tun würde. Hm. Was auch immer das ist.
GStreamer ist ein Video- und Audio-Framework, das mich mit wirklich guter Doku überrascht hat. Eine GStreamer-Pipeline ist quasi ein Container für Dinge, die etwas mit Audio- und Videodaten machen: aufnehmen, enkodieren, in eine Datei schreiben, aus einer Datei lesen etc. In einer Pipeline hängt man diese Dinge aneinander, und dann fließen die Daten da halt durch. Man muss dann “nur” noch rausfinden, was man wie hintereinanderhängen muss, aber dafür gibt es sogar einen graphischen Editor (der aber anscheinend nur mit den einfachsten Fällen klarkommt). Ich hab dann doch eine ganze Weile basteln müssen, bis ich’s hingekriegt hab. Jetzt läuft es soweit, allerdings habe ich noch einige Probleme mit der Bildqualität (vor allem mit der Helligkeit und dem Kontrast).
Hier ist eine Pipeline, um Video und Audio aufzunehmen und in eine Ogg/Theora-Datei zu schreiben:
$ gst-launch oggmux name=mux ! filesink location=output.ogg { v4lsrc ! tee name=t ! {queue ! ffmpegcolorspace ! theoraenc ! queue ! mux. } } { alsasrc ! audioconvert ! rawvorbisenc ! queue ! mux. } { t. ! queue ! ffmpegcolorspace ! sdlvideosink }
Und hier ist die Erklärung dazu.
ist das Kommandozeilen-Tool, um eine GStreamer-Pipeline aufzurufen. Dann kommen die Dinge in der Pipeline, jeweils mit ! getrennt (die Ventile quasi). Dinge können mit {} zusammengefasst werden, und zwar laufen mehrere {}s parallel (Threads). Aber fangen wir vorn an.
oggmux name=mux ! filesink location=output.ogg
— eine Ogg/Theora-Datei ist ein Container für (zumindest in diesem Fall) eine Audio- und eine Videodatei. Der oggmux bastelt diese zwei Dateien zu einer einzelnen zusammen. Außerdem geben wir dem oggmux hier einen Namen, nämlich mux. Dann (das ist das !) schicken wir diese Datei zum filesink, der schreibt die Datei auf die Festplatte und gibt ihr den Namen
.
So, wo kriegt unser oggmux namens mux denn nun die Audio- und die Videodatei her, die er zusammenbasteln soll? Das kommt jetzt. An den {}s kann man sehen, dass 3 Dinge gleichzeitig ablaufen, weil dreimal {…} hintereinander kommt. Und zwar ist das:
{ v4lsrc ! tee name=t ! {queue ! ffmpegcolorspace ! theoraenc ! queue ! mux. } }
v4lsrc redet mit der Kamera, und zwar über die video4linux-Schnittstelle. Das, was die Kamera rauswirft, schicken wir in ein tee — das ist wie eine Weiche. Die hat auch einen Namen, nämlich t. Eine Spur, die aus der Weiche rausgeht, sehen wir hier sofort: Schick die Videodaten durch eine Farbraum-Transformation (ffmpegcolorspace), dann durch einen Theora-Enkodierer (der macht aus den rohen Videodaten etwas zivilisiertere Theora-Daten) und dann in unseren mux von oben. Die “queue”s dazwischen sind Datenpuffer und sorgen dafür, dass nichts überläuft (weil sonst brennt das an, und das wollen wir nicht).
{ alsasrc ! audioconvert ! rawvorbisenc ! queue ! mux. }
Hier ist die Audiospur: alsasrc spricht mit der Soundkarte, audioconvert bastelt noch ein bisschen dran rum, und rawvorbisenc ist das Äquivalent zu theoraenc. Genauso wie die Videodaten werden auch die Audiodaten am Ende an unseren mux gesendet.
Den dritten Teil, der gleichzeitig abläuft, hab ich bisher noch gar nicht erwähnt. Wenn man ein Filmchen aufnimmt, möchte man eigentlich schon direkt sehen können, was man da aufnimmt. Und deswegen zweigen wir bei der Videospur mit der Weiche namens t noch einen Zweig ab:
–das, was aus t rauskommt, wird wieder durch eine Farbraumtransformation geschickt und dann auf dem Bildschirm angezeigt.
Disclaimer: Das funktioniert so für mich. Sehr wahrscheinlich kann es auf anderen Rechnern damit Probleme geben. Und vermutlich kann man das auch viel cleverer hinkriegen. Aber “erstmal schonmal” tut es…

gst-launch oggmux name=mux ! filesink location=output.ogg { v4lsrc ! tee name=t ! {queue ! ffmpegcolorspace ! theoraenc ! queue ! mux. } } { alsasrc ! audioconvert ! rawvorbisenc ! queue ! mux. } { t. ! queue ! ffmpegcolorspace ! sdlvideosink }
can provide gst programe source code?