I am trying to encode a .mp4 video from a set of frames using FFMPEG using the libx264 codec.
This is the command I am running:
/usr/local/bin/ffmpeg -r 24 -i frame_%05d.jpg -vcodec libx264 -y -an video.mp4
I sometimes get the following error:
[libx264 @ 0xa3b85a0] height not divisible by 2 (520x369)
After searching around a bit it seems that the issue has something to do with the scaling algorithm and can be fixed by adding a -vf argument.
However, in my case I don't want to do any scaling. Ideally, I want to keep the dimensions exactly the same as the frames. Any advice? Is there some sort of aspect ratio that h264 enforces?
You may also use
bitand
function instead oftrunc
:bitand(x, 65534)
will do the same as
trunc(x/2)*2
and it is more transparent in my opinion.(Consider 65534 a magical number here ;) )
My task was to scale automatically a lot of video files to half resolution.
scale=-2,ih/2
lead to slightly blurred imagesreason:
scale
scales the real frame dimensionssolution:
explanation:
setsar=1
means output_dimensions are now final, no aspect ratio correction should be appliedSomeone might find this helpful.
It's likely due to the the fact that H264 video is usually converted from RGB to YUV space as 4:2:0 prior to applying compression (although the format conversion itself is a lossy compression algorithm resulting in 50% space savings).
YUV-420 starts with an RGB (Red Green Blue) picture and converts it into YUV (basically one intensity channel and two "hue" channels). The Hue channels are then subsampled by creating one hue sample for every 2X2 square of that hue.
If you have an odd number of RGB pixels either horizontally or vertically, you will have incomplete data for the last pixel column or row in the subsampled hue space of the YUV frame.
LordNeckbeard has the right answer, very fast
For android, dont forget add
If you want to set some output width and have output with the same ratio as original
and not to fall with this problem then you can use
(Just for people searching how to do that with scaling)
The answer to the original question which does not want to scale the video is:
Command:
Basically, .h264 needs even dimensions so this filter will:
You can change the color of the padding by adding filter parameter
:color=white
. See the documentation of pad.Just use
-2
From the scale filter documentation:
Examples
Set width to 1280, and height will automatically be calculated to preserve the aspect ratio, and the height will be divisible by 2:
Same as above, but with a declared height instead; leaving width to be dealt with by the filter:
"divisible by 2"
As required by x264, the "divisible by 2 for width and height" is needed for YUV 4:2:0 chroma subsampled outputs. 4:2:2 would need "divisible by 2 for width", and 4:4:4 does not have these restrictions. However, most non-FFmpeg based players can only properly decode 4:2:0, so that is why you often see
ffmpeg
commands with the-pix_fmt yuv420p
option when outputting H.264 video.Caveat
Unfortunately you can't use
-2
for both width and height, but if you already specified one dimension then using-2
is a simple solution.