录制时我有一个旋转了180°的视频。可以使用FFmpeg纠正此问题吗?
录制时我有一个旋转了180°的视频。可以使用FFmpeg纠正此问题吗?
Answers:
ffmpeg
会自动旋转视频,除非:
ffmpeg
太老了某些视频(例如来自iPhone的视频)在物理上并未翻转,但包含视频流显示矩阵辅助数据或旋转元数据。有些播放器会忽略这些元数据,有些则不会。请参考ffmpeg
控制台输出,以查看您的输入是否具有此类元数据:
$ ffmpeg -i input.mp4
...
Input #0, mov,mp4,m4a,3gp,3g2,mj2, from 'input.mp4':
Duration: 00:00:05.00, start: 0.000000, bitrate: 43 kb/s
Stream #0:0(und): Video: h264 (High 4:4:4 Predictive) (avc1 / 0x31637661), yuv444p, 320x240 [SAR 1:1 DAR 4:3], 39 kb/s, 25 fps, 25 tbr, 12800 tbn, 50 tbc (default)
Metadata:
rotate : 180
Side data:
displaymatrix: rotation of -180.00 degrees
ffmpeg
会根据任何现有的视频流旋转元数据自动对视频进行物理旋转。
从2015年5月2日开始,您需要一个包含提交1630224的构建,才能使用自动旋转功能。
ffmpeg -i input.mp4 -c:a copy output.mp4
要禁用此行为,请使用该-noautorotate
选项。
ffmpeg
旧您将必须使用过滤器来旋转视频,并且如果存在任何旋转元数据,则必须将其删除,如以下示例所示:
使用,ffmpeg
您可以选择三种使用视频滤镜旋转180°的方法。
hflip
和 vflip
ffmpeg -i input.mp4 -vf "hflip,vflip,format=yuv420p" -metadata:s:v rotate=0 \
-codec:v libx264 -codec:a copy output.mkv
transpose
ffmpeg -i input.mp4 -vf "transpose=2,transpose=2,format=yuv420p" \
-metadata:s:v rotate=0 -codec:v libx264 -codec:a copy output.mp4
rotate
该滤镜可以旋转到任意角度,并以弧度为单位而不是度。本示例将旋转π/ 1弧度或180°:
ffmpeg -i input.mp4 -vf "rotate=PI:bilinear=0,format=yuv420p" \
-metadata:s:v rotate=0 -codec:v libx264 -codec:a copy output.mp4
您可以改用度数。一度等于π/ 180弧度。因此,如果您想旋转45°:
ffmpeg -i input.mp4 -vf "rotate=45*(PI/180),format=yuv420p" \
-metadata:s:v rotate=0 -codec:v libx264 -codec:a copy output.mp4
使用rotate
滤镜时,应关闭双线性插值(使用bilinear=0
)以将角度除以90,否则可能会显得模糊。
过滤需要编码。这些示例进行H.264视频输出。有关获得所需质量的指导,请参阅FFmpeg H.264视频编码指南。
色度二次采样。我将其包括在内,format=yuv420p
因为这ffmpeg
将尝试最小化或避免色度二次采样(取决于编码器,输入,ffmpeg
版本等)。从纯技术角度来讲,这是一种良好的行为,但是大多数播放器与更多的“高级”色度子采样方案不兼容。这与使用相同-pix_fmt yuv420
,但位于过滤链中很方便。
复制音频。该-codec:a copy
选项将流式复制(重新混合)而不是编码。如果您只想操作视频,则没有理由重新编码音频(除非您想转换为其他音频格式)。由于编码非常耗时,因此可以节省时间,并且可以保留音频质量。
另外,您可以在播放时旋转并避免重新编码。ffplay
会自动旋转:
ffplay input.mp4
如果没有displaymatrix辅助数据或旋转元数据,则可以使用过滤器:
ffplay -vf "hflip,vflip" -i input.mp4
...或参考您最喜欢的球员。像VLC这样的大多数值得使用的播放器都具有此功能。
ffmpeg
较旧的ffmpeg版本不包含过滤功能。请参阅FFmpeg下载页面,以获取多个选项,包括适用于Linux,OS X和Windows的便捷构建,或参阅FFmpeg Wiki获取ffmpeg逐步编译指南。
-vf vflip
,它就像一种魅力。但这是重新编码。我不确定我在读对吗。您是说-vf hflip,vflip
不会重新编码吗?
ffmpeg
要求您在使用视频和音频过滤器时重新编码。但是,ffplay
如我的第二个示例所示,在回放过程中也可以使用许多过滤器。
-codec:v libx264
?可以ffmpeg
仅使用相同的编码而无需用户尝试弄清楚吗?
rotate
使用弧度而不是度作为单位。我认为人们对学位更加熟悉,因此我尝试在示例中展示如何使用学位。一度等于π/ 180弧度。因此,如果您想旋转45°,只需使用rotate="45*(PI/180)"
。
使用ffmpeg作为解码后端的媒体播放器也可以利用其所有过滤器。使用“偏移和翻转”过滤器查看此屏幕截图。
另外,如果您想重新编码视频,请在Stackoverflow上查看使用FFmpeg旋转视频。
transpose
过滤器链接在一起以达到效果。
以下是一个bash脚本,它将输出具有“ fixedFiles”下目录结构的文件。它可以转换和旋转iOS视频并转码AVI。该脚本依赖于同时安装了exiftool和ffmpeg。
#!/bin/bash
# rotation of 90 degrees. Will have to concatenate.
#ffmpeg -i <originalfile> -metadata:s:v:0 rotate=0 -vf "transpose=1" <destinationfile>
#/VLC -I dummy -vvv <originalfile> --sout='#transcode{width=1280,vcodec=mp4v,vb=16384,vfilter={canvas{width=1280,height=1280}:rotate{angle=-90}}}:std{access=file,mux=mp4,dst=<outputfile>}\' vlc://quit
#Allowing blanks in file names
SAVEIFS=$IFS
IFS=$(echo -en "\n\b")
#Bit Rate
BR=16384
#where to store fixed files
FIXED_FILES_DIR="fixedFiles"
#rm -rf $FIXED_FILES_DIR
mkdir $FIXED_FILES_DIR
# VLC
VLC_START="/Applications/VLC.app/Contents/MacOS/VLC -I dummy -vvv"
VLC_END="vlc://quit"
#############################################
# Processing of MOV in the wrong orientation
for f in `find . -regex '\./.*\.MOV'`
do
ROTATION=`exiftool "$f" |grep Rotation|cut -c 35-38`
SHORT_DIMENSION=`exiftool "$f" |grep "Image Size"|cut -c 39-43|sed 's/x//'`
BITRATE_INT=`exiftool "$f" |grep "Avg Bitrate"|cut -c 35-38|sed 's/\..*//'`
echo Short dimension [$SHORT_DIMENSION] $BITRATE_INT
if test "$ROTATION" != ""; then
DEST=$(dirname ${f})
echo "Processing $f with rotation $ROTATION in directory $DEST"
mkdir -p $FIXED_FILES_DIR/"$DEST"
if test "$ROTATION" == "0"; then
cp "$f" "$FIXED_FILES_DIR/$f"
elif test "$ROTATION" == "180"; then
# $(eval $VLC_START \"$f\" "--sout="\'"#transcode{vfilter={rotate{angle=-"$ROTATION"}},vcodec=mp4v,vb=$BR}:std{access=file,mux=mp4,dst=\""$FIXED_FILES_DIR/$f"\"}'" $VLC_END )
$(eval ffmpeg -i \"$f\" -vf hflip,vflip -r 30 -metadata:s:v:0 rotate=0 -b:v "$BITRATE_INT"M -vcodec libx264 -acodec copy \"$FIXED_FILES_DIR/$f\")
elif test "$ROTATION" == "270"; then
$(eval ffmpeg -i \"$f\" -vf "scale=$SHORT_DIMENSION:-1,transpose=2,pad=$SHORT_DIMENSION:$SHORT_DIMENSION:\(ow-iw\)/2:0" -r 30 -s "$SHORT_DIMENSION"x"$SHORT_DIMENSION" -metadata:s:v:0 rotate=0 -b:v "$BITRATE_INT"M -vcodec libx264 -acodec copy \"$FIXED_FILES_DIR/$f\" )
else
# $(eval $VLC_START \"$f\" "--sout="\'"#transcode{scale=1,width=$SHORT_DIMENSION,vcodec=mp4v,vb=$BR,vfilter={canvas{width=$SHORT_DIMENSION,height=$SHORT_DIMENSION}:rotate{angle=-"$ROTATION"}}}:std{access=file,mux=mp4,dst=\""$FIXED_FILES_DIR/$f"\"}'" $VLC_END )
echo ffmpeg -i \"$f\" -vf "scale=$SHORT_DIMENSION:-1,transpose=1,pad=$SHORT_DIMENSION:$SHORT_DIMENSION:\(ow-iw\)/2:0" -r 30 -s "$SHORT_DIMENSION"x"$SHORT_DIMENSION" -metadata:s:v:0 rotate=0 -b:v "$BITRATE_INT"M -vcodec libx264 -acodec copy \"$FIXED_FILES_DIR/$f\"
$(eval ffmpeg -i \"$f\" -vf "scale=$SHORT_DIMENSION:-1,transpose=1,pad=$SHORT_DIMENSION:$SHORT_DIMENSION:\(ow-iw\)/2:0" -r 30 -s "$SHORT_DIMENSION"x"$SHORT_DIMENSION" -metadata:s:v:0 rotate=0 -b:v "$BITRATE_INT"M -vcodec libx264 -acodec copy \"$FIXED_FILES_DIR/$f\" )
fi
fi
echo
echo ==================================================================
sleep 1
done
#############################################
# Processing of AVI files for my Panasonic TV
# Use ffmpegX + QuickBatch. Bitrate at 16384. Camera res 640x424
for f in `find . -regex '\./.*\.AVI'`
do
DEST=$(dirname ${f})
DEST_FILE=`echo "$f" | sed 's/.AVI/.MOV/'`
mkdir -p $FIXED_FILES_DIR/"$DEST"
echo "Processing $f in directory $DEST"
$(eval ffmpeg -i \"$f\" -r 20 -acodec libvo_aacenc -b:a 128k -vcodec mpeg4 -b:v 8M -flags +aic+mv4 \"$FIXED_FILES_DIR/$DEST_FILE\" )
echo
echo ==================================================================
done
IFS=$SAVEIFS
我被要求对其进行编辑,以作为文本的开头,指出我最终找到的解决方案是在文本结尾。因此,最后您将找到两个连续的ffmpeg命令,这些命令已成功将我的视频旋转到正确的方向。之前的文字旨在提供尽可能多的信息,因为我看到其他信息由于缺乏信息而被拒绝。无论如何,我希望这对使用ffmpeg的人有所帮助。在我看来,ffmpeg中的hflip和vflip的目的至少是令人困惑的,并且与我的预期相反。
merlin.mov文件是我在iphone上拍摄的视频的副本,该视频首先上传到Dropbox,然后下载到运行Ubuntu的笔记本电脑:
$ uname -a
Linux gazelle 3.13.0-135-generic #184-Ubuntu SMP
Wed Oct 18 11:55:51 UTC 2017 x86_64 x86_64 x86_64
GNU/Linux
我知道我应该能够通过USB挂载iphone并直接复制文件,但这是行不通的。我的笔记本电脑会识别iphone已连接,但不会挂载其文件系统,并且我的iphone上没有提示“信任”笔记本电脑。
我用来从Dropbox复制到笔记本电脑的命令是这样的:
cp ~/Dropbox/Camera\ Uploads/Video\ Nov\ 02\,\ 9\ 41\ 55\ AM.mov \
merlin.mov
原始文件是Video 1920 x 1080编解码器HEVC / H.265帧速率30 /秒,比特率8140 kbps,音频编解码器MPEG-4 AAC音频通道立体声,采样率44100 Hz,比特率85 kbps。当我在iPhone上播放时,它的方向正确,并且声音已同步。当我在笔记本电脑上的视频中播放时,它既颠倒又水平颠倒,并且声音不同步。这是“ ffmpeg -i merlin.mov”的部分输出:
Metadata:
rotate : 180
creation_time : 2017-11-02T14:41:55.000000Z
handler_name : Core Media Data Handler
encoder : HEVC
这是“ ffmpeg -version”输出的第一行:
ffmpeg版本3.3.3版权所有(c)2000-2017 FFmpeg开发人员
以下内容使回放在垂直和水平方向上都反转了,尽管它确实转换为MPEG-4视频(video / mp4)并同步了声音:
ffmpeg -i merlin.mov -vf 'hflip,vflip' merlinhflipvflip.mp4
以下内容垂直翻转,因此播放是直立的,同步了声音,并转换为MPEG-4,但是水平错误地从头到尾翻转了一下(这不是错别字,我确实指定了“ hflip”):
ffmpeg -i merlin.mov -vf 'hflip' merlinhflip.mp4
以下内容将水平方向翻转为正确的方向,但将播放倒置:
ffmpeg -i merlin.mov -vf 'vflip' merlinvflip.mp4
以下似乎没有任何作用:
ffmpeg -i merlin.mov -vf 'hflip' merlinhflip.mp4
ffmpeg -i merlinhflip.mp4 -vf 'vflip' merlin2stepA.mp4
我也根据在superuser.com上找到的命令尝试了此操作。它成功地同步了声音,并转换为MPEG-4,但是水平和垂直方向仍然不正确:
ffmpeg -i merlin.mov \
-vf "rotate=PI:bilinear=0,format=yuv420p" \
-metadata:s:v rotate=0 -codec:v libx264 \
-codec:a copy merlinrotate.mp4
我也尝试过这种方法,但在纠正方向方面没有用:
ffmpeg -noautorotate -i merlin.mov merlinnoautorotate.mp4
以下两步过程终于得到了我想要的;垂直和水平翻转,声音同步,并转换为MPEG-4格式(同样,这不是拼写错误;我在两个命令中都使用了hflip):
ffmpeg -i merlin.mov -vf 'hflip' merlinhflip.mp4
ffmpeg -i merlinhflip.mp4 -vf 'hflip' merlin2stepB.mp4
步骤如下:
首先在QuickTime中打开您的视频文件。您可以先启动QuickTime,然后转到“文件”,然后转到“打开文件”。或者,您可以右键单击文件本身,选择“打开方式”,然后选择QuickTime。
视频打开后,单击“编辑”,然后直接在下面找到“旋转”和“翻转”选项
锁定所需的方向后,您必须使用已添加的新更改导出视频。您会在QuickTime的“文件”菜单下找到“导出”选项。
选择要导出为的文件设置,然后单击“确定”以开始导出。
导出操作完成后,您将在选择以正确方向保存文件的位置找到新文件!
整个修复过程只花了我不到5分钟的时间,但是视视频的长度而定,它可能要花费更长的时间(或更短,还是有所不同)。