Cómo concatenar clips del mismo video con ffmpeg

15

Tengo un video largo con diferentes escenas. Quiero extraer y concatenar 2 escenas del video (que no comienzan en un cuadro I) usando ffmpeg 2.1.4.

Para argumentar, digamos que quiero 5 segundos de 01:00 a 02:00.

Puedo hacer esto:

ffmpeg -ss 01:00 -i in.mkv -ss 02:00 -i in.mkv -filter_complex "
  [0:v]select='lt(t,5)'[v0];
  [0:a]aselect='lt(t,5)'[a0];
  [v0][a0][1:v][1:a]concat=n=2:v=1:a=1
" -c:a libvorbis -t 10 out.mkv

Eso me da la película que quiero, pero seleccionar en realidad obliga a ffmpeg a decodificar el resto de la película. Entonces, ¿cómo le digo que trunca la primera película en lugar de decodificarla?

Preferiría hacer esto con un filtro complejo ffmpeg, si es posible. Sé que -tprimero puedo usar para recodificar películas separadas, pero el paso de codificación adicional es muy lento en mi caso y también pierde una buena cantidad de calidad para este video.

Parece que no puedo encontrar un filtro que trunca la longitud de un vapor. ¿Hay nodos de filtro que corresponden a los parámetros -to -ss?

fregado
fuente

Respuestas:

16

filtro de concat

Este método es mejor si necesita realizar un filtrado adicional:

Utilice los trim, atrim, setpts, asetpts, y concatfiltros:

ffmpeg -i input -filter_complex \
"[0:v]trim=60:65,setpts=PTS-STARTPTS[v0]; \
 [0:a]atrim=60:65,asetpts=PTS-STARTPTS[a0]; \
 [0:v]trim=120:125,setpts=PTS-STARTPTS[v1];
 [0:a]atrim=120:125,asetpts=PTS-STARTPTS[a1]; \
 [v0][a0][v1][a1]concat=n=2:v=1:a=1[out]" \
-map "[out]" output.mkv
  • setptsy asetptsevitará una salida desigual debido a problemas de marca de tiempo de presentación.

  • Asegúrate de usar una versión reciente. Consulte la página de descarga de FFmpeg para obtener enlaces a compilaciones para Windows, OS X y Linux.


demuxer concat

Otro método es crear los segmentos individualmente y copiarlos en secuencia en lugar de volver a codificarlos (para ahorrar tiempo y calidad), y unirlos con el demuxer concat .

$ ffmpeg -ss 60 -i input -t 5 -codec copy clip1.mkv
$ ffmpeg -ss 120 -i input -t 5 -codec copy clip2.mkv
$ echo "file 'clip1.mkv'" > concat.txt
$ echo "file 'clip2.mkv'" >> concat.txt
$ ffmpeg -f concat -i concat.txt -codec copy output.mkv
lema
fuente
2
Ah gracias. recortar es lo que me faltaba. Sin embargo, lleva mucho tiempo llegar al desplazamiento de tiempo que especifico, como si decodificara todo. Además, a parte de la salida le faltaba audio. Para solucionarlo, especifiqué la misma entrada varias veces con -ss, luego uso trim para truncar el video. No necesita setpts en ese caso, ya que ss establece pts en 0. Eso pareció funcionar y no tuvo pausas aleatorias extrañas durante la codificación. En cuanto a copiar secuencias, lo intenté antes. Comienza en el cuadro I anterior, por lo que obtienes una parte diferente de la película que la que querías.
fregado el
¿Podría responder mi pregunta? Es similar a esta. video.stackexchange.com/questions/18247/…
Eftekhari
Curiosamente -filter_complexfunciona, pero los concatarchivos no, es decir, el primer video se ve bien, pero la calidad del segundo es horrible. Tenga en cuenta que copié estos comandos exactamente para ambos (excepto para el archivo de entrada).
bobmarksie
7

Esto debería funcionar más rápido ...

ffmpeg -ss 1:00 -t 5 -i in.mkv -ss 2:00 -t 5 -i in.mkv \
  -filter_complex "[0][1]concat=n=2:v=1:a=1" \ 
  out.mkv

No es necesario especificar -t en la salida. No es necesario dividir el audio y el video antes del concat.

William Frantz
fuente
1
Esto utiliza el filtro concat que requerirá una nueva codificación. Esto puede o no ser deseado por el usuario.
llogan