关于FFmpeg对手机里拍摄的视频进行转码时角度问题的处理

手机在拍摄视频时,会记录下手机拍摄时的角度,这个角度会保存到视频文件里,使用ffprobe查看时,会看到rotate值,这值代表将手机顺时针旋转了rotate度进行拍摄的,下面是手机角度示意图(拍摄时,被拍物体是正的)。

//用ffprobe查看视频信息
ffprobe -print_format  json -select_streams v -show_format -show_streams -i "M1.mp4"

关于FFmpeg对手机里拍摄的视频进行转码时角度问题的处理_第1张图片

现在很多视频播放器是会判断rotate的值,比如使用fflay进行播放时,这四个视频里的 糖盒 都是正的(向上),如果使用没有判断rotate值功能的播放器(系统自带的Windows Media Player),则视频角度跟上面表格中角度是一样。

//直播用ffmpeg自带的播放器进行播放
ffplay M1.mp4

如果使用FFmpeg进行转码而不使用任何旋转相关参数时,FFmpeg会根据rotate的值对视频进行旋转,以保证在所有播放器里播放时是正的(糖盒向上)的,使用的命令及产生的结果如下:

//用ffmpeg进行转换时,不使用旋转相关参数
ffmpeg -y -i " M1.mp4" -vcodec libx264 –b:v 1024000  -s 320x180 -acodec copy " M1_cp.mp4"

关于FFmpeg对手机里拍摄的视频进行转码时角度问题的处理_第2张图片
对比上面的图片可以看出,FFmpeg默认根据rotate的值,将视频的旋转成正的(糖盒向上)了,并且,从参数里删除的rotate值(可以认为rotate值为0),对于M2_cp.mp4和M4_cp.mp4,会将原宽高(1280*720)转换成宽高(720*1280),不过用ffprobe查看视频信息时,里面的值仍保持(width=1280,height=720)。在电脑上播放没问题,在手机上播放(特别是系统自带的视频播放器)时,将会视频以手机角度1进行播放,画面会拉变形了,为了保证转换后,生成的视频角度与原视频角度一致并保留rotate的值,则需要使用以下命令进行转换。

//处理视频M1.mp4, 不需要旋转
ffmpeg -y -i " M1.mp4" -vcodec libx264 -b 1024000  -s 320x180 -acodec copy " M1_cp.mp4"
//处理视频M2.mp4,逆时针旋转90
ffmpeg -y -i " M2.mp4" -vf transpose=2 -vcodec libx264 -b 1024000  -s 320x180 -acodec copy -metadata:s:v:0 rotate=90 " M2_cp.mp4"
//处理视频M3.mp4,旋转180
ffmpeg -y -i " M3.mp4" -vf vflip,hflip -vcodec libx264 -b 1024000  -s 320x180 -acodec copy -metadata:s:v:0 rotate=180  " M3_cp.mp4"
//处理视频M4.mp4,逆时针旋转270(或者顺时针旋转90)
ffmpeg -y -i "M4_cp.mp4" -vf transpose=1 -vcodec libx264 -b 1024000  -s 320x180 -acodec copy -metadata:s:v:0 rotate=270 "M4_cp.mp4"

里面参数的基本函义

-vf transpose 旋转视频
0:逆时针旋转90°然后垂直翻转
1:顺时针旋转90°
2:逆时针旋转90°
3:顺时针旋转90°然后水平翻转
hflip 水平翻转
vflip 垂直翻转
//根据视频文件添加rotate值
-metadata:s:v:0 rotate=270

下面这条命令可为某个视频文件设置rotate的值

ffmpeg -i "M2.mp4" -c copy -metadata:s:v:0 rotate=90 "M2_cp.mp4"

你可能感兴趣的:(.Net,FFmpeg,C#)