DEV Community

hao jia
hao jia

Posted on

Why 1-pass ABR landed under my target size: 60-second clip, x264, 25 and 10 MB

Say a ticket tool has a hard upload cap, so the browser has to squeeze screen recordings under it before they leave the laptop. The formula that comes to mind first is video bitrate = target × 8 / duration with single-pass ABR. On a 60-second 1080p clip that came out above the cap. After I subtracted the audio track it came out below the target instead, at both targets I tried, and I wanted to know why before trusting that direction.

All numbers below come from two clips, x264 preset medium, AAC 128 kbps, FFmpeg 7.1 on an M4 Mac, one run each. Clip A is a 60-second 1080p action clip (Isak Zvegelj, CC BY 3.0, Wikimedia Commons). Clip B is a synthetic 60-second screen recording, generated frame by frame, so it is quieter than a real one. "MB" means 1,000,000 bytes here.

Subtract the audio first

Audio at 128 kbps over 60 seconds is nominally 960,000 bytes, and the muxed track measured 971,835. That is about 3.9% of a 25 MB target and 9.7% of a 10 MB target. This is the whole budget calculation:

for target in (25_000_000, 10_000_000):
    print(target, (target * 8 / 60 - 128_000) / 1000)
Enter fullscreen mode Exit fullscreen mode
25000000 3205.3333333333335
10000000 1205.3333333333333
Enter fullscreen mode Exit fullscreen mode

On clip A the naive bitrate (no audio subtracted) overshot by 3.14% at 25 MB and 9.17% at 10 MB. With the audio subtracted, single-pass ABR (-b:v 3205k and -b:v 1205k) gave 24,835,380 bytes (−0.66%) and 9,965,325 bytes (−0.35%).

Where the missing 1% went

I split the naive single-pass overshoot at 25 MB into three parts: audio +971,835 bytes, container +66,834 bytes (almost all of it the moov box), and the video stream −253,166 bytes. That adds up to the +785,503 bytes the file was over by. So the video stream came in about 1.0% under the budget I had handed to the rate control, and nothing in the file filled that gap. The 10 MB run went the same direction.

Why? I did not look inside x264, so this part is inference. My guess is that single-pass ABR steers by what it has seen so far and stays slightly on the cautious side of its average. Per-second video bitrate on clip A swung between 790 and 1,950 kbps around a 1,205 kbps average at 10 MB, so there was plenty to steer. That fits the guess but does not prove it.

Two-pass did not fix it here

The textbook answer is two-pass, so I ran it with the same bitrate. On clip A it overshot: +0.28% at 25 MB (69,942 bytes over) and +1.74% at 10 MB. A CRF search that re-encodes the whole file each round landed at −0.86% and −1.45%, and took 157 to 217 seconds against about 23 seconds for single-pass. Under a hard cap, undershooting by a percent is the failure I can live with, and overshooting is the one that gets the upload rejected.

The clip decides how big the miss is

On clip A every method stayed within ±1.8% once the audio was subtracted. Clip B was different, and not in one direction. At 10 MB its single-pass run came in 8.65% under and its two-pass run 12.0% over. One synthetic clip says nothing about real recordings, so treat B as a warning about variance, not as a measurement.

What I would do with it

Keep the formula with the audio subtracted, plus about 70 KB for the container, and on footage like clip A expect single-pass to land up to a percent low. That is only what these two clips showed. If the file ends up far below the cap, check whether the clip is simply easy before blaming the encoder. I would not raise the bitrate automatically to use the slack, because the cap matters more than the last percent.

If you want to see what a ready-made tool does with the same clip, ImgIng (https://imging.ai/) has a video compression page that runs in a desktop browser, and the page says it processes locally. It has no compress-to-target-size mode, so the only lever is its presets: the balanced tier with a 1280 longest side gave 25,938,497 bytes against my 25,000,000 target, so even there I overshot. It does not work on phones. Free tiers and limits of other online tools change, so check their own pages.

One unit trap: ImgIng's interface counts MB as 1,048,576 bytes, 4.86% more than the 1,000,000 I used above. If a limit is written in MB, find out which one before you budget.

Top comments (0)