我有1920x1080
的mp4视频。我想将视频裁剪为480x270
而不会造成质量损失。
我使用以下命令:
ffmpeg -i input.mp4 -filter:v "crop=480:270:200:200" -crf 23 output.mp4
我也尝试过:
ffmpeg -i input.mp4 -filter:v "crop=480:270:200:100" -c:a copy -qp 0 output.mp4
我使用-crf 23
和-qp 0
进行无损视频裁剪,但裁剪后视频质量下降。
有谁知道如何裁剪视频而不会失去的质量?
答案 0 :(得分:24)
在编码为有损格式时,您无法在不降低质量的情况下执行任何过滤,但您有一些选择。
可能的解决方案是在播放期间裁剪,因此您甚至不需要重新编码。预览作物也很有用。
使用ffplay
和crop filter:
ffplay -vf "crop=480:270:200:100" input.mp4
使用vlc
(或cvlc
):
vlc input.mp4 --crop=480x270+200+100
或者您可以使用VLC GUI裁剪:工具>效果&过滤器>视频效果>作物。
此方法不会创建输出文件。这将使用您的视频播放器在播放时进行裁剪。如果需要输出文件,请参阅其他方法之一。
ffmpeg
可以编码几个无损编码器:ffv1,huffyuv,ffvhuff,utvideo,libx264(使用-crf 0
或-qp 0
)。输出将是无损的,但输出文件将是巨大的。
ffmpeg -i input.mp4 -vf "crop=480:270:200:100" -c:v ffv1 -c:a copy output.mkv
或
ffmpeg -i input.mp4 -vf "crop=480:270:200:100" -c:v libx264 -crf 0 -c:a copy output.mp4
给它足够的位,你可能无法分辨出质量差异:
ffmpeg -i input -vf "crop=480:270:200:100" -c:v libx264 -crf 17 -c:a copy ouput.mp4
有关详细信息,请参阅FFmpeg Wiki: H.264 Video Encoding Guide。
Stream copy the individual images with ffmpeg
,使用jpegtran
无损地裁剪它们,然后使用ffmpeg
将它们重新混合。这将导致不会丢失,但您将被限制在古老的MJPEG格式中。
答案 1 :(得分:4)
在基本级别,您无法使用有损编码,然后在解码然后再次编码时期望它不会丢失质量。唯一有效的方法是使用无损编解码器,例如使用动画编解码器的Quicktime。这只是数字视频制作的基本事实,你只需将命令行选项传递给ffmpeg就无法解决。
答案 2 :(得分:3)
使用ffmpeg无法做到这一点。
作为替代方案,您可以将视频嵌入Matroska(.mkv)容器和set a cropping tag in the file header,但it must be supported by your player。
据报道,对于H264编码的视频H264info也可以使用,但我仍然需要弄清楚如何使用它......
答案 3 :(得分:2)
至少对于某些视频格式而言,通过使用libavcodec的 bitstream 过滤器,也可以使用FFmpeg基于元数据 的软解决方案,例如hevc_metadata
或h264_metadata
。
与crop
和cropdetect
之类的过滤器不同,这不需要解码。但是,语法略有不同,因为您只能从四个边缘设置裁切量,而不能设置目标矩形的大小。对于在1920×1080全高清帧中左上方(200,200)位置的OP的480×270区域,我们得到:
ffmpeg -i input.mp4 -codec copy -bsf:v h264_metadata=crop_left=200:crop_right=1240:crop_top=200:crop_bottom=610 output.mp4
由于这是编解码器元数据,因此无论容器格式如何,此应该都可以工作,即不仅在MP4中,而且在MKV或AVI中也是如此。 las,我自己尚未测试过,不能说有关软件和硬件播放器支持的任何内容。 (不过,第一次简单的检查却失败了。)
有关更多详细信息,FFmpeg的文档分别引用了H.265和H.264规范的7.4.3.2.1和7.4.2.1.1节,这些文件可从ITU免费获得,并且基本上等效:
frame_cropping_flag
等于1表示帧裁剪偏移参数在序列参数集中紧随其后。 frame_cropping_flag等于0表示不存在帧裁剪偏移参数。
frame_crop_left_offset
,frame_crop_right_offset
,frame_crop_top_offset
,frame_crop_bottom_offset
指定输出的编码视频序列中图片的样本从解码过程来看, 在帧坐标中指定的区域用于输出。 变量CropUnitX
和CropUnitY
的得出如下:–如果ChromaArrayType等于0,则CropUnitX和CropUnitY导出为:
CropUnitX = 1
CropUnitY = 2 − frame_mbs_only_flag
–否则(ChromaArrayType
等于1、2或3),CropUnitX
和CropUnitY
推导为:CropUnitX = SubWidthC
CropUnitY = SubHeightC * ( 2 − frame_mbs_only_flag )
帧裁剪矩形包含亮度样本,其水平帧坐标为
CropUnitX * frame_crop_left_offset to PicWidthInSamplesL − ( CropUnitX * frame_crop_right_offset + 1 )
和垂直框架坐标来自CropUnitY * frame_crop_top_offset to ( 16 * FrameHeightInMbs ) − ( CropUnitY * frame_crop_bottom_offset + 1 )
(含)。
frame_crop_left_offset
的值应在0的范围内 到( PicWidthInSamplesL / CropUnitX ) − ( frame_crop_right_offset + 1 )
(含); 并且frame_crop_top_offset
的值应在0到( 16 * FrameHeightInMbs / CropUnitY ) − ( frame_crop_bottom_offset + 1 )
的范围内(包括两端)。当
frame_cropping_flag
等于0时,应该推断frame_crop_left_offset
,frame_crop_right_offset
,frame_crop_top_offset
和frame_crop_bottom_offset
的值等于0。当
ChromaArrayType
不等于0时,两个色度阵列的对应指定样本是具有帧坐标( x / SubWidthC, y / SubHeightC )
的样本,其中( x, y )
是指定亮度的帧坐标 样本。对于解码字段,解码字段的指定样本是落在帧坐标中指定矩形内的样本。