rafx_plugins/features/tile_layer/
tile_layer_resource.rs

1use super::{TileLayerRenderObject, TileLayerRenderObjectSet};
2use crate::assets::ldtk::LdtkProjectAsset;
3use glam::{Quat, Vec3};
4use hydrate_base::handle::Handle;
5use rafx::assets::AssetManager;
6use rafx::render_features::RenderObjectHandle;
7use rafx::visibility::{CullModel, ObjectId, VisibilityObjectArc, VisibilityResource};
8
9#[derive(Default)]
10pub struct TileLayerResource {
11    project: Option<Handle<LdtkProjectAsset>>,
12    render_objects: Vec<RenderObjectHandle>,
13    visibility_handles: Vec<VisibilityObjectArc>,
14}
15
16impl TileLayerResource {
17    pub fn project(&self) -> &Option<Handle<LdtkProjectAsset>> {
18        &self.project
19    }
20
21    pub fn render_objects(&self) -> &Vec<RenderObjectHandle> {
22        &self.render_objects
23    }
24
25    pub fn set_project(
26        &mut self,
27        project: &Handle<LdtkProjectAsset>,
28        asset_manager: &AssetManager,
29        tile_layer_render_object_set: &mut TileLayerRenderObjectSet,
30        visibility_resource: &mut VisibilityResource,
31    ) {
32        self.clear_project();
33        self.project = Some(project.clone());
34
35        let project_asset = asset_manager.committed_asset(project).unwrap();
36
37        let mut tile_layer_object_id: u64 = 0;
38        for (level_uid, level) in &project_asset.inner.levels {
39            for (layer_index, layer) in level.layers.iter().enumerate() {
40                if let (Some(vertex_buffer), Some(index_buffer)) =
41                    (&level.vertex_buffer, &level.index_buffer)
42                {
43                    let layer_data =
44                        &project_asset.inner.data.levels[level_uid].layer_data[layer_index];
45
46                    let render_object = tile_layer_render_object_set.register_render_object(
47                        TileLayerRenderObject {
48                            per_layer_descriptor_set: layer.per_layer_descriptor_set.clone(),
49                            draw_call_data: layer_data.draw_call_data.clone(),
50                            vertex_buffer: vertex_buffer.clone(),
51                            index_buffer: index_buffer.clone(),
52                            z_position: layer_data.z_pos,
53                        },
54                    );
55
56                    // NOTE(dvd): Not an actual entity, but necessary for the frame packet.
57                    tile_layer_object_id += 1;
58                    let handle = visibility_resource.register_static_object(
59                        ObjectId::from(tile_layer_object_id),
60                        CullModel::quad(layer.width as f32, layer.height as f32),
61                        vec![render_object.clone()],
62                    );
63                    let mut translation = layer.center;
64                    translation.y = -translation.y; // NOTE(dvd): +y is up in our world, but _down_ in LDtk.
65                    handle.set_transform(translation, Quat::IDENTITY, Vec3::ONE);
66
67                    self.visibility_handles.push(handle);
68                    self.render_objects.push(render_object);
69                }
70            }
71        }
72    }
73
74    pub fn clear_project(&mut self) {
75        self.project = None;
76        self.render_objects.clear();
77        self.visibility_handles.clear();
78    }
79}