fennel_engine/resources/
mod.rs1use std::{any::Any, cell::Ref, collections::HashMap, path::PathBuf, sync::Arc};
2
3use sdl3::{render::TextureCreator, video::WindowContext};
4
5pub mod loadable;
7
8pub struct ResourceManager {
10 pub resources: HashMap<String, Box<dyn LoadableResource>>,
12}
13
14pub trait LoadableResource: Any {
16 fn load(
21 path: PathBuf,
22 texture_creator: &Arc<TextureCreator<WindowContext>>,
23 ) -> anyhow::Result<Box<dyn LoadableResource>>
24 where
25 Self: Sized;
26
27 fn name(&self) -> String;
29
30 fn as_mut_slice(&self) -> &mut [u8];
32
33 fn as_slice(&self) -> Ref<'_, [u8]>;
35}
36
37pub fn as_concrete<T: 'static + LoadableResource>(b: &Box<dyn LoadableResource>) -> &T {
39 let dyn_ref: &dyn LoadableResource = b.as_ref();
40
41 let any_ref = dyn_ref as &dyn Any;
42
43 any_ref
44 .downcast_ref::<T>()
45 .expect("incorrect concrete type")
46}
47
48impl ResourceManager {
49 pub fn new() -> Self {
51 Self {
52 resources: HashMap::new(),
53 }
54 }
55
56 pub fn cache_asset(&mut self, asset: Box<dyn LoadableResource>) -> anyhow::Result<()> {
60 self.resources.insert(asset.name(), asset);
61 Ok(())
62 }
63
64 pub fn get_asset(&mut self, name: String) -> anyhow::Result<&Box<dyn LoadableResource>> {
69 let asset = self.resources.get(&name).unwrap();
70 Ok(asset)
71 }
72
73 pub fn is_cached(&mut self, name: String) -> bool {
74 self.resources.contains_key(&name)
75 }
76}
77
78impl Default for ResourceManager {
79 fn default() -> Self {
81 Self::new()
82 }
83}