From 047f75917dc963d2ee92cb6d3d3dca1c3aea5854 Mon Sep 17 00:00:00 2001 From: HampusM Date: Wed, 16 Sep 2026 15:48:15 +0200 Subject: fix(engine): disable old mesh vertex attrs even if not consecutive --- .../src/rendering/backend/opengl/graphics_mesh.rs | 60 ++++++---------------- engine/src/util.rs | 45 +--------------- 2 files changed, 18 insertions(+), 87 deletions(-) diff --git a/engine/src/rendering/backend/opengl/graphics_mesh.rs b/engine/src/rendering/backend/opengl/graphics_mesh.rs index 29ae01a..a3f4197 100644 --- a/engine/src/rendering/backend/opengl/graphics_mesh.rs +++ b/engine/src/rendering/backend/opengl/graphics_mesh.rs @@ -17,7 +17,6 @@ use crate::rendering::shader::{ VertexInputSemName, }; use crate::rendering::MeshUsage; -use crate::util::DisplaySlice; const VERTEX_BUF_BINDING_INDEX: u32 = 0; @@ -27,7 +26,7 @@ pub struct GraphicsMesh /// Vertex and index buffer has to live as long as the vertex array vertex_buffer: GlBuffer, vertex_attr_props: Vec, - last_used_vertex_attr_cnt: u32, + last_max_vertex_attr_index: u32, pub index_buffer: Option>, pub element_cnt: u32, pub vertex_arr: GlVertexArray, @@ -89,7 +88,7 @@ impl GraphicsMesh return Ok(Self { vertex_buffer: vertex_buffer, vertex_attr_props: mesh.vertex_buf().vertex_attr_props().to_vec(), - last_used_vertex_attr_cnt: 0, + last_max_vertex_attr_index: 0, index_buffer: Some(index_buffer), element_cnt: indices .len() @@ -102,7 +101,7 @@ impl GraphicsMesh Ok(Self { vertex_buffer: vertex_buffer, vertex_attr_props: mesh.vertex_buf().vertex_attr_props().to_vec(), - last_used_vertex_attr_cnt: 0, + last_max_vertex_attr_index: 0, index_buffer: None, element_cnt: mesh .vertex_buf() @@ -161,26 +160,24 @@ impl GraphicsMesh shader_vertex_desc: &ShaderVertexDescription, ) -> Result<(), VertexAttrsUpdatingError> { - let vertex_input_cnt = u32::try_from(shader_vertex_desc.inputs.len()) - .expect("Shader has too many vertex inputs. Count does not fit into u32"); - - if self.last_used_vertex_attr_cnt > vertex_input_cnt { - for index in vertex_input_cnt..self.last_used_vertex_attr_cnt { - self.vertex_arr.disable_attrib(curr_gl_ctx, index); - } + for index in 0..self.last_max_vertex_attr_index { + self.vertex_arr.disable_attrib(curr_gl_ctx, index); } - let mut used_vertex_attr_cnt = 0u32; + let mut max_vertex_attr_index = 0u32; - for vertex_attr_props in &self.vertex_attr_props { - let Some(vertex_input_desc) = - shader_vertex_desc.inputs.iter().find(|vertex_input_desc| { + for vertex_input_desc in &*shader_vertex_desc.inputs { + let Some(vertex_attr_props) = + self.vertex_attr_props.iter().find(|vertex_attr_props| { vertex_input_desc .semantic_name .matches_vertex_label(&vertex_attr_props.label) }) else { - continue; + cold_path(); + return Err(VertexAttrsUpdatingError::MissingVertexAttr( + vertex_input_desc.semantic_name.clone(), + )); }; let attrib_index: u32 = vertex_input_desc.index.try_into().unwrap(); @@ -214,32 +211,10 @@ impl GraphicsMesh VERTEX_BUF_BINDING_INDEX, ); - used_vertex_attr_cnt += 1; + max_vertex_attr_index = max_vertex_attr_index.max(attrib_index); } - self.last_used_vertex_attr_cnt = used_vertex_attr_cnt; - - if used_vertex_attr_cnt as usize != shader_vertex_desc.inputs.len() { - cold_path(); - - return Err(VertexAttrsUpdatingError::MissingVertexAttrs( - shader_vertex_desc - .inputs - .iter() - .filter_map(|vertex_input_desc| { - if self.vertex_attr_props.iter().any(|props| { - vertex_input_desc - .semantic_name - .matches_vertex_label(&props.label) - }) { - return None; - } - - Some(vertex_input_desc.semantic_name.clone()) - }) - .collect(), - )); - } + self.last_max_vertex_attr_index = max_vertex_attr_index; Ok(()) } @@ -269,10 +244,9 @@ pub enum Error pub enum VertexAttrsUpdatingError { #[error( - "Mesh is missing equivalent vertex attribute(s) for shader's vertex inputs: {}", - DisplaySlice::new(.0) + "Mesh is missing equivalent vertex attribute for shader's vertex input: {0}" )] - MissingVertexAttrs(Vec), + MissingVertexAttr(VertexInputSemName), } fn mesh_usage_to_gl_buffer_usage(mesh_usage: MeshUsage) -> GlBufferUsage diff --git a/engine/src/util.rs b/engine/src/util.rs index a7caa2a..f016ad3 100644 --- a/engine/src/util.rs +++ b/engine/src/util.rs @@ -1,4 +1,4 @@ -use std::fmt::{Debug, Display}; +use std::fmt::Debug; use crate::ecs::util::StreamingIterator; @@ -28,49 +28,6 @@ impl OptionExt for Option } } -pub struct DisplaySlice<'a, Item> -{ - slice: &'a [Item], -} - -impl<'a, Item> DisplaySlice<'a, Item> -{ - pub fn new(slice: &'a [Item]) -> Self - { - Self { slice } - } -} - -impl Display for DisplaySlice<'_, Item> -where - Item: Display, -{ - fn fmt(&self, formatter: &mut std::fmt::Formatter<'_>) -> std::fmt::Result - { - let Some(first_item) = self.slice.first() else { - return formatter.write_str(""); - }; - - write!(formatter, "{first_item}")?; - - if self.slice.len() == 1 { - return Ok(()); - } - - for item in &self.slice[1..self.slice.len() - 1] { - write!(formatter, ", {item}")?; - } - - let Some(last_item) = self.slice.last() else { - unreachable!(); - }; - - write!(formatter, " & {last_item}")?; - - Ok(()) - } -} - #[derive(Debug)] pub struct BitArray { -- cgit v1.2.3-18-g5258