summaryrefslogtreecommitdiff
path: root/alligator_resources
diff options
context:
space:
mode:
authorMicha White <botahamec@outlook.com>2022-10-25 21:10:57 -0400
committerMicha White <botahamec@outlook.com>2022-10-25 21:10:57 -0400
commit64096d822a1d0437db558263845d6908c96f634b (patch)
tree834dd39afed72f671ee5edf63a182980b928e67d /alligator_resources
parentf04763063848df9d8e0d0f1177bc7e2cef50e19e (diff)
Allowed loading into the texture atlas
Diffstat (limited to 'alligator_resources')
-rw-r--r--alligator_resources/src/texture.rs42
1 files changed, 33 insertions, 9 deletions
diff --git a/alligator_resources/src/texture.rs b/alligator_resources/src/texture.rs
index 79e0e94..4b4baa4 100644
--- a/alligator_resources/src/texture.rs
+++ b/alligator_resources/src/texture.rs
@@ -20,6 +20,7 @@ impl TextureId {
}
/// These are the formats supported by the renderer.
+// TODO make these feature-enabled
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum ImageFormat {
@@ -92,8 +93,8 @@ impl TextureManager {
let atlas: Box<[MaybeUninit<u16>]> = Box::new_zeroed_slice((4 * width * height) as _);
let atlas = unsafe { atlas.assume_init() };
- let atlas =
- Rgba16Texture::from_raw(width, height, atlas).expect("atlas cache is too small");
+ let atlas = Rgba16Texture::from_raw(width, height, atlas);
+ let atlas = atlas.expect("atlas cache is too small");
Self {
textures,
@@ -104,9 +105,32 @@ impl TextureManager {
}
}
+ pub fn load_to_atlas(&mut self, id: TextureId) {
+ let texture = self.texture(id);
+ if self.packer.pack_own(id, texture.clone()).is_err() {
+ let texture = self.texture(id);
+ self.resize_atlas(self.width + texture.width(), self.height + texture.height());
+
+ let texture = self.texture(id);
+ self.packer
+ .pack_own(id, texture.clone())
+ .expect("packer is still too small after resizing");
+ }
+ }
+
/// Resize the texture atlas
pub fn resize_atlas(&mut self, width: u32, height: u32) {
- self.packer = packer(width, height);
+ let old_packer = &self.packer;
+ let mut new_packer = packer(width, height);
+
+ for id in old_packer.get_frames().keys() {
+ let texture = self.texture(*id).clone();
+ new_packer
+ .pack_own(*id, texture)
+ .expect("resized packer is too small to hold subtextures");
+ }
+
+ self.packer = new_packer;
}
/// Clear the texture atlas
@@ -120,7 +144,6 @@ impl TextureManager {
///
/// This returns `Expected(DecodingError)` if the given buffer was invalid
/// for the given format.
- #[allow(clippy::missing_panics_doc)]
pub fn load_from_memory(
&mut self,
buf: &[u8],
@@ -134,6 +157,7 @@ impl TextureManager {
let width = texture.width();
let height = texture.height();
let buf = texture.into_raw().into_boxed_slice();
+ // TODO this expect can be removed by using unexpect
let texture = ImageBuffer::from_raw(width, height, buf).expect("image buffer is too small");
self.textures.insert(id, texture);
@@ -155,11 +179,11 @@ impl TextureManager {
&self.atlas
}
- fn texture(&self, id: TextureId) -> Option<&Rgba16Texture> {
- self.textures.get(&id)
+ fn texture(&self, id: TextureId) -> &Rgba16Texture {
+ self.textures.get(&id).expect("invalid TextureId")
}
- /// Get the subtexture
+ /// Get the subtexture in the texture atlas
fn subtexture(&self, id: TextureId) -> Option<&Frame<TextureId>> {
self.packer.get_frame(&id)
}
@@ -184,7 +208,7 @@ impl TextureManager {
#[must_use]
#[allow(clippy::cast_precision_loss)]
pub fn texture_width(&self, id: TextureId) -> f32 {
- let width = self.texture(id).expect("invalid TextureId").width();
+ let width = self.texture(id).width();
width as f32 / self.width as f32
}
@@ -192,7 +216,7 @@ impl TextureManager {
#[must_use]
#[allow(clippy::cast_precision_loss)]
pub fn texture_height(&self, id: TextureId) -> f32 {
- let height = self.texture(id).expect("invalid TextureId").height();
+ let height = self.texture(id).height();
height as f32 / self.height as f32
}
}