ffmpeg 输出视频相关信息

一、前言

容器格式 V.S. 编解码格式

容器格式(container: avi,mp4,wmv,mpeg\mpg)

编解码格式(codec: mpeg4、h263、h264)

参考:

https://www.jianshu.com/p/f2f82a97adb2

https://blog.csdn.net/qiurisuixiang/article/details/54943657

更深入的了解可以参见博客:https://blog.csdn.net/class_brick/article/details/82893967

二、FFmpeg简介

“A complete, cross-platform solution to record, convert and stream audio and video.” 可以实现视频和音频的转码、裁剪、合并等。

安装:

sudo apt-get install ffmpeg

如下依赖项自动安装:

The following additional packages will be installed:
  libavdevice-ffmpeg56 libavfilter-ffmpeg5 libbs2b0 libflite1 libopenal-data
  libopenal1 libsodium18 libvdpau1 libzmq5 mesa-vdpau-drivers vdpau-driver-all
Suggested packages:
  ffmpeg-doc libvdpau-va-gl1 nvidia-vdpau-driver
  nvidia-legacy-340xx-vdpau-driver
The following NEW packages will be installed:
  ffmpeg libavdevice-ffmpeg56 libavfilter-ffmpeg5 libbs2b0 libflite1
  libopenal-data libopenal1 libsodium18 libvdpau1 libzmq5 mesa-vdpau-drivers
  vdpau-driver-all
0 upgraded, 12 newly installed, 0 to remove and 30 not upgraded.
Need to get 17.3 MB of archives.

三、查询视频信息

3.1如果容器中储存了视频的相关信息,可以快速通过容器查询:

ffprobe -show_streams -i video.h264
ffprobe -v error -show_format -show_streams video.h264

3.2如果容器中没有存储相关信息,只能读入视频计算相关信息:

ffprobe -v error -count_frames -select_streams v:0 -show_entries stream=nb_read_frames -of default=nokey=1:noprint_wrappers=1 video.h264

或者

ffmpeg -i video.h264 -map 0:v:0 -c copy -f null -

-c/-codec copy,保留原始视频编码格式,不重新做视频编解码,因此非常快;

 -map [-]input_file_id[:stream_specifier][,sync_file_id[:stream_specifier]],因此,-map 0:v:0表示第一个输入文件的第一个video stream;

 -f fmt (input/output). Force input or output file format.

参考:https://stackoverflow.com/questions/2017843/fetch-frame-count-with-ffmpeg

四、转码

4.1 只转换容器容器格式,不改变编解码格式

Streamcopy: input file _demuxer_> encoded data packets_muxer__ > outputfile

ffmpeg -i input.avi -codec copy out.mp4

-c/-codec copy,保留原始视频编码格式,不重新做视频编解码,因此非常快;

注意:如果未加-codec copy,即ffmpeg -i input.avi out.mp4,则使用默认视频编解码器进行encoder和decoder,因此速度比较慢,属于同时转换编解码格式&容器格式的转换。

4.2 同时转换编解码格式&容器格式的转换

Transcoding process:input file _demuxer_> encoded data packets _decoder__>decoded frames _encoder_> encoded data packets __muxer__ > outputfile :

ffmpeg -i input.avi -vcodec h264 out.mp4

-i 表示输入视频选项;

-vcodec指定了视频编码格式为h264

五、改变播放速度或码率

改变帧率(播放速度):

ffmpeg -r f_output -i input output

-r f_output 表示帧率,例如 -r 20将output视频的帧率设为20fps。ouput和input视频的帧总数不变,视频时长根据修改的帧率做调整,即t_output=t_input*f_input/f_output.

改变码流:

ffmpeg -i input -r f_output output

output视频总时长与input视频相同,output视频的码流设置成-r f_output。

六、剪切

按时间剪切:

ffmpeg -i video.h264 -ss 00:00:50.0 -c copy -t 00:00:20.0 video_copy.h264

从50s开始,向后剪切20s。

-c[:stream_specifier] codec. Select an encoder (when used before an output file) or a decoder (when used before an input file) for one or more streams.  -c:v 选中video stream, -c:a选中audio stream。-c 表示选中所有stream。

注意:如果容器中不包含时间信息,则无法通过此工具裁剪,因为ffmpeg不支持根据帧数剪切,只支持基于时间剪切。

参考:https://blog.csdn.net/angus_17/article/details/80696989

按帧剪切:

Filtering: input file _demuxer_> encoded data packets _decoder_>decoded frames__simple filtergraph  >filtered frames _encoder_> encoded data packets __muxer__ > outputfile

ffmpeg -i input.h264 -vf "select=between(n\,20\,200)*not(mod(n\,2))" -vsync 0 ./cut_result.h264  

其中,Simple filtergraphs are configured with the per-stream -filter option (with -vf and -af aliases for video and audio respectively). 使用filter进入视频先解码,再编码的模式,则不能再使用stream copy。

-vf: filtergraph. Create the filtergraph specified by filtergraph and use it to filter the stream. This is an alias for "-filter:v".

select filter中between(n\,20\,200)*not(mod(n\,1))中 between内的参数为开始帧和结束帧,not(mod n\,2)中的参数为间隔数

关于filters的详细文档可以参见:http://ffmpeg.org/ffmpeg-filters.html

PS:

 -vsync 控制时间戳
Video sync method.  For compatibility reasons old values can be specified as numbers.  Newly added values will have to be specified as strings always.

0, passthrough.  Each frame is passed with its timestamp from the demuxer to the muxer.

1, cfr. Frames will be duplicated and dropped to achieve exactly the requested constant frame rate.

2, vfr. Frames are passed through with their timestamp or dropped so as to prevent 2 frames from having the same timestamp.

drop. As passthrough but destroys all timestamps, making the muxer generate fresh timestamps based on frame-rate.

-1, auto. Chooses between 1 and 2 depending on muxer capabilities. This is the default method.

七、合并

建立filelist.txt文件,里面写入需要合并(时间上)的视频信息:

file '1.h264'
file '2.h264'
file '3.h264'
file '4.h264'

运行命令:

ffmpeg -f concat -i filelist.txt -c copy output.h264

八、拼接

将多个视频在空间上拼合成多个窗口,播放时同时显示。
垂直拼接:

ffmpeg -i input0.avi -i input1.avi -filter_complex "[0:v]scale=1600:-1[v0];[v0][1:v]vstack=inputs=2" output.avi

选中[0:v]第一个视频的video stream,

scale=1600:-1, scale为缩放滤镜,宽度为1600,-1表示输出时保持原始的宽高比。

水平拼接:

ffmpeg   -i input0.avi  -i input1.avi   -filter_complex '[0:v]pad=iw*2:ih[int];[int][1:v]overlay=W/2:0[vid]'   -map [vid]   -c:v libx264   -crf 23   -preset veryfast   output.avi

PS:

 -filter[:stream_specifier] filtergraph (output,per-stream). 单进->单出。例如:单一视频文件的格式转换。Create the filtergraph specified by filtergraph and use it to filter the stream.  filtergraph is a description of the filtergraph to apply to the stream, and must have a single input and a single output of the same type of the stream.

-filter_complex: filtergraph (global). 多进->单出 or 单进->多出 or 多进->多出。例如,多个视频拼合一个文件。Define a complex filtergraph, i.e. one with arbitrary number of inputs and/or outputs.

关于filter的详细文档可以参见:http://ffmpeg.org/ffmpeg-filters.html

参考:https://stackoverflow.com/questions/11552565/vertically-or-horizontally-stack-several-videos-using-ffmpeg

猜你喜欢

转载自blog.csdn.net/Cxiazaiyu/article/details/96965916