chuot/assets/loader/
png.rs1use std::io::Cursor;
4
5use png::{BitDepth, ColorType, Decoder, Transformations};
6use rgb::RGBA8;
7
8use super::Loader;
9use crate::assets::Id;
10
11#[non_exhaustive]
15pub struct PngLoader;
16
17impl Loader<(u32, u32, Vec<RGBA8>)> for PngLoader {
18 const EXTENSION: &'static str = "png";
19
20 #[inline]
21 fn load(bytes: &[u8], id: &Id) -> (u32, u32, Vec<RGBA8>) {
22 let cursor = Cursor::new(bytes.to_vec());
24
25 let mut decoder = Decoder::new(cursor);
27
28 decoder.set_ignore_text_chunk(true);
30 decoder.ignore_checksums(true);
32
33 decoder
35 .set_transformations(Transformations::normalize_to_color8() | Transformations::ALPHA);
36
37 let mut reader = decoder.read_info().unwrap();
39
40 let (color_type, bits) = reader.output_color_type();
42
43 assert!(
45 color_type == ColorType::Rgba && bits == BitDepth::Eight,
46 "PNG of asset with ID '{id}' is not 8 bit RGB with an alpha channel"
47 );
48
49 let mut pixels = vec![RGBA8::default(); reader.output_buffer_size()];
51 let info = reader
52 .next_frame(bytemuck::cast_slice_mut(&mut pixels))
53 .expect("Error reading image");
54
55 (info.width, info.height, pixels)
56 }
57}