EEVEE: Metal: Enable attachmentless FB support for VSM update FB
Utilise attachmentless framebuffer for atomic shadow update Path. Authored by Apple: Michael Parkin-White. Pull Request: https://projects.blender.org/blender/blender/pulls/116396
This commit is contained in:
committed by
Clément Foucault
parent
258ba00a03
commit
6692390501
@@ -1287,19 +1287,10 @@ void ShadowModule::set_view(View &view, GPUTexture *depth_tx)
|
||||
int fb_layers = SHADOW_VIEW_MAX;
|
||||
|
||||
if (shadow_technique == ShadowTechnique::ATOMIC_RASTER) {
|
||||
if (GPU_backend_get_type() == GPU_BACKEND_METAL) {
|
||||
/* Metal requires a memoryless attachment to create an empty framebuffer.
|
||||
* Might as well make use of it. */
|
||||
shadow_depth_fb_tx_.ensure_2d_array(GPU_DEPTH_COMPONENT32F, fb_size, fb_layers, usage);
|
||||
shadow_depth_accum_tx_.free();
|
||||
render_fb_.ensure(GPU_ATTACHMENT_TEXTURE(shadow_depth_fb_tx_));
|
||||
}
|
||||
else {
|
||||
/* Create attachment-less framebuffer. */
|
||||
shadow_depth_fb_tx_.free();
|
||||
shadow_depth_accum_tx_.free();
|
||||
render_fb_.ensure(fb_size);
|
||||
}
|
||||
/* Create attachment-less framebuffer. */
|
||||
shadow_depth_fb_tx_.free();
|
||||
shadow_depth_accum_tx_.free();
|
||||
render_fb_.ensure(fb_size);
|
||||
}
|
||||
else if (shadow_technique == ShadowTechnique::TILE_COPY) {
|
||||
/* Create memoryless depth attachment for on-tile surface depth accumulation.*/
|
||||
|
||||
@@ -152,10 +152,14 @@ void init_interface()
|
||||
#if defined(GPU_VERTEX_SHADER) && defined(MAT_SHADOW)
|
||||
void shadow_viewport_layer_set(int view_id, int lod)
|
||||
{
|
||||
# ifdef SHADOW_UPDATE_ATOMIC_RASTER
|
||||
shadow_iface.shadow_view_id = view_id;
|
||||
# else
|
||||
/* We still render to a layered frame-buffer in the case of Metal + Tile Based Renderer.
|
||||
* Since it needs correct depth buffering, each view needs to not overlap each others.
|
||||
* It doesn't matter much for other platform, so we use that as a way to pass the view id. */
|
||||
gpu_Layer = view_id;
|
||||
# endif
|
||||
gpu_ViewportIndex = lod;
|
||||
}
|
||||
#endif
|
||||
@@ -163,6 +167,10 @@ void shadow_viewport_layer_set(int view_id, int lod)
|
||||
#if defined(GPU_FRAGMENT_SHADER) && defined(MAT_SHADOW)
|
||||
int shadow_view_id_get()
|
||||
{
|
||||
# ifdef SHADOW_UPDATE_ATOMIC_RASTER
|
||||
return shadow_iface.shadow_view_id;
|
||||
# else
|
||||
return gpu_Layer;
|
||||
# endif
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -226,10 +226,13 @@ GPU_SHADER_CREATE_INFO(eevee_surf_world)
|
||||
// "eevee_cryptomatte_out",
|
||||
"eevee_utility_texture");
|
||||
|
||||
GPU_SHADER_INTERFACE_INFO(eevee_surf_shadow_atomic_iface, "shadow_iface")
|
||||
.flat(Type::INT, "shadow_view_id");
|
||||
|
||||
GPU_SHADER_CREATE_INFO(eevee_surf_shadow)
|
||||
.define("DRW_VIEW_LEN", STRINGIFY(SHADOW_VIEW_MAX))
|
||||
.define("MAT_SHADOW")
|
||||
.builtins(BuiltinBits::VIEWPORT_INDEX | BuiltinBits::LAYER)
|
||||
.builtins(BuiltinBits::VIEWPORT_INDEX)
|
||||
.storage_buf(SHADOW_VIEWPORT_INDEX_BUF_SLOT,
|
||||
Qualifier::READ,
|
||||
"uint",
|
||||
@@ -244,6 +247,7 @@ GPU_SHADER_CREATE_INFO(eevee_surf_shadow_atomic)
|
||||
/* Early fragment test for speeding up platforms that requires a depth buffer. */
|
||||
/* NOTE: This removes the possibility of using gl_FragDepth. */
|
||||
.early_fragment_test(true)
|
||||
.vertex_out(eevee_surf_shadow_atomic_iface)
|
||||
.storage_buf(SHADOW_RENDER_MAP_BUF_SLOT,
|
||||
Qualifier::READ,
|
||||
"uint",
|
||||
@@ -257,6 +261,7 @@ GPU_SHADER_CREATE_INFO(eevee_surf_shadow_atomic)
|
||||
GPU_SHADER_CREATE_INFO(eevee_surf_shadow_tbdr)
|
||||
.additional_info("eevee_surf_shadow")
|
||||
.define("SHADOW_UPDATE_TBDR")
|
||||
.builtins(BuiltinBits::LAYER)
|
||||
/* F32 color attachment for on-tile depth accumulation without atomics. */
|
||||
.fragment_out(0, Type::FLOAT, "out_depth", DualBlend::NONE, SHADOW_ROG_ID);
|
||||
|
||||
|
||||
@@ -1084,11 +1084,16 @@ bool MTLContext::ensure_render_pipeline_state(MTLPrimitiveType mtl_prim_type)
|
||||
}
|
||||
else {
|
||||
/* Scissor is disabled, reset to default size as scissor state may have been previously
|
||||
* assigned on this encoder. */
|
||||
* assigned on this encoder.
|
||||
* NOTE: If an attachment-less framebuffer is used, fetch specified width/height rather
|
||||
* than active attachment width/height as provided by get_default_w/h().*/
|
||||
uint default_w = render_fb->get_default_width();
|
||||
uint default_h = render_fb->get_default_height();
|
||||
bool is_attachmentless = (default_w == 0) && (default_h == 0);
|
||||
scissor.x = 0;
|
||||
scissor.y = 0;
|
||||
scissor.width = render_fb->get_default_width();
|
||||
scissor.height = render_fb->get_default_height();
|
||||
scissor.width = (is_attachmentless) ? render_fb->get_width() : default_w;
|
||||
scissor.height = (is_attachmentless) ? render_fb->get_height() : default_h;
|
||||
}
|
||||
|
||||
/* Scissor state can still be flagged as changed if it is toggled on and off, without
|
||||
|
||||
Reference in New Issue
Block a user