Converti in batch H.265 mkv in H.264 con ffmpeg per rendere i file compatibili per la ricodifica


31

Ho file codificati H.265 che sono così ricchi di risorse che non funzionano bene e il mio software di conversione (mencoder) non (al momento) supporta il formato H.265. Posso convertirli in H.264 in un file batch della riga di comando per convertire rapidamente i file per la ricompressione usando Devede / OGMrip? Durante la ricerca di questo sito non l'ho trovato discusso, quindi posterò ciò che ritengo sia una domanda utile e rispondo alla domanda.

Risposte:


37

Sì, usando ffmpeg.

Apri un terminale e indirizzalo alla directory contenente i file codificati H.265, supponendo che tu abbia ffmpeginstallato e che le librerie appropriate siano installate e supponendo che siano in formato MKV, copia e incolla quanto segue nella finestra del terminale.

INPUT="$1"
for i in *.mkv ; do
    ffmpeg -i "$i" -bsf:v h264_mp4toannexb -sn -map 0:0 -map 0:1 -vcodec libx264 "$i.ts"
    mv "$i.ts" "$i.mpg"
    sleep 3
done

Ecco qui. Questo verrà convertito in h.264 in un contenitore MPG nella stessa directory.

Spiegazione delle opzioni di comando:

  • for i in *.mkv ; do ... done

    Questo imposta tutti i file .mkv in una directory da includere nel processo batch. Questo può essere modificato per adattarsi all'estensione del contenitore dei file che si desidera elaborare.

  • ffmpeg -i "$i" Esegue il programma ffmpeg e richiede l'elaborazione dei file.

    • -bsf:v attiva il filtro del flusso di bit video da utilizzare.

    • h264_mp4toannexb - È il filtro del flusso di bit che è attivato.

      Convertire un bitstream H.264 dalla modalità con prefisso di lunghezza per avviare la modalità con prefisso (come definito nell'Allegato B della specifica ITU-T H.264).

      Ciò è richiesto da alcuni formati di streaming, in genere il formato del flusso di trasporto MPEG-2 ( mpegts) che elabora MKV h.264 (attualmente) lo richiede, se non è incluso, nella finestra del terminale verrà visualizzato un errore che indica di utilizzarlo.

    • -sn interrompe lo streaming dei flussi di sottotitoli (per coloro che non vogliono i sottotitoli nel loro video) Questo è facoltativo e può essere rimosso.

    • -map 0:0 -map 0:1Indica a ffmpeg di elaborare solo i primi due flussi del file ( 0:0è il flusso video, 0:1è il primo flusso audio del file). Questo fa due cose, elimina i flussi audio in eccesso, di solito il primo flusso audio è l'inglese ma non sempre. Altri stream come i sottotitoli incorporati vengono rimossi riducendo la dimensione del file. Questa è anche una stringa opzionale. È possibile utilizzare ffprobeper visualizzare i flussi disponibili nel file. -mapè facoltativo e può essere scartato dal comando.

    • -vcodec libx264 Questo dice a ffmpeg di codificare l'output su H.264

    • "$i.ts" Salva l'output nel formato .ts, questo è utile per non sovrascrivere i tuoi file sorgente.

  • mv "$i.ts" "$i.mpg"Converte l'estensione del file in MPG nella stessa directory. Questo può essere impostato per inviarlo a qualsiasi directory che ti piace.

  • sleep 3 - consente al processo di arrestarsi dando a ffmpeg il tempo di mettere in coda il file successivo


3
Eccellente! Ora possiamo eliminare i commenti sotto la domanda. Direi che sleep 3non è necessario (ma è utile per terminare il loop) ed INPUT=$1è insignificante poiché lo si esegue direttamente in una shell interattiva.
Muru,

11
Prendi in considerazione lo streaming copiando l'audio -c:a copyinvece di ricodificarlo. Inoltre, 0:0potrebbe non riferirsi sempre al video e 0:1potrebbe non riferirsi sempre all'audio. Puoi utilizzare un identificatore di flusso per evitare potenziali problemi: -map 0:v -map 0:ase vuoi tutti i flussi video e audio dall'ingresso 0 o -map 0:v:0 -map 0:a:0se vuoi solo i primi flussi video e audio dall'ingresso 0. Se vuoi solo il flusso audio inglese: -map 0:m:language:eng(supponendolo è etichettato).
Llogan,

1
@LordNeckbeard Voterò per te per scrivere una risposta completa.
Fran Marzoa,

1
@Fran Non ho notato che c'erano così tanti voti su quel commento. Ho aggiunto una risposta usando metodi più semplici, meno soggetti a errori e più efficienti.
llogan,

1
Ci andrei totalmente semplicemente ffmpeg -i $INPUT -vcodec h264 -acodec copy $OUTPUT. Qualcosa che uso tutti i giorni e posso effettivamente memorizzare al contrario di quella raffica di bandiere insignificanti per cui ogni risposta ffmpeg è così famigerata.
Ben Sinclair,

20

Conversione in lotti di H.265 in H.264

Questi esempi sono stati scritti di recente ffmpeg. Salva qualche problema e scarica una versione recente. Quindi inserire il ffmpegbinario ~/bino /usr/local/bin(potrebbe essere necessario disconnettersi quindi accedere per essere notato).

Uscita Matroska

mkdir h264vids
for f in *.mp4; do ffmpeg -i "$f" -map 0 -c copy -c:v libx264 -crf 23 -preset medium h264vids/"${f%.*}.mkv"; done
  • Questo esempio verrà generato in una directory denominata h264vids.

  • Questo esempio presuppone che siano i tuoi input .mp4. In caso contrario, cambia l' .mp4istanza nell'esempio con il tuo tipo di file di input, oppure usa semplicemente l'avido *da solo.

  • Regola -crfper qualità e -presetper codificare velocità / efficienza. O semplicemente rimuovi queste opzioni e usa le impostazioni predefinite che sono abbastanza buone e dovrebbero bastare per la maggior parte (l'esempio sta usando i valori predefiniti per queste opzioni). Vedi FFmpeg Wiki: H.264 per maggiori informazioni su queste opzioni.

Uscita MP4

Questo è un po 'più complicato. Ciò eseguirà la codifica condizionale a seconda che l'audio in ingresso sia AAC o meno. Se l'audio in ingresso è AAC, l'audio verrà copiato (ri-miscelato) così com'è e si eviterà inutilmente la ricodifica. Se l'audio in ingresso non è AAC, verrà ricodificato in AAC.

Ecco un semplice script che dimostra come farlo usando ffprobee ffmpeg. Copiarlo e salvarlo nella directory contenente i video da convertire, autorizzarlo con l'esecuzione chmod +x yourscriptname, quindi eseguirlo ./yourscriptname.

#!/bin/bash

mkdir h264vids

for f in *.mkv
do
  audioformat=$(ffprobe -loglevel error -select_streams a:0 -show_entries stream=codec_name -of default=nw=1:nk=1 "$f")
  if [ "$audioformat" = "aac" ]; then
    ffmpeg -i "$f" -c:v libx264 -crf 23 -preset medium -c:a copy -movflags +faststart h264vids/"${f%.*}.mp4"
  else
    ffmpeg -i "$f" -c:v libx264 -crf 23 -preset medium -c:a aac -movflags +faststart h264vids/"${f%.*}.mp4"
  fi
done
  • Questo esempio verrà generato in una directory denominata h264vids.

  • Questo esempio presuppone che siano i tuoi input .mkv. In caso contrario, cambia l' .mkvistanza nell'esempio con il tuo tipo di file di input, oppure usa semplicemente l'avido *da solo.

  • Vedi la nota sopra riguardante -crfe -preset.

  • Puoi mettere in pausa la codifica con ctrl+ ze riprendere con fg.


1

Considerando le risposte precedenti, ho pensato a quanto segue:

for file in *265.mkv; do nice -n19 ffmpeg -i $file -c copy -c:v libx264 ${file/%265.mkv/264.mkv}; done

Ciò presuppone che i file abbiano sempre un nome che termina con 265.mkv. Questo finale verrà sostituito con 264.mkv.

Se la denominazione dei file è diversa, è necessario adattare il comando di conseguenza.


Questa è un'ottima risposta che penso debba essere votata più in alto a causa del suo uso rilevante della sostituzione dei parametri di Bash.
Sysinfo.io
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.