Skip to content

Make image-quality more consistent#7822

Open
72374 wants to merge 4 commits intochatmail:mainfrom
72374:make-image-quality-more-consistent
Open

Make image-quality more consistent#7822
72374 wants to merge 4 commits intochatmail:mainfrom
72374:make-image-quality-more-consistent

Conversation

@72374
Copy link
Contributor

@72374 72374 commented Feb 4, 2026

See commit-descriptions for more information.

to the only part of the function where it is used.
@72374 72374 force-pushed the make-image-quality-more-consistent branch 2 times, most recently from 814267c to 40721b8 Compare February 4, 2026 14:01
72374 added 2 commits February 4, 2026 16:46
Currently, the resolution of a resized image that was sent in a chat,
depends on the aspect-ratio.

Assuming the `balanced`-quality-setting is used,
a square image, that is larger than the limits for resolution and file-size,
will be resized to 1280x1280 (1,638,400 pixels),
an image with an aspect-ratio of 16:9,
will be resized to 1280x720 (921,600 pixels),
and if the aspect-ratio is 32:9, to 1280x360 (460,800 pixels).

This change makes it so, that the number of pixels,
in images with different aspect-ratios, will be similar.
The resolution-limits for avatar-images are currently 512x512 or 128x128.
Reducing the resolution further, to 2/3 each step, can reduce the quality
much more than is necessary to fit within the file-size-limits,
which are currently 60 kB or 20 kB.

An image made entirely of noise (which results in unusually
large file-sizes), encoded with jpeg-quality 75,
and 4:2:2-colour-subsampling (the format currently used
for encoding images), can be below 60 kB at 227x227.
For the lower file-size-limit of 20 kB,
such images with a resolution of 128x128 already fit.
More normal images will have a lower file-size at the same resolution.

Before this change, the target-resolutions for resizing were:
512x512 ->                       341x341 ->                       227x227.

And for the lower file-size-limit:
128x128 (does already fit).

After this change, the target-resolutions for resizing will be:
512x512 -> 448x448 -> 392x392 -> 343x343 -> 300x300 -> 263x263 -> 230x230.

And for the lower file-size-limit, those will be:
256x256 -> 224x224 -> 196x196 -> 172x172 -> 150x150 -> 131x131.

The resolution-limit has been increased to 256x256, because the file-size
of many images is still smaller than 20 kB when encoded at 256x256,
and it can be a large improvement in quality.
@72374 72374 force-pushed the make-image-quality-more-consistent branch from 40721b8 to a32210d Compare February 4, 2026 15:47
@72374 72374 marked this pull request as ready for review February 4, 2026 16:08
@72374
Copy link
Contributor Author

72374 commented Feb 27, 2026

Here a comparison for the quality of images sent in chats.

Tap here to view the original images
Whole image Cropped to relevant content Further cropped to 1280 pixels Whole image cropped to square
Original image

1 - whole image - original (3840x2128 = 8,171,520 pixels)
3840x2128 =
8,171,520 pixels

2 - cropped to relevant content - original (3521×990 = 3,485,790 pixels)
3521×990 =
3,485,790 pixels

3 - further cropped to 1280 on the long side - original (1280x990 = 1,267,200 pixels)
1280x990 =
1,267,200 pixels

4 - cropped to square - original (2128x2128 = 4,528,384 pixels)
2128x2128 =
4,528,384 pixels

After sending Whole image Cropped to relevant content Further cropped to 1280 pixels* Whole image cropped to square*
Main branch

1 - whole image - main branch (907,520 pixels)
1280x709 =
907,520 pixels

2 - cropped to relevant content - main branch (460,800 pixels)
1280x360 =
460,800 pixels

3 - further cropped to 1280 pixels on the long side - main branch (1,267,200 pixels)
1280x990 =
1,267,200 pixels

4 - cropped to square - main branch (1,638,400 pixels)
1280x1280 =
1,638,400 pixels

This PR

1 - whole image - this pr (1,638,207 pixels)
1719x953 =
1,638,207 pixels

2 - cropped to relevant content - this pr (1,636,014 pixels)
2413x678 =
1,636,014 pixels

3 - further cropped to 1280 on the long side - this pr (1,267,200 pixels)
1280x990 =
1,267,200 pixels

4 - cropped to square - this pr (1,638,400 pixels)
1280x1280 =
1,638,400 pixels

*: The 2 columns on the right are supposed to be identical; i mostly included them, to make it visible that square-ish images already get encoded with up to ~1.6 megapixels, on the "main"-branch.

src/blob.rs Outdated
let mut target_wh = if !is_avatar && exceeds_wh {
// Limit resolution to the number of pixels that fit within max_wh * max_wh,
// so that the image-quality does not depend on the aspect-ratio.
(f64::from(resolution_of_longest_side_of_image)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So the image still can exceed "wh" if it's not square. Then exceeds_wh should be tweaked for images, it should compare not the longest image size, but the number of pixels, with max_wh * max_wh.

Secondly, not the number of pixels matters, but the number of JPEG blocks (which are 8x8), because we recode to JPEG.

});

if do_scale {
let resolution_of_longest_side_of_image = max(img.width(), img.height());
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe use shorter names for variables: longest_size_len, n_px_sqrt? We use n_* in the many places for "number", it's a standard abbreviation in Core. sqrt is also a standard abbreviation, even the function is called so. "in image" can be omitted because we don't have anything else here, do we?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants