2009-06-30 14 views

risposta

8

Questo potrebbe essere semplificato, ma ecco un vecchio codice PHP che avevo in giro che dovrebbe fare il trucco. (Aggiungere la posizione a ffmpeg se non è nel tuo percorso)

$output = shell_exec("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("ffmpeg -y -i {$path} -f mjpeg -vframes 1 -ss " . ($total_seconds/2) . " -s {$w}x{$h} {$output_filename}"); 
+0

Grazie, è proprio quello che stavo cercando! –

+0

@Derek Gathright Per favore fornisci i dettagli di base per iniziare a lavorare con ffmpeg. Per favore dai un'occhiata alla mia [domanda] (http://stackoverflow.com/questions/10071408/how-to-get-frames-of-video-file-in-android). –

4

FFmpeg ti aiuta a ottenere il framerate e la lunghezza del video, in modo da poter moltiplicare l'uno con l'altro e dividere per 2 per ottenere il numero del fotogramma centrale.

vale a dire per un video di 30 secondi in esecuzione a 15 fotogrammi al secondo: 30 * 15 = 450/2 = 225, il che significa che è necessario afferrare il 225 ° fotogramma.

0

Questo bash comando funziona come un fascino (testato):

avconv -i 'in.mpg' -vcodec mjpeg -vframes 1 -an -f rawvideo -s 420x300 -ss avconv -i in.mpg 2>&1 | grep Duration | awk '{print $2}' | tr -d , | awk -F ':' '{print ($3+$2*60+$1*3600)/2}' out.jpg 
2

Esempio

Supponendo che si sta utilizzando Linux possono utilizzare per ottenere ffprobe durata, bc calcolare mezzo punto, quindi ffmpeg per rendere il telaio:

eval "$(ffprobe -v error -of flat=s=_ -show_entries format=duration input.mp4)" 
ffmpeg -ss "$(echo "$format_duration/2" | bc)" -i input.mp4 -q:v 2 -frames:v 1 half.jpg 

Questo elimina la necessità di utilizzare awk, tr, grep, sed, ecc

In alternativa, è possibile utilizzare la select filter ed eliminare bc, ma il filtro di selezione può essere lento.

Una nota sulla durata

La durata da ffprobe potrebbe non essere corretto se il file è danneggiato o troncato in modo improprio. La durata può essere confermata decodificando completamente l'ingresso con ffmpeg poi notando la time= nel secondo-a-ultima riga del output della console:

ffmpeg -i input -f null - 
… 
frame= 2600 fps=569 q=-0.0 Lsize=N/A time=00:01:48.50 bitrate=N/A 
video:244kB audio:20344kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: unknown 
+0

Su Windows/Cygwin ho dovuto eseguire una brutta elaborazione del testo kludge dell'output di eval/ffprobe per eliminare una nuova riga di windows dalla fine di $ format_duration: 'eval" $ (ffprobe -v error -of flat = s = _ -show_entries format = durata tmp.mp4) "' ' echo $ format_duration> tmp.txt' ' eco/2 >> tmp.txt' 'dos2unix tmp.txt' format_duration =' 'tr -d '\ n'

+0

C'è una serie di apici inversi che circondano l'assegnazione della variabile dopo format_duration nell'ultima parte del mio commento (che viene eliminato qui dall'analisi del markdown). –

Problemi correlati