Skip to content

Commit 740ae9a

Browse files
committed
remove mandatory mesh attributes (#6127)
# Objective - It's possible to create a mesh without positions or normals, but currently bevy forces these attributes to be present on any mesh. ## Solution - Don't assume these attributes are present and add a shader defs for each attributes - I updated 2d and 3d meshes to use the same logic. --- ## Changelog - Meshes don't require any attributes # Notes I didn't update the pbr.wgsl shader because I'm not sure how to handle it. It doesn't really make sense to use it without positions or normals.
1 parent aebd760 commit 740ae9a

File tree

4 files changed

+64
-12
lines changed

4 files changed

+64
-12
lines changed

crates/bevy_pbr/src/render/mesh.rs

+12-5
Original file line numberDiff line numberDiff line change
@@ -566,12 +566,19 @@ impl SpecializedMeshPipeline for MeshPipeline {
566566
key: Self::Key,
567567
layout: &MeshVertexBufferLayout,
568568
) -> Result<RenderPipelineDescriptor, SpecializedMeshPipelineError> {
569-
let mut vertex_attributes = vec![
570-
Mesh::ATTRIBUTE_POSITION.at_shader_location(0),
571-
Mesh::ATTRIBUTE_NORMAL.at_shader_location(1),
572-
];
573-
574569
let mut shader_defs = Vec::new();
570+
let mut vertex_attributes = Vec::new();
571+
572+
if layout.contains(Mesh::ATTRIBUTE_POSITION) {
573+
shader_defs.push(String::from("VERTEX_POSITIONS"));
574+
vertex_attributes.push(Mesh::ATTRIBUTE_POSITION.at_shader_location(0));
575+
}
576+
577+
if layout.contains(Mesh::ATTRIBUTE_NORMAL) {
578+
shader_defs.push(String::from("VERTEX_NORMALS"));
579+
vertex_attributes.push(Mesh::ATTRIBUTE_NORMAL.at_shader_location(1));
580+
}
581+
575582
if layout.contains(Mesh::ATTRIBUTE_UV_0) {
576583
shader_defs.push(String::from("VERTEX_UVS"));
577584
vertex_attributes.push(Mesh::ATTRIBUTE_UV_0.at_shader_location(2));

crates/bevy_pbr/src/render/mesh.wgsl

+14-1
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,12 @@
55
#import bevy_pbr::mesh_functions
66

77
struct Vertex {
8+
#ifdef VERTEX_POSITIONS
89
@location(0) position: vec3<f32>,
10+
#endif
11+
#ifdef VERTEX_NORMALS
912
@location(1) normal: vec3<f32>,
13+
#endif
1014
#ifdef VERTEX_UVS
1115
@location(2) uv: vec2<f32>,
1216
#endif
@@ -30,25 +34,34 @@ struct VertexOutput {
3034
@vertex
3135
fn vertex(vertex: Vertex) -> VertexOutput {
3236
var out: VertexOutput;
37+
38+
#ifdef VERTEX_NORMALS
3339
#ifdef SKINNED
3440
var model = skin_model(vertex.joint_indices, vertex.joint_weights);
3541
out.world_normal = skin_normals(model, vertex.normal);
3642
#else
3743
var model = mesh.model;
3844
out.world_normal = mesh_normal_local_to_world(vertex.normal);
3945
#endif
46+
#endif
47+
48+
#ifdef VERTEX_POSITIONS
4049
out.world_position = mesh_position_local_to_world(model, vec4<f32>(vertex.position, 1.0));
50+
out.clip_position = mesh_position_world_to_clip(out.world_position);
51+
#endif
52+
4153
#ifdef VERTEX_UVS
4254
out.uv = vertex.uv;
4355
#endif
56+
4457
#ifdef VERTEX_TANGENTS
4558
out.world_tangent = mesh_tangent_local_to_world(model, vertex.tangent);
4659
#endif
60+
4761
#ifdef VERTEX_COLORS
4862
out.color = vertex.color;
4963
#endif
5064

51-
out.clip_position = mesh_position_world_to_clip(out.world_position);
5265
return out;
5366
}
5467

crates/bevy_sprite/src/mesh2d/mesh.rs

+17-6
Original file line numberDiff line numberDiff line change
@@ -325,13 +325,24 @@ impl SpecializedMeshPipeline for Mesh2dPipeline {
325325
key: Self::Key,
326326
layout: &MeshVertexBufferLayout,
327327
) -> Result<RenderPipelineDescriptor, SpecializedMeshPipelineError> {
328-
let mut vertex_attributes = vec![
329-
Mesh::ATTRIBUTE_POSITION.at_shader_location(0),
330-
Mesh::ATTRIBUTE_NORMAL.at_shader_location(1),
331-
Mesh::ATTRIBUTE_UV_0.at_shader_location(2),
332-
];
333-
334328
let mut shader_defs = Vec::new();
329+
let mut vertex_attributes = Vec::new();
330+
331+
if layout.contains(Mesh::ATTRIBUTE_POSITION) {
332+
shader_defs.push(String::from("VERTEX_POSITIONS"));
333+
vertex_attributes.push(Mesh::ATTRIBUTE_POSITION.at_shader_location(0));
334+
}
335+
336+
if layout.contains(Mesh::ATTRIBUTE_NORMAL) {
337+
shader_defs.push(String::from("VERTEX_NORMALS"));
338+
vertex_attributes.push(Mesh::ATTRIBUTE_NORMAL.at_shader_location(1));
339+
}
340+
341+
if layout.contains(Mesh::ATTRIBUTE_UV_0) {
342+
shader_defs.push(String::from("VERTEX_UVS"));
343+
vertex_attributes.push(Mesh::ATTRIBUTE_UV_0.at_shader_location(2));
344+
}
345+
335346
if layout.contains(Mesh::ATTRIBUTE_TANGENT) {
336347
shader_defs.push(String::from("VERTEX_TANGENTS"));
337348
vertex_attributes.push(Mesh::ATTRIBUTE_TANGENT.at_shader_location(3));

crates/bevy_sprite/src/mesh2d/mesh2d.wgsl

+21
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,15 @@
55
#import bevy_sprite::mesh2d_functions
66

77
struct Vertex {
8+
#ifdef VERTEX_POSITIONS
89
@location(0) position: vec3<f32>,
10+
#endif
11+
#ifdef VERTEX_NORMALS
912
@location(1) normal: vec3<f32>,
13+
#endif
14+
#ifdef VERTEX_UVS
1015
@location(2) uv: vec2<f32>,
16+
#endif
1117
#ifdef VERTEX_TANGENTS
1218
@location(3) tangent: vec4<f32>,
1319
#endif
@@ -24,13 +30,24 @@ struct VertexOutput {
2430
@vertex
2531
fn vertex(vertex: Vertex) -> VertexOutput {
2632
var out: VertexOutput;
33+
34+
#ifdef VERTEX_UVS
2735
out.uv = vertex.uv;
36+
#endif
37+
38+
#ifdef VERTEX_POSITIONS
2839
out.world_position = mesh2d_position_local_to_world(mesh.model, vec4<f32>(vertex.position, 1.0));
2940
out.clip_position = mesh2d_position_world_to_clip(out.world_position);
41+
#endif
42+
43+
#ifdef VERTEX_NORMALS
3044
out.world_normal = mesh2d_normal_local_to_world(vertex.normal);
45+
#endif
46+
3147
#ifdef VERTEX_TANGENTS
3248
out.world_tangent = mesh2d_tangent_local_to_world(mesh.model, vertex.tangent);
3349
#endif
50+
3451
#ifdef VERTEX_COLORS
3552
out.color = vertex.color;
3653
#endif
@@ -44,5 +61,9 @@ struct FragmentInput {
4461

4562
@fragment
4663
fn fragment(in: FragmentInput) -> @location(0) vec4<f32> {
64+
#ifdef VERTEX_COLORS
65+
return in.color;
66+
#else
4767
return vec4<f32>(1.0, 0.0, 1.0, 1.0);
68+
#endif
4869
}

0 commit comments

Comments
 (0)