![So erstellen Sie mit FFmpeg ein Miniaturbild aus der Mitte eines Videos](https://rvso.com/image/1330228/So%20erstellen%20Sie%20mit%20FFmpeg%20ein%20Miniaturbild%20aus%20der%20Mitte%20eines%20Videos.png)
Gibt es eine Möglichkeit, in FFmpeg ein Video-Thumbnail zu erfassen?
Ich möchte das mittlere Bild als Video nehmen und es als Miniaturbild verwenden. Die Videodauer ist unbekannt.
Auch die Möglichkeit, die Abmessungen des Miniaturbilds festzulegen, wäre hilfreich.
Antwort1
Einzeiliger Befehl:
ffmpeg -i input.mp4 -vcodec mjpeg -vframes 1 -an -f rawvideo -ss `ffmpeg -i input.mp4 2>&1 | grep Duration | awk '{print $2}' | tr -d , | awk -F ':' '{print ($3+$2*60+$1*3600)/2}'` output.jpg
Der Unterbefehl ermittelt die Gesamtdauer des Eingangsvideos
ffmpeg -i input.mp4 2>&1 | grep Duration | awk '{print $2}' | tr -d ,
Und leiten Sie es weiter, awk
um die Dauer/2 wie folgt zu berechnen
echo '00:01:30.000' | awk -F ':' '{print ($3+$2*60+$1*3600)/2}'
Geben Sie dies also innerhalb von Sekunden in die Option -ss ein, und fertig.
Wenn Sie die Größe angeben möchten, fügen Sie die Option -s wie WxH hinzu, wobei W und H ganzzahlige Werte sind (z. B. -s 800x600 oder -s svga), oder lesen Sie die Manpage von ffmpeg, um andere verfügbare Optionen oder Formate anzuzeigen.
Antwort2
Hier ist eine Methode, die Folgendes verwendet:
ffprobe
um die Dauer zu erhaltenbc
die halbe Dauer zu berechnenffmpeg
um das Miniaturbild zu erstellen
Beispiel:
input=input.mp4; ffmpeg -ss "$(bc -l <<< "$(ffprobe -loglevel error -of csv=p=0 -show_entries format=duration "$input")*0.5")" -i "$input" -frames:v 1 half.png
Antwort3
Verwenden Sie zunächst immer die neueste Version von FFmpeg.
Wenn Sie Zugriff auf PHP haben, wird Ihre Frage auf Stack Overflow perfekt beantwortet:FFMpeg verwenden, um das mittlere Bild eines Videos zu erhalten?
$output = shell_exec("/usr/local/bin/ffmpeg -i {$path}");
preg_match('/Duration: ([0-9]{2}):([0-9]{2}):([^ ,])+/', $output, $matches);
$time = str_replace("Duration: ", "", $matches[0]);
$time_breakdown = explode(":", $time);
$total_seconds = round(($time_breakdown[0]*60*60) + ($time_breakdown[1]*60) + $time_breakdown[2]);
shell_exec("/usr/local/bin/ffmpeg -y -i {$path} -f mjpeg -vframes 1 -ss " . ($total_seconds / 2) . " -s {$w}x{$h} {$output_filename}";
Es extrahiert lediglich die Dauer aus der FFmpeg-Ausgabe und verwendet diese, um den Zeitcode des mittleren Frames zu bestimmen.
Das lässt sich problemlos an andere Shells anpassen und einfach in den folgenden Befehl einfügen, wobei der mittlere Frame ungefähr bei 534
Sekunden steht:
ffmpeg -y -i input.mp4 -f mjpeg -vframes 1 -ss 534 thumbnail.jpg
Du kannst die Größe jederzeit mit -s 480x320
oder ähnlich ändern, je nachdem wie groß du es haben möchtest, irgendwo nach der -i input.mp4
Option eingefügt.
Die obige Lösung ist ein wenig ungenau. Sie erhalten zwar sofort ein Ergebnis, können aber nicht angeben, welches Bild Sie möchten. Wenn Sie bereits genau wissen, welches Bild Sie extrahieren möchten, verwenden Sie den select
Filter, z. B. mit der Bildnummer 12345
:
ffmpeg -i input.mp4 -filter:v select="eq(n\,12345)" -vframes 1 thumbnail.jpg
Beachten Sie, dass dieser Befehl eine Weile dauern kann, da er zum angegebenen Frame springen muss, bevor er ihn extrahieren kann.
Antwort4
Die einfache Lösung ist:
ffmpeg -i l1.mp4 -ss 00:00:14.435 -vframes 1 out.png