diff --git a/source/blender/draw/engines/eevee_next/eevee_ambient_occlusion.cc b/source/blender/draw/engines/eevee_next/eevee_ambient_occlusion.cc index 417727657cb..6ca02087340 100644 --- a/source/blender/draw/engines/eevee_next/eevee_ambient_occlusion.cc +++ b/source/blender/draw/engines/eevee_next/eevee_ambient_occlusion.cc @@ -56,9 +56,9 @@ void AmbientOcclusion::sync() render_pass_ps_.shader_set(inst_.shaders.static_shader_get(AMBIENT_OCCLUSION_PASS)); render_pass_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, &inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&render_pass_ps_); - inst_.sampling.bind_resources(render_pass_ps_); - inst_.hiz_buffer.bind_resources(render_pass_ps_); + render_pass_ps_.bind_resources(inst_.uniform_data); + render_pass_ps_.bind_resources(inst_.sampling); + render_pass_ps_.bind_resources(inst_.hiz_buffer.front); render_pass_ps_.bind_image("in_normal_img", &inst_.render_buffers.rp_color_tx); render_pass_ps_.push_constant("in_normal_img_layer_index", &inst_.render_buffers.data.normal_id); diff --git a/source/blender/draw/engines/eevee_next/eevee_depth_of_field.cc b/source/blender/draw/engines/eevee_next/eevee_depth_of_field.cc index 060280ec918..7862b1cf9c9 100644 --- a/source/blender/draw/engines/eevee_next/eevee_depth_of_field.cc +++ b/source/blender/draw/engines/eevee_next/eevee_depth_of_field.cc @@ -359,7 +359,7 @@ void DepthOfField::gather_pass_sync() DOF_GATHER_FOREGROUND) : (use_bokeh_lut_ ? DOF_GATHER_BACKGROUND_LUT : DOF_GATHER_BACKGROUND); drw_pass.init(); - inst_.sampling.bind_resources(drw_pass); + drw_pass.bind_resources(inst_.sampling); drw_pass.shader_set(inst_.shaders.static_shader_get(sh_type)); drw_pass.bind_ubo("dof_buf", data_); drw_pass.bind_texture("color_bilinear_tx", reduced_color_tx_, gather_bilinear); @@ -423,7 +423,7 @@ void DepthOfField::hole_fill_pass_sync() const GPUSamplerState gather_nearest = {GPU_SAMPLER_FILTERING_MIPMAP}; hole_fill_ps_.init(); - inst_.sampling.bind_resources(hole_fill_ps_); + hole_fill_ps_.bind_resources(inst_.sampling); hole_fill_ps_.shader_set(inst_.shaders.static_shader_get(DOF_GATHER_HOLE_FILL)); hole_fill_ps_.bind_ubo("dof_buf", data_); hole_fill_ps_.bind_texture("color_bilinear_tx", reduced_color_tx_, gather_bilinear); @@ -444,7 +444,7 @@ void DepthOfField::resolve_pass_sync() eShaderType sh_type = use_bokeh_lut_ ? DOF_RESOLVE_LUT : DOF_RESOLVE; resolve_ps_.init(); - inst_.sampling.bind_resources(resolve_ps_); + resolve_ps_.bind_resources(inst_.sampling); resolve_ps_.shader_set(inst_.shaders.static_shader_get(sh_type)); resolve_ps_.bind_ubo("dof_buf", data_); resolve_ps_.bind_texture("depth_tx", &render_buffers.depth_tx, no_filter); diff --git a/source/blender/draw/engines/eevee_next/eevee_film.cc b/source/blender/draw/engines/eevee_next/eevee_film.cc index 915a7ebe689..adb76a6c150 100644 --- a/source/blender/draw/engines/eevee_next/eevee_film.cc +++ b/source/blender/draw/engines/eevee_next/eevee_film.cc @@ -426,7 +426,7 @@ void Film::sync() accumulate_ps_.init(); accumulate_ps_.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_ALWAYS); accumulate_ps_.shader_set(inst_.shaders.static_shader_get(shader)); - inst_.bind_uniform_data(&accumulate_ps_); + accumulate_ps_.bind_resources(inst_.uniform_data); accumulate_ps_.bind_ubo("camera_prev", &(*velocity.camera_steps[STEP_PREVIOUS])); accumulate_ps_.bind_ubo("camera_curr", &(*velocity.camera_steps[STEP_CURRENT])); accumulate_ps_.bind_ubo("camera_next", &(*velocity.camera_steps[step_next])); @@ -637,7 +637,7 @@ void Film::accumulate(View &view, GPUTexture *combined_final_tx) combined_final_tx_ = combined_final_tx; data_.display_only = false; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); inst_.manager->submit(accumulate_ps_, view); @@ -664,7 +664,7 @@ void Film::display() combined_final_tx_ = inst_.render_buffers.combined_tx; data_.display_only = true; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); draw::View drw_view("MainView", DRW_view_default_get()); diff --git a/source/blender/draw/engines/eevee_next/eevee_hizbuffer.cc b/source/blender/draw/engines/eevee_next/eevee_hizbuffer.cc index 8752b28b537..166e8b09bd1 100644 --- a/source/blender/draw/engines/eevee_next/eevee_hizbuffer.cc +++ b/source/blender/draw/engines/eevee_next/eevee_hizbuffer.cc @@ -80,7 +80,7 @@ void HiZBuffer::sync() debug_draw_ps_.init(); debug_draw_ps_.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND_CUSTOM); debug_draw_ps_.shader_set(inst_.shaders.static_shader_get(HIZ_DEBUG)); - this->bind_resources(debug_draw_ps_); + debug_draw_ps_.bind_resources(this->front); debug_draw_ps_.draw_procedural(GPU_PRIM_TRIS, 1, 3); } } diff --git a/source/blender/draw/engines/eevee_next/eevee_hizbuffer.hh b/source/blender/draw/engines/eevee_next/eevee_hizbuffer.hh index 6243728b35c..a0837b21320 100644 --- a/source/blender/draw/engines/eevee_next/eevee_hizbuffer.hh +++ b/source/blender/draw/engines/eevee_next/eevee_hizbuffer.hh @@ -30,11 +30,6 @@ class HiZBuffer { /** Contains depth pyramid of the current pass and the previous pass. */ SwapChain hiz_tx_; - /** References to the textures in the swap-chain. */ - /* Closest surface depth of the current layer. */ - GPUTexture *hiz_front_ref_tx_ = nullptr; - /* Closest surface depth of the layer below. */ - GPUTexture *hiz_back_ref_tx_ = nullptr; /** References to the mip views of the current (front) HiZ texture. */ std::array hiz_mip_ref_; @@ -87,8 +82,8 @@ class HiZBuffer { void swap_layer() { hiz_tx_.swap(); - hiz_back_ref_tx_ = hiz_tx_.previous(); - hiz_front_ref_tx_ = hiz_tx_.current(); + back.ref_tx_ = hiz_tx_.previous(); + front.ref_tx_ = hiz_tx_.current(); set_dirty(); } @@ -109,18 +104,16 @@ class HiZBuffer { void debug_draw(View &view, GPUFrameBuffer *view_fb); - enum class Type { - /* Previous layer depth (ex: For refraction). */ - BACK, - /* Previous layer depth. */ - FRONT, - }; + /* Back is Previous layer depth (ex: For refraction). Front for current layer depth. */ + struct { + /** References to the textures in the swap-chain. */ + GPUTexture *ref_tx_ = nullptr; - template void bind_resources(PassType &pass, Type type = Type::FRONT) - { - pass.bind_texture(HIZ_TEX_SLOT, - (type == Type::FRONT) ? &hiz_front_ref_tx_ : &hiz_back_ref_tx_); - } + template void bind_resources(PassType &pass) + { + pass.bind_texture(HIZ_TEX_SLOT, &ref_tx_); + } + } front, back; }; /** \} */ diff --git a/source/blender/draw/engines/eevee_next/eevee_instance.cc b/source/blender/draw/engines/eevee_next/eevee_instance.cc index 224b7958cea..13493ef5da3 100644 --- a/source/blender/draw/engines/eevee_next/eevee_instance.cc +++ b/source/blender/draw/engines/eevee_next/eevee_instance.cc @@ -292,7 +292,7 @@ void Instance::end_sync() reflection_probes.end_sync(); planar_probes.end_sync(); - global_ubo_.push_update(); + uniform_data.push_update(); depsgraph_last_update_ = DEG_get_update_count(depsgraph); } diff --git a/source/blender/draw/engines/eevee_next/eevee_instance.hh b/source/blender/draw/engines/eevee_next/eevee_instance.hh index 1aa1fc87a9a..e0074e47f27 100644 --- a/source/blender/draw/engines/eevee_next/eevee_instance.hh +++ b/source/blender/draw/engines/eevee_next/eevee_instance.hh @@ -44,6 +44,21 @@ namespace blender::eevee { +/* Combines data from several modules to avoid wasting binding slots. */ +struct UniformDataModule { + UniformDataBuf data; + + void push_update() + { + data.push_update(); + } + + template void bind_resources(PassType &pass) + { + pass.bind_ubo(UNIFORM_BUF_SLOT, &data); + } +}; + /** * \class Instance * \brief A running instance of the engine. @@ -52,14 +67,13 @@ class Instance { friend VelocityModule; friend MotionBlurModule; - UniformDataBuf global_ubo_; - uint64_t depsgraph_last_update_ = 0; bool overlays_enabled_; public: ShaderModule &shaders; SyncModule sync; + UniformDataModule uniform_data; MaterialModule materials; SubsurfaceModule subsurface; PipelineModule pipelines; @@ -120,23 +134,23 @@ class Instance { : shaders(*ShaderModule::module_get()), sync(*this), materials(*this), - subsurface(*this, global_ubo_.subsurface), - pipelines(*this, global_ubo_.pipeline), - shadows(*this, global_ubo_.shadow), + subsurface(*this, uniform_data.data.subsurface), + pipelines(*this, uniform_data.data.pipeline), + shadows(*this, uniform_data.data.shadow), lights(*this), - ambient_occlusion(*this, global_ubo_.ao), - raytracing(*this, global_ubo_.raytrace), + ambient_occlusion(*this, uniform_data.data.ao), + raytracing(*this, uniform_data.data.raytrace), reflection_probes(*this), planar_probes(*this), velocity(*this), motion_blur(*this), depth_of_field(*this), cryptomatte(*this), - hiz_buffer(*this, global_ubo_.hiz), + hiz_buffer(*this, uniform_data.data.hiz), sampling(*this), - camera(*this, global_ubo_.camera), - film(*this, global_ubo_.film), - render_buffers(*this, global_ubo_.render_pass), + camera(*this, uniform_data.data.camera), + film(*this, uniform_data.data.film), + render_buffers(*this, uniform_data.data.render_pass), main_view(*this), capture_view(*this), world(*this), @@ -144,7 +158,7 @@ class Instance { lookdev(*this), light_probes(*this), irradiance_cache(*this), - volume(*this, global_ubo_.volumes){}; + volume(*this, uniform_data.data.volumes){}; ~Instance(){}; /* Render & Viewport. */ @@ -239,16 +253,6 @@ class Instance { ((v3d->shading.type == OB_MATERIAL) && (v3d->overlay.flag & V3D_OVERLAY_LOOK_DEV)); } - void push_uniform_data() - { - global_ubo_.push_update(); - } - - template void bind_uniform_data(draw::detail::PassBase *pass) - { - pass->bind_ubo(UNIFORM_BUF_SLOT, &global_ubo_); - } - int get_recalc_flags(const ObjectRef &ob_ref) { auto get_flags = [&](const ObjectRuntimeHandle &runtime) { diff --git a/source/blender/draw/engines/eevee_next/eevee_irradiance_cache.cc b/source/blender/draw/engines/eevee_next/eevee_irradiance_cache.cc index c40cc909057..1f6cf59adee 100644 --- a/source/blender/draw/engines/eevee_next/eevee_irradiance_cache.cc +++ b/source/blender/draw/engines/eevee_next/eevee_irradiance_cache.cc @@ -650,8 +650,8 @@ void IrradianceBake::sync() pass.bind_ssbo(SURFEL_BUF_SLOT, &surfels_buf_); pass.bind_ssbo(CAPTURE_BUF_SLOT, &capture_info_buf_); pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.lights.bind_resources(pass); - inst_.shadows.bind_resources(pass); + pass.bind_resources(inst_.lights); + pass.bind_resources(inst_.shadows); /* Sync with the surfel creation stage. */ pass.barrier(GPU_BARRIER_SHADER_STORAGE); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); @@ -701,7 +701,7 @@ void IrradianceBake::sync() sub.shader_set(inst_.shaders.static_shader_get(SURFEL_RAY)); sub.bind_ssbo(SURFEL_BUF_SLOT, &surfels_buf_); sub.bind_ssbo(CAPTURE_BUF_SLOT, &capture_info_buf_); - inst_.reflection_probes.bind_resources(sub); + sub.bind_resources(inst_.reflection_probes); sub.push_constant("radiance_src", &radiance_src_); sub.push_constant("radiance_dst", &radiance_dst_); sub.barrier(GPU_BARRIER_SHADER_STORAGE); @@ -714,7 +714,7 @@ void IrradianceBake::sync() pass.shader_set(inst_.shaders.static_shader_get(LIGHTPROBE_IRRADIANCE_RAY)); pass.bind_ssbo(SURFEL_BUF_SLOT, &surfels_buf_); pass.bind_ssbo(CAPTURE_BUF_SLOT, &capture_info_buf_); - inst_.reflection_probes.bind_resources(pass); + pass.bind_resources(inst_.reflection_probes); pass.bind_ssbo("list_start_buf", &list_start_buf_); pass.bind_ssbo("list_info_buf", &list_info_buf_); pass.push_constant("radiance_src", &radiance_src_); diff --git a/source/blender/draw/engines/eevee_next/eevee_light.cc b/source/blender/draw/engines/eevee_next/eevee_light.cc index c4540c36281..0beb489270d 100644 --- a/source/blender/draw/engines/eevee_next/eevee_light.cc +++ b/source/blender/draw/engines/eevee_next/eevee_light.cc @@ -439,8 +439,8 @@ void LightModule::debug_pass_sync() debug_draw_ps_.init(); debug_draw_ps_.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND_CUSTOM); debug_draw_ps_.shader_set(inst_.shaders.static_shader_get(LIGHT_CULLING_DEBUG)); - inst_.bind_uniform_data(&debug_draw_ps_); - inst_.hiz_buffer.bind_resources(debug_draw_ps_); + debug_draw_ps_.bind_resources(inst_.uniform_data); + debug_draw_ps_.bind_resources(inst_.hiz_buffer.front); debug_draw_ps_.bind_ssbo("light_buf", &culling_light_buf_); debug_draw_ps_.bind_ssbo("light_cull_buf", &culling_data_buf_); debug_draw_ps_.bind_ssbo("light_zbin_buf", &culling_zbin_buf_); diff --git a/source/blender/draw/engines/eevee_next/eevee_lookdev.cc b/source/blender/draw/engines/eevee_next/eevee_lookdev.cc index 2d86442179f..f0522db8a10 100644 --- a/source/blender/draw/engines/eevee_next/eevee_lookdev.cc +++ b/source/blender/draw/engines/eevee_next/eevee_lookdev.cc @@ -233,13 +233,13 @@ void LookdevModule::sync_pass(PassSimple &pass, pass.bind_image("rp_value_img", dummy_aov_value_tx_); pass.bind_image("aov_color_img", dummy_aov_color_tx_); pass.bind_image("aov_value_img", dummy_aov_value_tx_); - inst_.bind_uniform_data(&pass); - inst_.hiz_buffer.bind_resources(pass); - inst_.reflection_probes.bind_resources(pass); - inst_.irradiance_cache.bind_resources(pass); - inst_.shadows.bind_resources(pass); - inst_.volume.bind_resources(pass); - inst_.cryptomatte.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.hiz_buffer.front); + pass.bind_resources(inst_.reflection_probes); + pass.bind_resources(inst_.irradiance_cache); + pass.bind_resources(inst_.shadows); + pass.bind_resources(inst_.volume.result); + pass.bind_resources(inst_.cryptomatte); pass.draw(geom, res_handle, 0); } diff --git a/source/blender/draw/engines/eevee_next/eevee_motion_blur.cc b/source/blender/draw/engines/eevee_next/eevee_motion_blur.cc index ec3ddff74e0..253af021a7f 100644 --- a/source/blender/draw/engines/eevee_next/eevee_motion_blur.cc +++ b/source/blender/draw/engines/eevee_next/eevee_motion_blur.cc @@ -140,8 +140,8 @@ void MotionBlurModule::sync() RenderBuffers &render_buffers = inst_.render_buffers; motion_blur_ps_.init(); - inst_.velocity.bind_resources(motion_blur_ps_); - inst_.sampling.bind_resources(motion_blur_ps_); + motion_blur_ps_.bind_resources(inst_.velocity); + motion_blur_ps_.bind_resources(inst_.sampling); { /* Create max velocity tiles. */ PassSimple::Sub &sub = motion_blur_ps_.sub("TilesFlatten"); diff --git a/source/blender/draw/engines/eevee_next/eevee_pipeline.cc b/source/blender/draw/engines/eevee_next/eevee_pipeline.cc index cd0977aa9d3..54b67a738a5 100644 --- a/source/blender/draw/engines/eevee_next/eevee_pipeline.cc +++ b/source/blender/draw/engines/eevee_next/eevee_pipeline.cc @@ -41,8 +41,8 @@ void BackgroundPipeline::sync(GPUMaterial *gpumat, const float background_opacit world_ps_.bind_image("rp_value_img", &rbufs.rp_value_tx); world_ps_.bind_image("rp_cryptomatte_img", &rbufs.cryptomatte_tx); /* Required by validation layers. */ - inst_.cryptomatte.bind_resources(world_ps_); - inst_.bind_uniform_data(&world_ps_); + world_ps_.bind_resources(inst_.cryptomatte); + world_ps_.bind_resources(inst_.uniform_data); world_ps_.draw_procedural(GPU_PRIM_TRIS, 1, 3); /* To allow opaque pass rendering over it. */ world_ps_.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); @@ -89,8 +89,8 @@ void WorldPipeline::sync(GPUMaterial *gpumat) pass.bind_image("aov_value_img", dummy_aov_value_tx_); pass.bind_ssbo("aov_buf", &inst_.film.aovs_info); /* Required by validation layers. */ - inst_.cryptomatte.bind_resources(pass); - inst_.bind_uniform_data(&pass); + pass.bind_resources(inst_.cryptomatte); + pass.bind_resources(inst_.uniform_data); pass.draw_procedural(GPU_PRIM_TRIS, 1, 3); } @@ -98,10 +98,10 @@ void WorldPipeline::render(View &view) { /* TODO(Miguel Pozo): All world probes are rendered as RAY_TYPE_GLOSSY. */ inst_.pipelines.data.is_probe_reflection = true; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); inst_.manager->submit(cubemap_face_ps_, view); inst_.pipelines.data.is_probe_reflection = false; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); } /** \} */ @@ -122,9 +122,9 @@ void WorldVolumePipeline::sync(GPUMaterial *gpumat) world_ps_.init(); world_ps_.state_set(DRW_STATE_WRITE_COLOR); world_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&world_ps_); - inst_.volume.bind_properties_buffers(world_ps_); - inst_.sampling.bind_resources(world_ps_); + world_ps_.bind_resources(inst_.uniform_data); + world_ps_.bind_resources(inst_.volume.properties); + world_ps_.bind_resources(inst_.sampling); world_ps_.material_set(*inst_.manager, gpumat); volume_sub_pass(world_ps_, nullptr, nullptr, gpumat); @@ -191,8 +191,8 @@ void ShadowPipeline::sync() pass.bind_ssbo(SHADOW_RENDER_MAP_BUF_SLOT, &inst_.shadows.render_map_buf_); pass.bind_ssbo(SHADOW_PAGE_INFO_SLOT, &inst_.shadows.pages_infos_data_); } - inst_.bind_uniform_data(&pass); - inst_.sampling.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.sampling); surface_double_sided_ps_ = &pass.sub("Shadow.Surface.Double-Sided"); surface_single_sided_ps_ = &pass.sub("Shadow.Surface.Single-Sided"); surface_single_sided_ps_->state_set(state | DRW_STATE_CULL_BACK); @@ -255,9 +255,9 @@ void ForwardPipeline::sync() /* Textures. */ prepass_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&prepass_ps_); - inst_.velocity.bind_resources(prepass_ps_); - inst_.sampling.bind_resources(prepass_ps_); + prepass_ps_.bind_resources(inst_.uniform_data); + prepass_ps_.bind_resources(inst_.velocity); + prepass_ps_.bind_resources(inst_.sampling); } prepass_double_sided_static_ps_ = &prepass_ps_.sub("DoubleSided.Static"); @@ -285,14 +285,14 @@ void ForwardPipeline::sync() /* Textures. */ opaque_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&opaque_ps_); - inst_.lights.bind_resources(opaque_ps_); - inst_.shadows.bind_resources(opaque_ps_); - inst_.volume.bind_resources(opaque_ps_); - inst_.sampling.bind_resources(opaque_ps_); - inst_.hiz_buffer.bind_resources(opaque_ps_); - inst_.irradiance_cache.bind_resources(opaque_ps_); - inst_.reflection_probes.bind_resources(opaque_ps_); + opaque_ps_.bind_resources(inst_.uniform_data); + opaque_ps_.bind_resources(inst_.lights); + opaque_ps_.bind_resources(inst_.shadows); + opaque_ps_.bind_resources(inst_.volume.result); + opaque_ps_.bind_resources(inst_.sampling); + opaque_ps_.bind_resources(inst_.hiz_buffer.front); + opaque_ps_.bind_resources(inst_.irradiance_cache); + opaque_ps_.bind_resources(inst_.reflection_probes); } opaque_single_sided_ps_ = &opaque_ps_.sub("SingleSided"); @@ -313,14 +313,14 @@ void ForwardPipeline::sync() /* Textures. */ sub.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&sub); - inst_.lights.bind_resources(sub); - inst_.shadows.bind_resources(sub); - inst_.volume.bind_resources(sub); - inst_.sampling.bind_resources(sub); - inst_.hiz_buffer.bind_resources(sub); - inst_.irradiance_cache.bind_resources(sub); - inst_.reflection_probes.bind_resources(sub); + sub.bind_resources(inst_.uniform_data); + sub.bind_resources(inst_.lights); + sub.bind_resources(inst_.shadows); + sub.bind_resources(inst_.volume.result); + sub.bind_resources(inst_.sampling); + sub.bind_resources(inst_.hiz_buffer.front); + sub.bind_resources(inst_.irradiance_cache); + sub.bind_resources(inst_.reflection_probes); } } @@ -433,17 +433,17 @@ void DeferredLayerBase::gbuffer_pass_sync(Instance &inst) /* Textures. */ gbuffer_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst.pipelines.utility_tx); - inst.bind_uniform_data(&gbuffer_ps_); - inst.sampling.bind_resources(gbuffer_ps_); - inst.hiz_buffer.bind_resources(gbuffer_ps_); - inst.cryptomatte.bind_resources(gbuffer_ps_); + gbuffer_ps_.bind_resources(inst.uniform_data); + gbuffer_ps_.bind_resources(inst.sampling); + gbuffer_ps_.bind_resources(inst.hiz_buffer.front); + gbuffer_ps_.bind_resources(inst.cryptomatte); /* Bind light resources for the NPR materials that gets rendered first. * Non-NPR shaders will override these resource bindings. */ - inst.lights.bind_resources(gbuffer_ps_); - inst.shadows.bind_resources(gbuffer_ps_); - inst.reflection_probes.bind_resources(gbuffer_ps_); - inst.irradiance_cache.bind_resources(gbuffer_ps_); + gbuffer_ps_.bind_resources(inst.lights); + gbuffer_ps_.bind_resources(inst.shadows); + gbuffer_ps_.bind_resources(inst.reflection_probes); + gbuffer_ps_.bind_resources(inst.irradiance_cache); DRWState state = DRW_STATE_WRITE_COLOR | DRW_STATE_DEPTH_EQUAL; @@ -474,9 +474,9 @@ void DeferredLayer::begin_sync() bool alpha_hash_subpixel_scale = !inst_.is_viewport() || !inst_.velocity.camera_has_motion(); inst_.pipelines.data.alpha_hash_scale = alpha_hash_subpixel_scale ? 0.1f : 1.0f; - inst_.bind_uniform_data(&prepass_ps_); - inst_.velocity.bind_resources(prepass_ps_); - inst_.sampling.bind_resources(prepass_ps_); + prepass_ps_.bind_resources(inst_.uniform_data); + prepass_ps_.bind_resources(inst_.velocity); + prepass_ps_.bind_resources(inst_.sampling); DRWState state_depth_only = DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS; DRWState state_depth_color = DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS | @@ -582,12 +582,12 @@ void DeferredLayer::end_sync() sub.bind_image("direct_radiance_1_img", &direct_radiance_txs_[0]); sub.bind_image("direct_radiance_2_img", &direct_radiance_txs_[1]); sub.bind_image("direct_radiance_3_img", &direct_radiance_txs_[2]); - inst_.bind_uniform_data(&sub); - inst_.gbuffer.bind_resources(sub); - inst_.lights.bind_resources(sub); - inst_.shadows.bind_resources(sub); - inst_.sampling.bind_resources(sub); - inst_.hiz_buffer.bind_resources(sub); + sub.bind_resources(inst_.uniform_data); + sub.bind_resources(inst_.gbuffer); + sub.bind_resources(inst_.lights); + sub.bind_resources(inst_.shadows); + sub.bind_resources(inst_.sampling); + sub.bind_resources(inst_.hiz_buffer.front); sub.state_stencil(0xFFu, 1u << i, 0xFFu); if (GPU_backend_get_type() == GPU_BACKEND_METAL) { /* WORKAROUND: On Apple silicon the stencil test is broken. Only issue one expensive @@ -625,8 +625,8 @@ void DeferredLayer::end_sync() pass.bind_image("indirect_refract_img", &indirect_refract_tx_); pass.bind_image(RBUFS_COLOR_SLOT, &inst_.render_buffers.rp_color_tx); pass.bind_image(RBUFS_VALUE_SLOT, &inst_.render_buffers.rp_value_tx); - inst_.gbuffer.bind_resources(pass); - inst_.bind_uniform_data(&pass); + pass.bind_resources(inst_.gbuffer); + pass.bind_resources(inst_.uniform_data); pass.barrier(GPU_BARRIER_TEXTURE_FETCH | GPU_BARRIER_SHADER_IMAGE_ACCESS); pass.draw_procedural(GPU_PRIM_TRIS, 1, 3); } @@ -843,7 +843,7 @@ void DeferredPipeline::debug_pass_sync() pass.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND_CUSTOM); pass.shader_set(inst.shaders.static_shader_get(DEBUG_GBUFFER)); pass.push_constant("debug_mode", int(inst.debug_mode)); - inst.gbuffer.bind_resources(pass); + pass.bind_resources(inst.gbuffer); pass.draw_procedural(GPU_PRIM_TRIS, 1, 3); } @@ -947,18 +947,18 @@ void VolumeLayer::sync() PassMain::Sub &pass = layer_pass.sub("occupancy_ps"); /* Double sided without depth test. */ pass.state_set(DRW_STATE_WRITE_DEPTH); - inst_.bind_uniform_data(&pass); - inst_.volume.bind_occupancy_buffers(pass); - inst_.sampling.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.volume.occupancy); + pass.bind_resources(inst_.sampling); occupancy_ps_ = &pass; } { PassMain::Sub &pass = layer_pass.sub("material_ps"); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&pass); - inst_.volume.bind_properties_buffers(pass); - inst_.sampling.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.volume.properties); + pass.bind_resources(inst_.sampling); material_ps_ = &pass; } } @@ -1164,9 +1164,9 @@ void DeferredProbeLayer::begin_sync() /* Textures. */ prepass_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&prepass_ps_); - inst_.velocity.bind_resources(prepass_ps_); - inst_.sampling.bind_resources(prepass_ps_); + prepass_ps_.bind_resources(inst_.uniform_data); + prepass_ps_.bind_resources(inst_.velocity); + prepass_ps_.bind_resources(inst_.sampling); } DRWState state_depth_only = DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS; @@ -1191,13 +1191,13 @@ void DeferredProbeLayer::end_sync() pass.bind_image(RBUFS_COLOR_SLOT, &inst_.render_buffers.rp_color_tx); pass.bind_image(RBUFS_VALUE_SLOT, &inst_.render_buffers.rp_value_tx); pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&pass); - inst_.gbuffer.bind_resources(pass); - inst_.lights.bind_resources(pass); - inst_.shadows.bind_resources(pass); - inst_.sampling.bind_resources(pass); - inst_.hiz_buffer.bind_resources(pass); - inst_.irradiance_cache.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.gbuffer); + pass.bind_resources(inst_.lights); + pass.bind_resources(inst_.shadows); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.hiz_buffer.front); + pass.bind_resources(inst_.irradiance_cache); pass.barrier(GPU_BARRIER_TEXTURE_FETCH | GPU_BARRIER_SHADER_IMAGE_ACCESS); pass.draw_procedural(GPU_PRIM_TRIS, 1, 3); } @@ -1236,7 +1236,7 @@ void DeferredProbeLayer::render(View &view, int2 extent) { inst_.pipelines.data.is_probe_reflection = true; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); GPU_framebuffer_bind(prepass_fb); inst_.manager->submit(prepass_ps_, view); @@ -1256,7 +1256,7 @@ void DeferredProbeLayer::render(View &view, inst_.manager->submit(eval_light_ps_, view); inst_.pipelines.data.is_probe_reflection = false; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); } /** \} */ @@ -1311,8 +1311,8 @@ void PlanarProbePipeline::begin_sync() prepass_ps_.init(); prepass_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); prepass_ps_.bind_ubo(CLIP_PLANE_BUF, inst_.planar_probes.world_clip_buf_); - inst_.bind_uniform_data(&prepass_ps_); - inst_.sampling.bind_resources(prepass_ps_); + prepass_ps_.bind_resources(inst_.uniform_data); + prepass_ps_.bind_resources(inst_.sampling); DRWState state_depth_only = DRW_STATE_WRITE_DEPTH | DRW_STATE_DEPTH_LESS; @@ -1331,14 +1331,14 @@ void PlanarProbePipeline::begin_sync() pass.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND_ADD_FULL); pass.shader_set(inst_.shaders.static_shader_get(DEFERRED_PLANAR_EVAL)); pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&pass); - inst_.gbuffer.bind_resources(pass); - inst_.lights.bind_resources(pass); - inst_.shadows.bind_resources(pass); - inst_.sampling.bind_resources(pass); - inst_.hiz_buffer.bind_resources(pass); - inst_.reflection_probes.bind_resources(pass); - inst_.irradiance_cache.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.gbuffer); + pass.bind_resources(inst_.lights); + pass.bind_resources(inst_.shadows); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.hiz_buffer.front); + pass.bind_resources(inst_.reflection_probes); + pass.bind_resources(inst_.irradiance_cache); pass.barrier(GPU_BARRIER_TEXTURE_FETCH | GPU_BARRIER_SHADER_IMAGE_ACCESS); pass.draw_procedural(GPU_PRIM_TRIS, 1, 3); } @@ -1385,7 +1385,7 @@ void PlanarProbePipeline::render(View &view, GPU_debug_group_begin("Planar.Capture"); inst_.pipelines.data.is_probe_reflection = true; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); GPU_framebuffer_bind(gbuffer_fb); GPU_framebuffer_clear_depth(gbuffer_fb, 1.0f); @@ -1415,7 +1415,7 @@ void PlanarProbePipeline::render(View &view, inst_.manager->submit(eval_light_ps_, view); inst_.pipelines.data.is_probe_reflection = false; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); GPU_debug_group_end(); } @@ -1441,7 +1441,7 @@ void CapturePipeline::sync() surface_ps_.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); /* TODO(fclem): Remove. Bind to get the camera data, * but there should be no view dependent behavior during capture. */ - inst_.bind_uniform_data(&surface_ps_); + surface_ps_.bind_resources(inst_.uniform_data); } PassMain::Sub *CapturePipeline::surface_material_add(::Material *blender_mat, GPUMaterial *gpumat) diff --git a/source/blender/draw/engines/eevee_next/eevee_raytrace.cc b/source/blender/draw/engines/eevee_next/eevee_raytrace.cc index 99dcc569178..2be119902dc 100644 --- a/source/blender/draw/engines/eevee_next/eevee_raytrace.cc +++ b/source/blender/draw/engines/eevee_next/eevee_raytrace.cc @@ -55,8 +55,8 @@ void RayTraceModule::sync() pass.bind_image("tile_raytrace_tracing_img", &tile_raytrace_tracing_tx_); pass.bind_image("tile_horizon_denoise_img", &tile_horizon_denoise_tx_); pass.bind_image("tile_horizon_tracing_img", &tile_horizon_tracing_tx_); - inst_.bind_uniform_data(&pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.gbuffer); pass.dispatch(&tile_classify_dispatch_size_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS | GPU_BARRIER_SHADER_STORAGE); } @@ -76,7 +76,7 @@ void RayTraceModule::sync() pass.bind_ssbo("raytrace_denoise_tiles_buf", &raytrace_denoise_tiles_buf_); pass.bind_ssbo("horizon_tracing_tiles_buf", &horizon_tracing_tiles_buf_); pass.bind_ssbo("horizon_denoise_tiles_buf", &horizon_denoise_tiles_buf_); - inst_.bind_uniform_data(&pass); + pass.bind_resources(inst_.uniform_data); pass.dispatch(&tile_compact_dispatch_size_); pass.barrier(GPU_BARRIER_SHADER_STORAGE); } @@ -87,8 +87,8 @@ void RayTraceModule::sync() pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); pass.bind_image("out_ray_data_img", &ray_data_tx_); pass.bind_ssbo("tiles_coord_buf", &raytrace_tracing_tiles_buf_); - inst_.sampling.bind_resources(pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.gbuffer); pass.dispatch(raytrace_tracing_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_STORAGE | GPU_BARRIER_TEXTURE_FETCH | GPU_BARRIER_SHADER_IMAGE_ACCESS); @@ -106,16 +106,14 @@ void RayTraceModule::sync() sub.bind_image("ray_time_img", &ray_time_tx_); sub.bind_image("ray_radiance_img", &ray_radiance_tx_); sub.bind_texture("depth_tx", &depth_tx); - inst_.bind_uniform_data(&sub); - inst_.planar_probes.bind_resources(sub); - inst_.irradiance_cache.bind_resources(sub); - inst_.reflection_probes.bind_resources(sub); + sub.bind_resources(inst_.uniform_data); + sub.bind_resources(inst_.planar_probes); + sub.bind_resources(inst_.irradiance_cache); + sub.bind_resources(inst_.reflection_probes); /* TODO(@fclem): Use another dispatch with only tiles that touches planar captures. */ sub.dispatch(raytrace_tracing_dispatch_buf_); sub.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } - HiZBuffer::Type hiz_type = (&pass == &trace_refract_ps_) ? HiZBuffer::Type::BACK : - HiZBuffer::Type::FRONT; pass.shader_set(inst_.shaders.static_shader_get(SHADER_VARIATION(RAY_TRACE_SCREEN_, type))); pass.bind_ssbo("tiles_coord_buf", &raytrace_tracing_tiles_buf_); pass.bind_image("ray_data_img", &ray_data_tx_); @@ -123,11 +121,12 @@ void RayTraceModule::sync() pass.bind_texture("screen_radiance_tx", &screen_radiance_tx_); pass.bind_texture("depth_tx", &depth_tx); pass.bind_image("ray_radiance_img", &ray_radiance_tx_); - inst_.bind_uniform_data(&pass); - inst_.hiz_buffer.bind_resources(pass, hiz_type); - inst_.sampling.bind_resources(pass); - inst_.irradiance_cache.bind_resources(pass); - inst_.reflection_probes.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources((&pass == &trace_refract_ps_) ? inst_.hiz_buffer.back : + inst_.hiz_buffer.front); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.irradiance_cache); + pass.bind_resources(inst_.reflection_probes); pass.dispatch(raytrace_tracing_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -140,10 +139,10 @@ void RayTraceModule::sync() pass.bind_image("ray_time_img", &ray_time_tx_); pass.bind_image("ray_radiance_img", &ray_radiance_tx_); pass.bind_texture("depth_tx", &depth_tx); - inst_.bind_uniform_data(&pass); - inst_.irradiance_cache.bind_resources(pass); - inst_.reflection_probes.bind_resources(pass); - inst_.sampling.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.irradiance_cache); + pass.bind_resources(inst_.reflection_probes); + pass.bind_resources(inst_.sampling); pass.dispatch(raytrace_tracing_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -165,9 +164,9 @@ void RayTraceModule::sync() pass.bind_image("out_variance_img", &hit_variance_tx_); pass.bind_image("out_hit_depth_img", &hit_depth_tx_); pass.bind_image("tile_mask_img", &tile_raytrace_denoise_tx_); - inst_.bind_uniform_data(&pass); - inst_.sampling.bind_resources(pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.gbuffer); pass.dispatch(raytrace_denoise_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -175,7 +174,7 @@ void RayTraceModule::sync() PassSimple &pass = denoise_temporal_ps_; pass.init(); pass.shader_set(inst_.shaders.static_shader_get(RAY_DENOISE_TEMPORAL)); - inst_.bind_uniform_data(&pass); + pass.bind_resources(inst_.uniform_data); pass.bind_texture("radiance_history_tx", &radiance_history_tx_); pass.bind_texture("variance_history_tx", &variance_history_tx_); pass.bind_texture("tilemask_history_tx", &tilemask_history_tx_); @@ -186,7 +185,7 @@ void RayTraceModule::sync() pass.bind_image("in_variance_img", &hit_variance_tx_); pass.bind_image("out_variance_img", &denoise_variance_tx_); pass.bind_ssbo("tiles_coord_buf", &raytrace_denoise_tiles_buf_); - inst_.sampling.bind_resources(pass); + pass.bind_resources(inst_.sampling); pass.dispatch(raytrace_denoise_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -201,9 +200,9 @@ void RayTraceModule::sync() pass.bind_image("in_variance_img", &denoise_variance_tx_); pass.bind_image("tile_mask_img", &tile_raytrace_denoise_tx_); pass.bind_ssbo("tiles_coord_buf", &raytrace_denoise_tiles_buf_); - inst_.bind_uniform_data(&pass); - inst_.sampling.bind_resources(pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.gbuffer); pass.dispatch(raytrace_denoise_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -211,13 +210,13 @@ void RayTraceModule::sync() PassSimple &pass = horizon_setup_ps_; pass.init(); pass.shader_set(inst_.shaders.static_shader_get(HORIZON_SETUP)); - inst_.bind_uniform_data(&pass); + pass.bind_resources(inst_.uniform_data); pass.bind_texture("depth_tx", &depth_tx); pass.bind_texture("in_radiance_tx", &screen_radiance_tx_, GPUSamplerState::default_sampler()); pass.bind_image("out_radiance_img", &downsampled_in_radiance_tx_); pass.bind_image("out_normal_img", &downsampled_in_normal_tx_); - inst_.bind_uniform_data(&pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.gbuffer); pass.dispatch(&tracing_dispatch_size_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -231,10 +230,10 @@ void RayTraceModule::sync() pass.bind_texture("screen_radiance_tx", &downsampled_in_radiance_tx_); pass.bind_texture("screen_normal_tx", &downsampled_in_normal_tx_); pass.bind_texture(RBUFS_UTILITY_TEX_SLOT, inst_.pipelines.utility_tx); - inst_.bind_uniform_data(&pass); - inst_.hiz_buffer.bind_resources(pass); - inst_.sampling.bind_resources(pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.hiz_buffer.front); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.gbuffer); pass.dispatch(horizon_tracing_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -242,18 +241,17 @@ void RayTraceModule::sync() PassSimple &pass = horizon_denoise_ps_; pass.init(); pass.shader_set(inst_.shaders.static_shader_get(HORIZON_DENOISE)); - inst_.bind_uniform_data(&pass); pass.bind_texture("depth_tx", &depth_tx); pass.bind_image("horizon_radiance_img", &horizon_radiance_tx_); pass.bind_image("horizon_occlusion_img", &horizon_occlusion_tx_); pass.bind_image("radiance_img", &horizon_scan_output_tx_); pass.bind_image("tile_mask_img", &tile_horizon_denoise_tx_); pass.bind_ssbo("tiles_coord_buf", &horizon_denoise_tiles_buf_); - inst_.bind_uniform_data(&pass); - inst_.sampling.bind_resources(pass); - inst_.gbuffer.bind_resources(pass); - inst_.irradiance_cache.bind_resources(pass); - inst_.reflection_probes.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.sampling); + pass.bind_resources(inst_.gbuffer); + pass.bind_resources(inst_.irradiance_cache); + pass.bind_resources(inst_.reflection_probes); pass.dispatch(horizon_denoise_dispatch_buf_); pass.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); } @@ -334,7 +332,7 @@ RayTraceResult RayTraceModule::render(RayTraceBuffer &rt_buffer, /* TODO(fclem): Eventually all uniform data is setup here. */ - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); RayTraceResult result; @@ -504,7 +502,7 @@ RayTraceResultTexture RayTraceModule::trace( data_.full_resolution_inv = 1.0f / float2(extent); data_.skip_denoise = !use_spatial_denoise; data_.closure_index = closure_index; - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); /* Ray setup. */ raytrace_tracing_dispatch_buf_.clear_to_zero(); diff --git a/source/blender/draw/engines/eevee_next/eevee_shadow.cc b/source/blender/draw/engines/eevee_next/eevee_shadow.cc index 9110632f550..0de1f729d96 100644 --- a/source/blender/draw/engines/eevee_next/eevee_shadow.cc +++ b/source/blender/draw/engines/eevee_next/eevee_shadow.cc @@ -849,7 +849,7 @@ void ShadowModule::begin_sync() sub.bind_ssbo("capture_info_buf", &capture_info_buf); sub.push_constant("directional_level", directional_level); sub.push_constant("tilemap_projection_ratio", projection_ratio); - inst_.lights.bind_resources(sub); + sub.bind_resources(inst_.lights); sub.dispatch(&inst_.irradiance_cache.bake.dispatch_per_surfel_); /* Skip opaque and transparent tagging for light baking. */ @@ -864,7 +864,7 @@ void ShadowModule::begin_sync() sub.bind_ssbo("tiles_buf", &tilemap_pool.tiles_data); sub.bind_texture("depth_tx", &src_depth_tx_); sub.push_constant("tilemap_projection_ratio", &tilemap_projection_ratio_); - inst_.lights.bind_resources(sub); + sub.bind_resources(inst_.lights); sub.dispatch(&dispatch_depth_scan_size_); } { @@ -883,9 +883,9 @@ void ShadowModule::begin_sync() sub.push_constant("pixel_world_radius", &pixel_world_radius_); sub.push_constant("fb_resolution", &usage_tag_fb_resolution_); sub.push_constant("fb_lod", &usage_tag_fb_lod_); - inst_.bind_uniform_data(&sub); - inst_.hiz_buffer.bind_resources(sub); - inst_.lights.bind_resources(sub); + sub.bind_resources(inst_.uniform_data); + sub.bind_resources(inst_.hiz_buffer.front); + sub.bind_resources(inst_.lights); box_batch_ = DRW_cache_cube_get(); tilemap_usage_transparent_ps_ = ⊂ @@ -1029,7 +1029,7 @@ void ShadowModule::end_sync() sub.bind_ssbo("casters_id_buf", curr_casters_); sub.bind_ssbo("bounds_buf", &manager.bounds_buf.current()); sub.push_constant("resource_len", int(curr_casters_.size())); - inst_.lights.bind_resources(sub); + sub.bind_resources(inst_.lights); sub.dispatch(int3( divide_ceil_u(std::max(curr_casters_.size(), int64_t(1)), SHADOW_BOUNDS_GROUP_SIZE), 1, @@ -1083,12 +1083,11 @@ void ShadowModule::end_sync() sub.bind_ssbo("tilemaps_buf", &tilemap_pool.tilemaps_data); sub.bind_ssbo("tiles_buf", &tilemap_pool.tiles_data); sub.push_constant("tilemap_projection_ratio", &tilemap_projection_ratio_); - inst_.bind_uniform_data(&sub); - inst_.hiz_buffer.bind_resources(sub); - inst_.sampling.bind_resources(sub); - inst_.lights.bind_resources(sub); - inst_.volume.bind_resources(sub); - inst_.volume.bind_properties_buffers(sub); + sub.bind_resources(inst_.uniform_data); + sub.bind_resources(inst_.hiz_buffer.front); + sub.bind_resources(inst_.sampling); + sub.bind_resources(inst_.lights); + sub.bind_resources(inst_.volume.result); sub.barrier(GPU_BARRIER_SHADER_IMAGE_ACCESS); sub.dispatch(math::divide_ceil(inst_.volume.grid_size(), int3(VOLUME_GROUP_SIZE))); } @@ -1230,10 +1229,10 @@ void ShadowModule::debug_end_sync() debug_draw_ps_.push_constant("debug_tilemap_index", light.tilemap_index); debug_draw_ps_.bind_ssbo("tilemaps_buf", &tilemap_pool.tilemaps_data); debug_draw_ps_.bind_ssbo("tiles_buf", &tilemap_pool.tiles_data); - inst_.bind_uniform_data(&debug_draw_ps_); - inst_.hiz_buffer.bind_resources(debug_draw_ps_); - inst_.lights.bind_resources(debug_draw_ps_); - inst_.shadows.bind_resources(debug_draw_ps_); + debug_draw_ps_.bind_resources(inst_.uniform_data); + debug_draw_ps_.bind_resources(inst_.hiz_buffer.front); + debug_draw_ps_.bind_resources(inst_.lights); + debug_draw_ps_.bind_resources(inst_.shadows); debug_draw_ps_.draw_procedural(GPU_PRIM_TRIS, 1, 3); } diff --git a/source/blender/draw/engines/eevee_next/eevee_subsurface.cc b/source/blender/draw/engines/eevee_next/eevee_subsurface.cc index 085bff39146..2f0e4bc2c86 100644 --- a/source/blender/draw/engines/eevee_next/eevee_subsurface.cc +++ b/source/blender/draw/engines/eevee_next/eevee_subsurface.cc @@ -34,7 +34,7 @@ void SubsurfaceModule::end_sync() pass.init(); pass.state_set(DRW_STATE_NO_DRAW); pass.shader_set(inst_.shaders.static_shader_get(SUBSURFACE_SETUP)); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.gbuffer); pass.bind_texture("depth_tx", &inst_.render_buffers.depth_tx); pass.bind_image("direct_light_img", &direct_light_tx_); pass.bind_image("indirect_light_img", &indirect_light_tx_); @@ -59,8 +59,8 @@ void SubsurfaceModule::end_sync() pass.init(); pass.state_set(DRW_STATE_NO_DRAW); pass.shader_set(inst_.shaders.static_shader_get(SUBSURFACE_CONVOLVE)); - inst_.bind_uniform_data(&pass); - inst_.gbuffer.bind_resources(pass); + pass.bind_resources(inst_.uniform_data); + pass.bind_resources(inst_.gbuffer); pass.bind_texture("radiance_tx", &radiance_tx_, sampler); pass.bind_texture("depth_tx", &inst_.render_buffers.depth_tx, sampler); pass.bind_texture("object_id_tx", &object_id_tx_, sampler); @@ -124,7 +124,7 @@ void SubsurfaceModule::precompute_samples_location() data_.samples[i].z = 1.0f / burley_pdf(d, r); } - inst_.push_uniform_data(); + inst_.uniform_data.push_update(); } /** \} */ diff --git a/source/blender/draw/engines/eevee_next/eevee_volume.cc b/source/blender/draw/engines/eevee_next/eevee_volume.cc index 875fd9c4ba4..31ab3d703f9 100644 --- a/source/blender/draw/engines/eevee_next/eevee_volume.cc +++ b/source/blender/draw/engines/eevee_next/eevee_volume.cc @@ -108,9 +108,18 @@ void VolumeModule::end_sync() integrated_scatter_tx_.free(); integrated_transmit_tx_.free(); - transparent_pass_scatter_tx_ = dummy_scatter_tx_; - transparent_pass_transmit_tx_ = dummy_transmit_tx_; - + /* Update references for bindings. */ + result.scattering_tx_ = dummy_scatter_tx_; + result.transmittance_tx_ = dummy_transmit_tx_; + /* These shouldn't be used. */ + properties.scattering_tx_ = nullptr; + properties.extinction_tx_ = nullptr; + properties.emission_tx_ = nullptr; + properties.phase_tx_ = nullptr; + properties.occupancy_tx_ = nullptr; + occupancy.occupancy_tx_ = nullptr; + occupancy.hit_depth_tx_ = nullptr; + occupancy.hit_count_tx_ = nullptr; return; } @@ -167,8 +176,17 @@ void VolumeModule::end_sync() integrated_scatter_tx_.ensure_3d(GPU_R11F_G11F_B10F, data_.tex_size, usage); integrated_transmit_tx_.ensure_3d(GPU_R11F_G11F_B10F, data_.tex_size, usage); - transparent_pass_scatter_tx_ = integrated_scatter_tx_; - transparent_pass_transmit_tx_ = integrated_transmit_tx_; + /* Update references for bindings. */ + result.scattering_tx_ = integrated_scatter_tx_; + result.transmittance_tx_ = integrated_transmit_tx_; + properties.scattering_tx_ = prop_scattering_tx_; + properties.extinction_tx_ = prop_extinction_tx_; + properties.emission_tx_ = prop_emission_tx_; + properties.phase_tx_ = prop_phase_tx_; + properties.occupancy_tx_ = occupancy_tx_; + occupancy.occupancy_tx_ = occupancy_tx_; + occupancy.hit_depth_tx_ = hit_depth_tx_; + occupancy.hit_count_tx_ = hit_count_tx_; scatter_ps_.init(); scatter_ps_.shader_set( @@ -192,7 +210,7 @@ void VolumeModule::end_sync() integration_ps_.init(); integration_ps_.shader_set(inst_.shaders.static_shader_get(VOLUME_INTEGRATION)); - inst_.bind_uniform_data(&integration_ps_); + integration_ps_.bind_resources(inst_.uniform_data); integration_ps_.bind_texture("in_scattering_tx", &scatter_tx_); integration_ps_.bind_texture("in_extinction_tx", &extinction_tx_); integration_ps_.bind_image("out_scattering_img", &integrated_scatter_tx_); @@ -205,8 +223,8 @@ void VolumeModule::end_sync() resolve_ps_.init(); resolve_ps_.state_set(DRW_STATE_WRITE_COLOR | DRW_STATE_BLEND_CUSTOM); resolve_ps_.shader_set(inst_.shaders.static_shader_get(VOLUME_RESOLVE)); - inst_.bind_uniform_data(&resolve_ps_); - bind_resources(resolve_ps_); + resolve_ps_.bind_resources(inst_.uniform_data); + resolve_ps_.bind_resources(this->result); resolve_ps_.bind_texture("depth_tx", &inst_.render_buffers.depth_tx); resolve_ps_.bind_image(RBUFS_COLOR_SLOT, &inst_.render_buffers.rp_color_tx); resolve_ps_.bind_image(RBUFS_VALUE_SLOT, &inst_.render_buffers.rp_value_tx); diff --git a/source/blender/draw/engines/eevee_next/eevee_volume.hh b/source/blender/draw/engines/eevee_next/eevee_volume.hh index 014144016b3..bf08b84e86b 100644 --- a/source/blender/draw/engines/eevee_next/eevee_volume.hh +++ b/source/blender/draw/engines/eevee_next/eevee_volume.hh @@ -90,11 +90,7 @@ class VolumeModule { /* Full-screen Resolve */ PassSimple resolve_ps_ = {"Volumes.Resolve"}; Framebuffer resolve_fb_; - /* Used in the forward transparent pass (ForwardPipeline). - * The forward transparent pass must perform its own resolve step for correct composition between - * volumes and transparent surfaces. */ - GPUTexture *transparent_pass_scatter_tx_; - GPUTexture *transparent_pass_transmit_tx_; + Texture dummy_scatter_tx_; Texture dummy_transmit_tx_; @@ -107,30 +103,6 @@ class VolumeModule { ~VolumeModule(){}; - /* Bind resources needed by external passes to perform their own resolve. */ - template void bind_resources(PassType &pass) - { - pass.bind_texture(VOLUME_SCATTERING_TEX_SLOT, &transparent_pass_scatter_tx_); - pass.bind_texture(VOLUME_TRANSMITTANCE_TEX_SLOT, &transparent_pass_transmit_tx_); - } - - /* Bind the common resources needed by all volumetric passes. */ - template void bind_properties_buffers(PassType &pass) - { - pass.bind_image(VOLUME_PROP_SCATTERING_IMG_SLOT, &prop_scattering_tx_); - pass.bind_image(VOLUME_PROP_EXTINCTION_IMG_SLOT, &prop_extinction_tx_); - pass.bind_image(VOLUME_PROP_EMISSION_IMG_SLOT, &prop_emission_tx_); - pass.bind_image(VOLUME_PROP_PHASE_IMG_SLOT, &prop_phase_tx_); - pass.bind_image(VOLUME_OCCUPANCY_SLOT, &occupancy_tx_); - } - - template void bind_occupancy_buffers(PassType &pass) - { - pass.bind_image(VOLUME_OCCUPANCY_SLOT, &occupancy_tx_); - pass.bind_image(VOLUME_HIT_DEPTH_SLOT, &hit_depth_tx_); - pass.bind_image(VOLUME_HIT_COUNT_SLOT, &hit_count_tx_); - } - bool needs_shadow_tagging() { return enabled_ && use_lights_; @@ -153,5 +125,52 @@ class VolumeModule { void draw_compute(View &view); /* Final image compositing. */ void draw_resolve(View &view); + + /* Final occupancy after resolve. Used by object volume material evaluation. */ + struct { + /** References to the textures in the module. */ + GPUTexture *scattering_tx_ = nullptr; + GPUTexture *transmittance_tx_ = nullptr; + + template void bind_resources(PassType &pass) + { + pass.bind_texture(VOLUME_SCATTERING_TEX_SLOT, &scattering_tx_); + pass.bind_texture(VOLUME_TRANSMITTANCE_TEX_SLOT, &transmittance_tx_); + } + } result; + + /* Volume property buffers that are populated by objects or world volume shaders. */ + struct { + /** References to the textures in the module. */ + GPUTexture *scattering_tx_ = nullptr; + GPUTexture *extinction_tx_ = nullptr; + GPUTexture *emission_tx_ = nullptr; + GPUTexture *phase_tx_ = nullptr; + GPUTexture *occupancy_tx_ = nullptr; + + template void bind_resources(PassType &pass) + { + pass.bind_image(VOLUME_PROP_SCATTERING_IMG_SLOT, &scattering_tx_); + pass.bind_image(VOLUME_PROP_EXTINCTION_IMG_SLOT, &extinction_tx_); + pass.bind_image(VOLUME_PROP_EMISSION_IMG_SLOT, &emission_tx_); + pass.bind_image(VOLUME_PROP_PHASE_IMG_SLOT, &phase_tx_); + pass.bind_image(VOLUME_OCCUPANCY_SLOT, &occupancy_tx_); + } + } properties; + + /* Textures used for object volume occupancy computation. */ + struct { + /** References to the textures in the module. */ + GPUTexture *occupancy_tx_ = nullptr; + GPUTexture *hit_depth_tx_ = nullptr; + GPUTexture *hit_count_tx_ = nullptr; + + template void bind_resources(PassType &pass) + { + pass.bind_image(VOLUME_OCCUPANCY_SLOT, &occupancy_tx_); + pass.bind_image(VOLUME_HIT_DEPTH_SLOT, &hit_depth_tx_); + pass.bind_image(VOLUME_HIT_COUNT_SLOT, &hit_count_tx_); + } + } occupancy; }; } // namespace blender::eevee diff --git a/source/blender/draw/intern/draw_pass.hh b/source/blender/draw/intern/draw_pass.hh index 65b689534ec..6cebc6c8c43 100644 --- a/source/blender/draw/intern/draw_pass.hh +++ b/source/blender/draw/intern/draw_pass.hh @@ -383,6 +383,17 @@ class PassBase { void specialize_constant(GPUShader *shader, const char *name, const uint *data); void specialize_constant(GPUShader *shader, const char *name, const bool *data); + /** + * Custom resource binding. + * Syntactic sugar to avoid calling `resources.bind_resources(pass)` which is semantically less + * pleasing. + * `U` type must have a `bind_resources &pass>()` method. + */ + template void bind_resources(U &resources) + { + resources.bind_resources(*this); + } + /** * Turn the pass into a string for inspection. */