Skip to content

Commit

Permalink
refactor(image cache): ♻️ drop the use of multiple bind groups for on…
Browse files Browse the repository at this point in the history
…e monolithic bind group
  • Loading branch information
melody-rs committed Nov 30, 2023
1 parent 96cfa41 commit e003788
Show file tree
Hide file tree
Showing 23 changed files with 640 additions and 703 deletions.
8 changes: 0 additions & 8 deletions crates/components/src/command_view/command_ui.rs
Original file line number Diff line number Diff line change
Expand Up @@ -35,11 +35,3 @@ impl super::CommandView {
todo!()
}
}

fn parameter_label(
_string: &mut String,
_parameter: &luminol_data::commands::Parameter,
_command: &mut luminol_data::rpg::EventCommand,
) -> std::fmt::Result {
todo!()
}
4 changes: 2 additions & 2 deletions crates/components/src/tilepicker.rs
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ impl egui_wgpu::CallbackTrait for Callback {
render_pass: &mut wgpu::RenderPass<'a>,
_callback_resources: &'a egui_wgpu::CallbackResources,
) {
self.resources.viewport.bind(1, render_pass);
self.resources.tiles.draw(
&self.graphics_state,
&self.resources.viewport,
Expand All @@ -71,7 +70,6 @@ impl egui_wgpu::CallbackTrait for Callback {
);

if self.coll_enabled {
self.resources.viewport.bind(0, render_pass);
self.resources.collision.draw(
&self.graphics_state,
&self.resources.viewport,
Expand Down Expand Up @@ -153,6 +151,7 @@ impl Tilepicker {

let tiles = luminol_graphics::tiles::Tiles::new(
&update_state.graphics,
&viewport,
atlas,
&tilepicker_data,
update_state.graphics.push_constants_supported(),
Expand All @@ -176,6 +175,7 @@ impl Tilepicker {
.copy_from_slice(&tileset.passages.as_slice()[384..384 + length]);
let collision = luminol_graphics::collision::Collision::new(
&update_state.graphics,
&viewport,
&passages,
update_state.graphics.push_constants_supported(),
);
Expand Down
140 changes: 140 additions & 0 deletions crates/graphics/src/binding_helpers.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,140 @@
// Copyright (C) 2023 Lily Lyons
//
// This file is part of Luminol.
//
// Luminol is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
//
// Luminol is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with Luminol. If not, see <http://www.gnu.org/licenses/>.
//
// Additional permission under GNU GPL version 3 section 7
//
// If you modify this Program, or any covered work, by linking or combining
// it with Steamworks API by Valve Corporation, containing parts covered by
// terms of the Steamworks API by Valve Corporation, the licensors of this
// Program grant you additional permission to convey the resulting work.

pub struct BindGroupLayoutBuilder {
entries: Vec<wgpu::BindGroupLayoutEntry>,
}

impl Default for BindGroupLayoutBuilder {
fn default() -> Self {
Self::new()
}
}

impl BindGroupLayoutBuilder {
pub fn new() -> Self {
Self {
entries: Vec::new(),
}
}

pub fn append(
&mut self,
visibility: wgpu::ShaderStages,
ty: wgpu::BindingType,
count: Option<std::num::NonZeroU32>,
) -> &mut Self {
self.entries.push(wgpu::BindGroupLayoutEntry {
binding: self.entries.len() as u32,
visibility,
ty,
count,
});
self
}

#[must_use]
pub fn build(self, device: &wgpu::Device, label: wgpu::Label<'_>) -> wgpu::BindGroupLayout {
let descriptor = wgpu::BindGroupLayoutDescriptor {
label,
entries: &self.entries,
};
device.create_bind_group_layout(&descriptor)
}
}

pub struct BindGroupBuilder<'res> {
entries: Vec<wgpu::BindGroupEntry<'res>>,
}

impl<'res> Default for BindGroupBuilder<'res> {
fn default() -> Self {
Self::new()
}
}

impl<'res> BindGroupBuilder<'res> {
pub fn new() -> Self {
Self {
entries: Vec::new(),
}
}

pub fn append(&mut self, resource: wgpu::BindingResource<'res>) -> &mut Self {
self.entries.push(wgpu::BindGroupEntry {
binding: self.entries.len() as u32,
resource,
});
self
}

pub fn append_buffer(&mut self, buffer: &'res wgpu::Buffer) -> &mut Self {
self.append(buffer.as_entire_binding())
}

pub fn append_buffer_with_size(&mut self, buffer: &'res wgpu::Buffer, size: u64) -> &mut Self {
self.append(wgpu::BindingResource::Buffer(wgpu::BufferBinding {
buffer,
offset: 0,
size: std::num::NonZeroU64::new(size),
}))
}

pub fn append_sampler(&mut self, sampler: &'res wgpu::Sampler) -> &mut Self {
self.append(wgpu::BindingResource::Sampler(sampler))
}

pub fn append_sampler_array(
&mut self,
sampler_array: &'res [&'res wgpu::Sampler],
) -> &mut Self {
self.append(wgpu::BindingResource::SamplerArray(sampler_array))
}

pub fn append_texture_view(&mut self, texture: &'res wgpu::TextureView) -> &mut Self {
self.append(wgpu::BindingResource::TextureView(texture))
}

pub fn append_texture_view_array(
&mut self,
texture_view_array: &'res [&'res wgpu::TextureView],
) -> &mut Self {
self.append(wgpu::BindingResource::TextureViewArray(texture_view_array))
}

#[must_use]
pub fn build(
self,
device: &wgpu::Device,
label: wgpu::Label<'_>,
layout: &wgpu::BindGroupLayout,
) -> wgpu::BindGroup {
let descriptor = wgpu::BindGroupDescriptor {
label,
layout,
entries: &self.entries,
};
device.create_bind_group(&descriptor)
}
}
28 changes: 28 additions & 0 deletions crates/graphics/src/collision/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@
// You should have received a copy of the GNU General Public License
// along with Luminol. If not, see <http://www.gnu.org/licenses/>.

use crate::{
viewport::{self, Viewport},
BindGroupBuilder, BindGroupLayoutBuilder,
};

use instance::Instances;
use itertools::Itertools;
use vertex::Vertex;
Expand All @@ -26,6 +31,7 @@ mod vertex;
#[derive(Debug)]
pub struct Collision {
pub instances: Instances,
pub bind_group: wgpu::BindGroup,
pub use_push_constants: bool,
}

Expand Down Expand Up @@ -141,13 +147,25 @@ pub fn calculate_passage(layers: impl Iterator<Item = (i16, i16, CollisionType)>
impl Collision {
pub fn new(
graphics_state: &crate::GraphicsState,
viewport: &Viewport,
passages: &luminol_data::Table2,
use_push_constants: bool,
) -> Self {
let instances = Instances::new(&graphics_state.render_state, passages);

let mut bind_group_builder = BindGroupBuilder::new();
if use_push_constants {
bind_group_builder.append_buffer(viewport.as_buffer().unwrap());
}
let bind_group = bind_group_builder.build(
&graphics_state.render_state.device,
Some("collision bind group"),
&graphics_state.bind_group_layouts.tiles,
);

Self {
instances,
bind_group,
use_push_constants,
}
}
Expand Down Expand Up @@ -188,3 +206,13 @@ impl Collision {
render_pass.pop_debug_group();
}
}

pub fn create_bind_group_layout(render_state: &egui_wgpu::RenderState) -> wgpu::BindGroupLayout {
let mut builder = BindGroupLayoutBuilder::new();

if crate::push_constants_supported(render_state) {
viewport::add_to_bind_group_layout(&mut builder);
}

builder.build(&render_state.device, Some("collision bind group layout"))
}
40 changes: 21 additions & 19 deletions crates/graphics/src/collision/shader.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,29 +55,31 @@ pub fn create_render_pipeline(
source: wgpu::ShaderSource::Naga(std::borrow::Cow::Owned(module)),
});

let pipeline_layout = if crate::push_constants_supported(render_state) {
render_state
.device
.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
label: Some("Tilemap Collision Render Pipeline Layout (push constants)"),
bind_group_layouts: &[],
push_constant_ranges: &[
// Viewport
wgpu::PushConstantRange {
stages: wgpu::ShaderStages::VERTEX,
range: 0..64,
},
],
})
let push_constant_ranges: &[_] = if push_constants_supported {
&[
// Viewport
wgpu::PushConstantRange {
stages: wgpu::ShaderStages::VERTEX,
range: 0..64,
},
]
} else {
&[]
};
let label = if push_constants_supported {
"Tilemap Collision Render Pipeline Layout (push constants)"
} else {
"Tilemap Collision Render Pipeline Layout (uniforms)"
};

let pipeline_layout =
render_state
.device
.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
label: Some("Tilemap Collision Render Pipeline Layout (uniforms)"),
bind_group_layouts: &[&bind_group_layouts.viewport],
push_constant_ranges: &[],
})
};
label: Some(label),
bind_group_layouts: &[&bind_group_layouts.collision],
push_constant_ranges,
});

render_state
.device
Expand Down
13 changes: 7 additions & 6 deletions crates/graphics/src/event.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@

use std::sync::Arc;

use crate::{sprite::Sprite, viewport::Viewport, GraphicsState};

#[derive(Debug)]
pub struct Event {
resources: Arc<Resources>,
Expand All @@ -25,13 +27,13 @@ pub struct Event {

#[derive(Debug)]
struct Resources {
sprite: crate::sprite::Sprite,
viewport: crate::viewport::Viewport,
sprite: Sprite,
viewport: Viewport,
}

struct Callback {
resources: Arc<Resources>,
graphics_state: Arc<crate::GraphicsState>,
graphics_state: Arc<GraphicsState>,
}

//? SAFETY:
Expand All @@ -49,7 +51,6 @@ impl egui_wgpu::CallbackTrait for Callback {
render_pass: &mut wgpu::RenderPass<'a>,
_callback_resources: &'a egui_wgpu::CallbackResources,
) {
self.resources.viewport.bind(1, render_pass);
self.resources
.sprite
.draw(&self.graphics_state, &self.resources.viewport, render_pass);
Expand All @@ -70,8 +71,7 @@ impl Event {
};

let texture = if let Some(ref filename) = page.graphic.character_name {
graphics_state.image_cache.load_wgpu_image(
graphics_state,
graphics_state.texture_loader.load_now_dir(
filesystem,
"Graphics/Characters",
filename,
Expand Down Expand Up @@ -125,6 +125,7 @@ impl Event {

let sprite = crate::sprite::Sprite::new(
graphics_state,
&viewport,
quads,
texture,
page.graphic.blend_type,
Expand Down
Loading

0 comments on commit e003788

Please sign in to comment.