Path: blob/main/crates/bevy_pbr/src/meshlet/pipelines.rs
6600 views
use super::resource_manager::ResourceManager;1use bevy_asset::{load_embedded_asset, AssetServer, Handle};2use bevy_core_pipeline::{3core_3d::CORE_3D_DEPTH_FORMAT, experimental::mip_generation::DownsampleDepthShader,4FullscreenShader,5};6use bevy_ecs::{7resource::Resource,8system::{Commands, Res},9world::World,10};11use bevy_render::render_resource::*;12use bevy_shader::Shader;13use bevy_utils::default;1415#[derive(Resource)]16pub struct MeshletPipelines {17clear_visibility_buffer: CachedComputePipelineId,18clear_visibility_buffer_shadow_view: CachedComputePipelineId,19first_instance_cull: CachedComputePipelineId,20second_instance_cull: CachedComputePipelineId,21first_bvh_cull: CachedComputePipelineId,22second_bvh_cull: CachedComputePipelineId,23first_meshlet_cull: CachedComputePipelineId,24second_meshlet_cull: CachedComputePipelineId,25downsample_depth_first: CachedComputePipelineId,26downsample_depth_second: CachedComputePipelineId,27downsample_depth_first_shadow_view: CachedComputePipelineId,28downsample_depth_second_shadow_view: CachedComputePipelineId,29visibility_buffer_software_raster: CachedComputePipelineId,30visibility_buffer_software_raster_shadow_view: CachedComputePipelineId,31visibility_buffer_hardware_raster: CachedRenderPipelineId,32visibility_buffer_hardware_raster_shadow_view: CachedRenderPipelineId,33visibility_buffer_hardware_raster_shadow_view_unclipped: CachedRenderPipelineId,34resolve_depth: CachedRenderPipelineId,35resolve_depth_shadow_view: CachedRenderPipelineId,36resolve_material_depth: CachedRenderPipelineId,37remap_1d_to_2d_dispatch: Option<CachedComputePipelineId>,38fill_counts: CachedComputePipelineId,39pub(crate) meshlet_mesh_material: Handle<Shader>,40}4142pub fn init_meshlet_pipelines(43mut commands: Commands,44resource_manager: Res<ResourceManager>,45fullscreen_shader: Res<FullscreenShader>,46downsample_depth_shader: Res<DownsampleDepthShader>,47pipeline_cache: Res<PipelineCache>,48asset_server: Res<AssetServer>,49) {50let clear_visibility_buffer_bind_group_layout = resource_manager51.clear_visibility_buffer_bind_group_layout52.clone();53let clear_visibility_buffer_shadow_view_bind_group_layout = resource_manager54.clear_visibility_buffer_shadow_view_bind_group_layout55.clone();56let first_instance_cull_bind_group_layout = resource_manager57.first_instance_cull_bind_group_layout58.clone();59let second_instance_cull_bind_group_layout = resource_manager60.second_instance_cull_bind_group_layout61.clone();62let first_bvh_cull_bind_group_layout =63resource_manager.first_bvh_cull_bind_group_layout.clone();64let second_bvh_cull_bind_group_layout =65resource_manager.second_bvh_cull_bind_group_layout.clone();66let first_meshlet_cull_bind_group_layout = resource_manager67.first_meshlet_cull_bind_group_layout68.clone();69let second_meshlet_cull_bind_group_layout = resource_manager70.second_meshlet_cull_bind_group_layout71.clone();72let downsample_depth_layout = resource_manager.downsample_depth_bind_group_layout.clone();73let downsample_depth_shadow_view_layout = resource_manager74.downsample_depth_shadow_view_bind_group_layout75.clone();76let visibility_buffer_raster_layout = resource_manager77.visibility_buffer_raster_bind_group_layout78.clone();79let visibility_buffer_raster_shadow_view_layout = resource_manager80.visibility_buffer_raster_shadow_view_bind_group_layout81.clone();82let resolve_depth_layout = resource_manager.resolve_depth_bind_group_layout.clone();83let resolve_depth_shadow_view_layout = resource_manager84.resolve_depth_shadow_view_bind_group_layout85.clone();86let resolve_material_depth_layout = resource_manager87.resolve_material_depth_bind_group_layout88.clone();89let remap_1d_to_2d_dispatch_layout = resource_manager90.remap_1d_to_2d_dispatch_bind_group_layout91.clone();9293let downsample_depth_shader = (*downsample_depth_shader).clone();94let vertex_state = fullscreen_shader.to_vertex_state();95let fill_counts_layout = resource_manager.fill_counts_bind_group_layout.clone();9697let clear_visibility_buffer =98load_embedded_asset!(asset_server.as_ref(), "clear_visibility_buffer.wgsl");99let cull_instances = load_embedded_asset!(asset_server.as_ref(), "cull_instances.wgsl");100let cull_bvh = load_embedded_asset!(asset_server.as_ref(), "cull_bvh.wgsl");101let cull_clusters = load_embedded_asset!(asset_server.as_ref(), "cull_clusters.wgsl");102let visibility_buffer_software_raster = load_embedded_asset!(103asset_server.as_ref(),104"visibility_buffer_software_raster.wgsl"105);106let visibility_buffer_hardware_raster = load_embedded_asset!(107asset_server.as_ref(),108"visibility_buffer_hardware_raster.wgsl"109);110let resolve_render_targets =111load_embedded_asset!(asset_server.as_ref(), "resolve_render_targets.wgsl");112let remap_1d_to_2d_dispatch =113load_embedded_asset!(asset_server.as_ref(), "remap_1d_to_2d_dispatch.wgsl");114let fill_counts = load_embedded_asset!(asset_server.as_ref(), "fill_counts.wgsl");115let meshlet_mesh_material =116load_embedded_asset!(asset_server.as_ref(), "meshlet_mesh_material.wgsl");117118commands.insert_resource(MeshletPipelines {119clear_visibility_buffer: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {120label: Some("meshlet_clear_visibility_buffer_pipeline".into()),121layout: vec![clear_visibility_buffer_bind_group_layout],122push_constant_ranges: vec![PushConstantRange {123stages: ShaderStages::COMPUTE,124range: 0..8,125}],126shader: clear_visibility_buffer.clone(),127shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into()],128..default()129}),130131clear_visibility_buffer_shadow_view: pipeline_cache.queue_compute_pipeline(132ComputePipelineDescriptor {133label: Some("meshlet_clear_visibility_buffer_shadow_view_pipeline".into()),134layout: vec![clear_visibility_buffer_shadow_view_bind_group_layout],135push_constant_ranges: vec![PushConstantRange {136stages: ShaderStages::COMPUTE,137range: 0..8,138}],139shader: clear_visibility_buffer,140..default()141},142),143144first_instance_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {145label: Some("meshlet_first_instance_cull_pipeline".into()),146layout: vec![first_instance_cull_bind_group_layout.clone()],147push_constant_ranges: vec![PushConstantRange {148stages: ShaderStages::COMPUTE,149range: 0..4,150}],151shader: cull_instances.clone(),152shader_defs: vec![153"MESHLET_INSTANCE_CULLING_PASS".into(),154"MESHLET_FIRST_CULLING_PASS".into(),155],156..default()157}),158159second_instance_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {160label: Some("meshlet_second_instance_cull_pipeline".into()),161layout: vec![second_instance_cull_bind_group_layout.clone()],162push_constant_ranges: vec![PushConstantRange {163stages: ShaderStages::COMPUTE,164range: 0..4,165}],166shader: cull_instances,167shader_defs: vec![168"MESHLET_INSTANCE_CULLING_PASS".into(),169"MESHLET_SECOND_CULLING_PASS".into(),170],171..default()172}),173174first_bvh_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {175label: Some("meshlet_first_bvh_cull_pipeline".into()),176layout: vec![first_bvh_cull_bind_group_layout.clone()],177push_constant_ranges: vec![PushConstantRange {178stages: ShaderStages::COMPUTE,179range: 0..8,180}],181shader: cull_bvh.clone(),182shader_defs: vec![183"MESHLET_BVH_CULLING_PASS".into(),184"MESHLET_FIRST_CULLING_PASS".into(),185],186..default()187}),188189second_bvh_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {190label: Some("meshlet_second_bvh_cull_pipeline".into()),191layout: vec![second_bvh_cull_bind_group_layout.clone()],192push_constant_ranges: vec![PushConstantRange {193stages: ShaderStages::COMPUTE,194range: 0..8,195}],196shader: cull_bvh,197shader_defs: vec![198"MESHLET_BVH_CULLING_PASS".into(),199"MESHLET_SECOND_CULLING_PASS".into(),200],201..default()202}),203204first_meshlet_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {205label: Some("meshlet_first_meshlet_cull_pipeline".into()),206layout: vec![first_meshlet_cull_bind_group_layout.clone()],207push_constant_ranges: vec![PushConstantRange {208stages: ShaderStages::COMPUTE,209range: 0..4,210}],211shader: cull_clusters.clone(),212shader_defs: vec![213"MESHLET_CLUSTER_CULLING_PASS".into(),214"MESHLET_FIRST_CULLING_PASS".into(),215],216..default()217}),218219second_meshlet_cull: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {220label: Some("meshlet_second_meshlet_cull_pipeline".into()),221layout: vec![second_meshlet_cull_bind_group_layout.clone()],222push_constant_ranges: vec![PushConstantRange {223stages: ShaderStages::COMPUTE,224range: 0..4,225}],226shader: cull_clusters,227shader_defs: vec![228"MESHLET_CLUSTER_CULLING_PASS".into(),229"MESHLET_SECOND_CULLING_PASS".into(),230],231..default()232}),233234downsample_depth_first: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {235label: Some("meshlet_downsample_depth_first_pipeline".into()),236layout: vec![downsample_depth_layout.clone()],237push_constant_ranges: vec![PushConstantRange {238stages: ShaderStages::COMPUTE,239range: 0..4,240}],241shader: downsample_depth_shader.clone(),242shader_defs: vec![243"MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into(),244"MESHLET".into(),245],246entry_point: Some("downsample_depth_first".into()),247..default()248}),249250downsample_depth_second: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {251label: Some("meshlet_downsample_depth_second_pipeline".into()),252layout: vec![downsample_depth_layout.clone()],253push_constant_ranges: vec![PushConstantRange {254stages: ShaderStages::COMPUTE,255range: 0..4,256}],257shader: downsample_depth_shader.clone(),258shader_defs: vec![259"MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into(),260"MESHLET".into(),261],262entry_point: Some("downsample_depth_second".into()),263..default()264}),265266downsample_depth_first_shadow_view: pipeline_cache.queue_compute_pipeline(267ComputePipelineDescriptor {268label: Some("meshlet_downsample_depth_first_pipeline".into()),269layout: vec![downsample_depth_shadow_view_layout.clone()],270push_constant_ranges: vec![PushConstantRange {271stages: ShaderStages::COMPUTE,272range: 0..4,273}],274shader: downsample_depth_shader.clone(),275shader_defs: vec!["MESHLET".into()],276entry_point: Some("downsample_depth_first".into()),277..default()278},279),280281downsample_depth_second_shadow_view: pipeline_cache.queue_compute_pipeline(282ComputePipelineDescriptor {283label: Some("meshlet_downsample_depth_second_pipeline".into()),284layout: vec![downsample_depth_shadow_view_layout],285push_constant_ranges: vec![PushConstantRange {286stages: ShaderStages::COMPUTE,287range: 0..4,288}],289shader: downsample_depth_shader,290shader_defs: vec!["MESHLET".into()],291entry_point: Some("downsample_depth_second".into()),292zero_initialize_workgroup_memory: false,293},294),295296visibility_buffer_software_raster: pipeline_cache.queue_compute_pipeline(297ComputePipelineDescriptor {298label: Some("meshlet_visibility_buffer_software_raster_pipeline".into()),299layout: vec![visibility_buffer_raster_layout.clone()],300push_constant_ranges: vec![],301shader: visibility_buffer_software_raster.clone(),302shader_defs: vec![303"MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into(),304"MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into(),305if remap_1d_to_2d_dispatch_layout.is_some() {306"MESHLET_2D_DISPATCH"307} else {308""309}310.into(),311],312..default()313},314),315316visibility_buffer_software_raster_shadow_view: pipeline_cache.queue_compute_pipeline(317ComputePipelineDescriptor {318label: Some(319"meshlet_visibility_buffer_software_raster_shadow_view_pipeline".into(),320),321layout: vec![visibility_buffer_raster_shadow_view_layout.clone()],322push_constant_ranges: vec![],323shader: visibility_buffer_software_raster,324shader_defs: vec![325"MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into(),326if remap_1d_to_2d_dispatch_layout.is_some() {327"MESHLET_2D_DISPATCH"328} else {329""330}331.into(),332],333..default()334},335),336337visibility_buffer_hardware_raster: pipeline_cache.queue_render_pipeline(338RenderPipelineDescriptor {339label: Some("meshlet_visibility_buffer_hardware_raster_pipeline".into()),340layout: vec![visibility_buffer_raster_layout.clone()],341push_constant_ranges: vec![PushConstantRange {342stages: ShaderStages::VERTEX,343range: 0..4,344}],345vertex: VertexState {346shader: visibility_buffer_hardware_raster.clone(),347shader_defs: vec![348"MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into(),349"MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into(),350],351..default()352},353fragment: Some(FragmentState {354shader: visibility_buffer_hardware_raster.clone(),355shader_defs: vec![356"MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into(),357"MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into(),358],359targets: vec![Some(ColorTargetState {360format: TextureFormat::R8Uint,361blend: None,362write_mask: ColorWrites::empty(),363})],364..default()365}),366..default()367},368),369370visibility_buffer_hardware_raster_shadow_view: pipeline_cache.queue_render_pipeline(371RenderPipelineDescriptor {372label: Some(373"meshlet_visibility_buffer_hardware_raster_shadow_view_pipeline".into(),374),375layout: vec![visibility_buffer_raster_shadow_view_layout.clone()],376push_constant_ranges: vec![PushConstantRange {377stages: ShaderStages::VERTEX,378range: 0..4,379}],380vertex: VertexState {381shader: visibility_buffer_hardware_raster.clone(),382shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into()],383..default()384},385fragment: Some(FragmentState {386shader: visibility_buffer_hardware_raster.clone(),387shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into()],388targets: vec![Some(ColorTargetState {389format: TextureFormat::R8Uint,390blend: None,391write_mask: ColorWrites::empty(),392})],393..default()394}),395..default()396},397),398399visibility_buffer_hardware_raster_shadow_view_unclipped: pipeline_cache400.queue_render_pipeline(RenderPipelineDescriptor {401label: Some(402"meshlet_visibility_buffer_hardware_raster_shadow_view_unclipped_pipeline"403.into(),404),405layout: vec![visibility_buffer_raster_shadow_view_layout],406push_constant_ranges: vec![PushConstantRange {407stages: ShaderStages::VERTEX,408range: 0..4,409}],410vertex: VertexState {411shader: visibility_buffer_hardware_raster.clone(),412shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into()],413..default()414},415fragment: Some(FragmentState {416shader: visibility_buffer_hardware_raster,417shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS".into()],418targets: vec![Some(ColorTargetState {419format: TextureFormat::R8Uint,420blend: None,421write_mask: ColorWrites::empty(),422})],423..default()424}),425..default()426}),427428resolve_depth: pipeline_cache.queue_render_pipeline(RenderPipelineDescriptor {429label: Some("meshlet_resolve_depth_pipeline".into()),430layout: vec![resolve_depth_layout],431vertex: vertex_state.clone(),432depth_stencil: Some(DepthStencilState {433format: CORE_3D_DEPTH_FORMAT,434depth_write_enabled: true,435depth_compare: CompareFunction::Always,436stencil: StencilState::default(),437bias: DepthBiasState::default(),438}),439fragment: Some(FragmentState {440shader: resolve_render_targets.clone(),441shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into()],442entry_point: Some("resolve_depth".into()),443..default()444}),445..default()446}),447448resolve_depth_shadow_view: pipeline_cache.queue_render_pipeline(RenderPipelineDescriptor {449label: Some("meshlet_resolve_depth_pipeline".into()),450layout: vec![resolve_depth_shadow_view_layout],451vertex: vertex_state.clone(),452depth_stencil: Some(DepthStencilState {453format: CORE_3D_DEPTH_FORMAT,454depth_write_enabled: true,455depth_compare: CompareFunction::Always,456stencil: StencilState::default(),457bias: DepthBiasState::default(),458}),459fragment: Some(FragmentState {460shader: resolve_render_targets.clone(),461entry_point: Some("resolve_depth".into()),462..default()463}),464..default()465}),466467resolve_material_depth: pipeline_cache.queue_render_pipeline(RenderPipelineDescriptor {468label: Some("meshlet_resolve_material_depth_pipeline".into()),469layout: vec![resolve_material_depth_layout],470vertex: vertex_state,471primitive: PrimitiveState::default(),472depth_stencil: Some(DepthStencilState {473format: TextureFormat::Depth16Unorm,474depth_write_enabled: true,475depth_compare: CompareFunction::Always,476stencil: StencilState::default(),477bias: DepthBiasState::default(),478}),479fragment: Some(FragmentState {480shader: resolve_render_targets,481shader_defs: vec!["MESHLET_VISIBILITY_BUFFER_RASTER_PASS_OUTPUT".into()],482entry_point: Some("resolve_material_depth".into()),483targets: vec![],484}),485..default()486}),487488fill_counts: pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {489label: Some("meshlet_fill_counts_pipeline".into()),490layout: vec![fill_counts_layout],491shader: fill_counts,492shader_defs: vec![if remap_1d_to_2d_dispatch_layout.is_some() {493"MESHLET_2D_DISPATCH"494} else {495""496}497.into()],498..default()499}),500501remap_1d_to_2d_dispatch: remap_1d_to_2d_dispatch_layout.map(|layout| {502pipeline_cache.queue_compute_pipeline(ComputePipelineDescriptor {503label: Some("meshlet_remap_1d_to_2d_dispatch_pipeline".into()),504layout: vec![layout],505push_constant_ranges: vec![PushConstantRange {506stages: ShaderStages::COMPUTE,507range: 0..4,508}],509shader: remap_1d_to_2d_dispatch,510..default()511})512}),513514meshlet_mesh_material,515});516}517518impl MeshletPipelines {519pub fn get(520world: &World,521) -> Option<(522&ComputePipeline,523&ComputePipeline,524&ComputePipeline,525&ComputePipeline,526&ComputePipeline,527&ComputePipeline,528&ComputePipeline,529&ComputePipeline,530&ComputePipeline,531&ComputePipeline,532&ComputePipeline,533&ComputePipeline,534&ComputePipeline,535&ComputePipeline,536&RenderPipeline,537&RenderPipeline,538&RenderPipeline,539&RenderPipeline,540&RenderPipeline,541&RenderPipeline,542Option<&ComputePipeline>,543&ComputePipeline,544)> {545let pipeline_cache = world.get_resource::<PipelineCache>()?;546let pipeline = world.get_resource::<Self>()?;547Some((548pipeline_cache.get_compute_pipeline(pipeline.clear_visibility_buffer)?,549pipeline_cache.get_compute_pipeline(pipeline.clear_visibility_buffer_shadow_view)?,550pipeline_cache.get_compute_pipeline(pipeline.first_instance_cull)?,551pipeline_cache.get_compute_pipeline(pipeline.second_instance_cull)?,552pipeline_cache.get_compute_pipeline(pipeline.first_bvh_cull)?,553pipeline_cache.get_compute_pipeline(pipeline.second_bvh_cull)?,554pipeline_cache.get_compute_pipeline(pipeline.first_meshlet_cull)?,555pipeline_cache.get_compute_pipeline(pipeline.second_meshlet_cull)?,556pipeline_cache.get_compute_pipeline(pipeline.downsample_depth_first)?,557pipeline_cache.get_compute_pipeline(pipeline.downsample_depth_second)?,558pipeline_cache.get_compute_pipeline(pipeline.downsample_depth_first_shadow_view)?,559pipeline_cache.get_compute_pipeline(pipeline.downsample_depth_second_shadow_view)?,560pipeline_cache.get_compute_pipeline(pipeline.visibility_buffer_software_raster)?,561pipeline_cache562.get_compute_pipeline(pipeline.visibility_buffer_software_raster_shadow_view)?,563pipeline_cache.get_render_pipeline(pipeline.visibility_buffer_hardware_raster)?,564pipeline_cache565.get_render_pipeline(pipeline.visibility_buffer_hardware_raster_shadow_view)?,566pipeline_cache.get_render_pipeline(567pipeline.visibility_buffer_hardware_raster_shadow_view_unclipped,568)?,569pipeline_cache.get_render_pipeline(pipeline.resolve_depth)?,570pipeline_cache.get_render_pipeline(pipeline.resolve_depth_shadow_view)?,571pipeline_cache.get_render_pipeline(pipeline.resolve_material_depth)?,572match pipeline.remap_1d_to_2d_dispatch {573Some(id) => Some(pipeline_cache.get_compute_pipeline(id)?),574None => None,575},576pipeline_cache.get_compute_pipeline(pipeline.fill_counts)?,577))578}579}580581582