Skip to content

Commit

Permalink
Support RGB WebP images (#5586)
Browse files Browse the repository at this point in the history
Current WebP loader assumes all WebP images to be RGBA, which is the
case if the image is animated (that's what `image` crate assumes at
least). Static images can instead choose to exclude its alpha channel,
though it seems to be more of a default choice to include it, even if
it's not being utilized. Currently, loading a static RGB WebP image will
cause a panic when `ColorImage::from_rgba_unmultiplied` gets called in
the loader
```
thread 'main' panicked at /home/aely/.cargo/git/checkouts/egui-226fc7cdd51201c1/f87219d/crates/epaint/src/image.rs:97:9:
assertion `left == right` failed
  left: 29184
 right: 21888
```
  • Loading branch information
Aely0 authored Jan 7, 2025
1 parent 52060c0 commit 7cb8187
Showing 1 changed file with 16 additions and 5 deletions.
21 changes: 16 additions & 5 deletions crates/egui_extras/src/loaders/webp_loader.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ use egui::{
mutex::Mutex,
ColorImage, FrameDurations, Id,
};
use image::{codecs::webp::WebPDecoder, AnimationDecoder as _, ImageDecoder, Rgba};
use image::{codecs::webp::WebPDecoder, AnimationDecoder as _, ColorType, ImageDecoder, Rgba};
use std::{io::Cursor, mem::size_of, sync::Arc, time::Duration};

#[derive(Clone)]
Expand Down Expand Up @@ -48,6 +48,17 @@ impl WebP {
frame_durations: FrameDurations::new(durations),
}))
} else {
// color_type() of WebPDecoder only returns Rgb8/Rgba8 variants of ColorType
let create_image = match decoder.color_type() {
ColorType::Rgb8 => ColorImage::from_rgb,
ColorType::Rgba8 => ColorImage::from_rgba_unmultiplied,
unreachable => {
return Err(format!(
"Unreachable WebP color type, expected Rgb8/Rgba8, got {unreachable:?}"
))
}
};

let (width, height) = decoder.dimensions();
let size = decoder.total_bytes() as usize;

Expand All @@ -56,10 +67,10 @@ impl WebP {
.read_image(&mut data)
.map_err(|error| format!("WebP image read failure ({error})"))?;

let image =
ColorImage::from_rgba_unmultiplied([width as usize, height as usize], &data);

Ok(Self::Static(Arc::new(image)))
Ok(Self::Static(Arc::new(create_image(
[width as usize, height as usize],
&data,
))))
}
}

Expand Down

0 comments on commit 7cb8187

Please sign in to comment.