Skip to main content

gizmo_engine/
asset_server.rs

1use crate::core::asset::Handle;
2use crate::renderer::async_assets::AsyncAssetLoader;
3use crate::renderer::components::{Material, Mesh};
4use wgpu::util::DeviceExt;
5
6pub struct AssetServer {
7    pub loader: AsyncAssetLoader,
8    mesh_paths: std::collections::HashMap<String, Handle<Mesh>>,
9    _material_paths: std::collections::HashMap<String, Handle<Material>>,
10}
11
12impl Default for AssetServer {
13    fn default() -> Self {
14        Self::new()
15    }
16}
17
18impl AssetServer {
19    pub fn new() -> Self {
20        Self {
21            loader: AsyncAssetLoader::new(),
22            mesh_paths: std::collections::HashMap::new(),
23            _material_paths: std::collections::HashMap::new(),
24        }
25    }
26
27    pub fn load_mesh(&mut self, path: &str) -> Handle<Mesh> {
28        if let Some(handle) = self.mesh_paths.get(path) {
29            return handle.clone();
30        }
31        let handle = Handle::new(); // Generates a new HandleId
32        self.loader.request_obj_load(path.to_string(), handle.id.0);
33        self.mesh_paths.insert(path.to_string(), handle.clone());
34        handle
35    }
36}
37
38pub fn asset_server_update_system(
39    server: crate::core::system::ResMut<AssetServer>,
40    renderer: crate::core::system::ResMut<crate::renderer::Renderer>,
41    mut meshes: crate::core::system::ResMut<crate::core::asset::Assets<Mesh>>,
42) {
43    let completed = server.loader.drain_completed();
44
45    if completed.objs.is_empty() && completed.textures.is_empty() {
46        return;
47    }
48
49    for obj in completed.objs {
50        let mesh_source = format!("obj:{}", obj.path);
51        // Create wgpu buffer
52        let vbuf = renderer
53            .device
54            .create_buffer_init(&wgpu::util::BufferInitDescriptor {
55                label: Some(&format!("Obj VBuf: {}", obj.path)),
56                contents: bytemuck::cast_slice(&obj.vertices),
57                usage: wgpu::BufferUsages::VERTEX,
58            });
59        let mesh = Mesh::new(
60            &renderer.device,
61            std::sync::Arc::new(vbuf),
62            &obj.vertices,
63            gizmo_math::Vec3::ZERO,
64            mesh_source,
65        );
66        for handle_id in obj.handle_ids {
67            let handle = crate::core::asset::Handle::weak(crate::core::asset::HandleId(handle_id));
68            meshes.insert(&handle, mesh.clone());
69        }
70    }
71}
72
73pub struct AssetServerPlugin;
74
75impl<State: 'static> crate::app::Plugin<State> for AssetServerPlugin {
76    fn build(&self, app: &mut crate::app::App<State>) {
77        app.world.insert_resource(AssetServer::new());
78        app.schedule.add_di_system(asset_server_update_system);
79    }
80}