Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 25 additions & 8 deletions src/blob.rs
Original file line number Diff line number Diff line change
Expand Up @@ -388,14 +388,9 @@ impl<'a> BlobObject<'a> {
_ => img,
};

// max_wh is the maximum image width and height, i.e. the resolution-limit.
// target_wh target-resolution for resizing the image.
// max_wh is the maximum image width and height, i.e. the resolution-limit,
// as set by the media-quality-setting.
let exceeds_wh = img.width() > max_wh || img.height() > max_wh;
let mut target_wh = if exceeds_wh {
max_wh
} else {
max(img.width(), img.height())
};
let exceeds_max_bytes = nr_bytes > max_bytes as u64;

let jpeg_quality = 75;
Expand Down Expand Up @@ -434,6 +429,27 @@ impl<'a> BlobObject<'a> {
});

if do_scale {
let resolution_of_longest_side_of_image = max(img.width(), img.height());
let square_root_of_number_of_pixels_in_image =
f64::from(img.width() * img.height()).sqrt();

// target_wh will be used as the target-resolution for resizing the image,
// so that the longest sides of the image match the target-resolution,
// without changing the aspect-ratio.
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)
* (f64::from(max_wh) / square_root_of_number_of_pixels_in_image))
as u32
} else {
max_wh
};

if target_wh > resolution_of_longest_side_of_image {
target_wh = resolution_of_longest_side_of_image
};

loop {
if mem::take(&mut add_white_bg) {
self::add_white_bg(&mut img);
Expand Down Expand Up @@ -467,7 +483,8 @@ impl<'a> BlobObject<'a> {
));
}

target_wh = target_wh * 2 / 3;
// Note: This is only done for avatar-images.
target_wh = target_wh * 7 / 8;
} else {
info!(
context,
Expand Down
12 changes: 6 additions & 6 deletions src/blob/blob_tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -384,8 +384,8 @@ async fn test_recode_image_balanced_png() {
extension: "png",
original_width: 1920,
original_height: 1080,
compressed_width: constants::WORSE_IMAGE_SIZE,
compressed_height: constants::WORSE_IMAGE_SIZE * 1080 / 1920,
compressed_width: 853,
compressed_height: 480,
..Default::default()
}
.test()
Expand Down Expand Up @@ -475,8 +475,8 @@ async fn test_recode_image_rgba_png_to_jpeg() {
extension: "png",
original_width: 1920,
original_height: 1080,
compressed_width: constants::WORSE_IMAGE_SIZE,
compressed_height: constants::WORSE_IMAGE_SIZE * 1080 / 1920,
compressed_width: 853,
compressed_height: 480,
..Default::default()
}
.test()
Expand All @@ -495,8 +495,8 @@ async fn test_recode_image_huge_jpg() {
has_exif: true,
original_width: 1920,
original_height: 1080,
compressed_width: constants::BALANCED_IMAGE_SIZE,
compressed_height: constants::BALANCED_IMAGE_SIZE * 1080 / 1920,
compressed_width: 1706,
compressed_height: 960,
..Default::default()
}
.test()
Expand Down
2 changes: 1 addition & 1 deletion src/constants.rs
Original file line number Diff line number Diff line change
Expand Up @@ -199,7 +199,7 @@ pub const WORSE_IMAGE_BYTES: usize = 130_000;
// max. width/height and bytes of an avatar
pub(crate) const BALANCED_AVATAR_SIZE: u32 = 512;
pub(crate) const BALANCED_AVATAR_BYTES: usize = 60_000;
pub(crate) const WORSE_AVATAR_SIZE: u32 = 128;
pub(crate) const WORSE_AVATAR_SIZE: u32 = 256;
pub(crate) const WORSE_AVATAR_BYTES: usize = 20_000; // this also fits to Outlook servers don't allowing headers larger than 32k.

// max. width/height of images scaled down because of being too huge
Expand Down
2 changes: 1 addition & 1 deletion src/tests/pre_messages/additional_text.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ async fn test_additional_text_on_different_viewtypes() -> Result<()> {
let (pre_message, _, _) = send_large_image_message(alice, a_group_id).await?;
let msg = bob.recv_msg(&pre_message).await;
assert_eq!(msg.text, "test".to_owned());
assert_eq!(msg.get_text(), "test [Image – 146.12 KiB]".to_owned());
assert_eq!(msg.get_text(), "test [Image – 227.50 KiB]".to_owned());

Ok(())
}
6 changes: 3 additions & 3 deletions src/tests/pre_messages/receiving.rs
Original file line number Diff line number Diff line change
Expand Up @@ -323,9 +323,9 @@ async fn test_receive_pre_message_image() -> Result<()> {
// test that metadata is correctly returned by methods
assert_eq!(msg.get_post_message_viewtype(), Some(Viewtype::Image));
// recoded image dimensions
assert_eq!(msg.get_filebytes(bob).await?, Some(149632));
assert_eq!(msg.get_height(), 1280);
assert_eq!(msg.get_width(), 720);
assert_eq!(msg.get_filebytes(bob).await?, Some(232957));
assert_eq!(msg.get_height(), 1706);
assert_eq!(msg.get_width(), 960);

Ok(())
}
Expand Down
Loading