Fix #111561: Workbench-Next: Overlay in-front compositing

Copy the in-front depth buffer to `DefaultTextureList::depth_in_front` for
correct overlay compositing.

Pull Request: https://projects.blender.org/blender/blender/pulls/111630
This commit is contained in:
Miguel Pozo
2023-08-28 21:01:56 +02:00
parent 0fa8b099a5
commit ee7e187b7f
4 changed files with 28 additions and 18 deletions
@@ -163,6 +163,8 @@ void AntiAliasingPass::sync(SceneResources &resources, int2 resolution)
sample0_depth_tx_.ensure_2d(GPU_DEPTH24_STENCIL8,
resolution,
GPU_TEXTURE_USAGE_SHADER_READ | GPU_TEXTURE_USAGE_ATTACHMENT);
sample0_depth_in_front_tx_.ensure_2d(
GPU_DEPTH24_STENCIL8, resolution, GPU_TEXTURE_USAGE_ATTACHMENT);
taa_accumulation_ps_.init();
taa_accumulation_ps_.state_set(sample_ == 0 ? DRW_STATE_WRITE_COLOR :
@@ -251,6 +253,7 @@ void AntiAliasingPass::draw(Manager &manager,
SceneResources &resources,
int2 resolution,
GPUTexture *depth_tx,
GPUTexture *depth_in_front_tx,
GPUTexture *color_tx)
{
auto draw_overlay_depth = [&](GPUTexture *target) {
@@ -287,9 +290,11 @@ void AntiAliasingPass::draw(Manager &manager,
if (sample_ == 0) {
draw_overlay_depth(sample0_depth_tx_);
GPU_texture_copy(sample0_depth_in_front_tx_, resources.depth_in_front_tx);
}
/* Copy back the saved depth buffer for correct overlays. */
GPU_texture_copy(depth_tx, sample0_depth_tx_);
GPU_texture_copy(depth_in_front_tx, sample0_depth_in_front_tx_);
if (!DRW_state_is_image_render() || last_sample) {
smaa_weight_tx_.acquire(
@@ -427,7 +427,10 @@ class Instance {
});
}
void draw(Manager &manager, GPUTexture *depth_tx, GPUTexture *color_tx)
void draw(Manager &manager,
GPUTexture *depth_tx,
GPUTexture *depth_in_front_tx,
GPUTexture *color_tx)
{
view.sync(DRW_view_default_get());
@@ -435,7 +438,8 @@ class Instance {
if (scene_state.render_finished) {
/* Just copy back the already rendered result */
anti_aliasing_ps.draw(manager, view, resources, resolution, depth_tx, color_tx);
anti_aliasing_ps.draw(
manager, view, resources, resolution, depth_tx, depth_in_front_tx, color_tx);
return;
}
@@ -455,18 +459,13 @@ class Instance {
fb.bind();
GPU_framebuffer_clear_depth_stencil(fb, 1.0f, 0x00);
if (!transparent_ps.accumulation_in_front_ps_.is_empty()) {
bool needs_depth_in_front = !transparent_ps.accumulation_in_front_ps_.is_empty() ||
scene_state.sample == 0;
if (needs_depth_in_front) {
resources.depth_in_front_tx.acquire(resolution,
GPU_DEPTH24_STENCIL8,
GPU_TEXTURE_USAGE_SHADER_READ |
GPU_TEXTURE_USAGE_ATTACHMENT);
if (opaque_ps.gbuffer_in_front_ps_.is_empty()) {
/* Clear only if it wont be overwritten by `opaque_ps`. */
Framebuffer fb = Framebuffer("Workbench.Clear");
fb.ensure(GPU_ATTACHMENT_TEXTURE(resources.depth_in_front_tx));
fb.bind();
GPU_framebuffer_clear_depth_stencil(fb, 1.0f, 0x00);
}
}
opaque_ps.draw(
@@ -477,16 +476,20 @@ class Instance {
volume_ps.draw(manager, view, resources);
outline_ps.draw(manager, resources);
dof_ps.draw(manager, view, resources, resolution);
anti_aliasing_ps.draw(manager, view, resources, resolution, depth_tx, color_tx);
anti_aliasing_ps.draw(
manager, view, resources, resolution, depth_tx, depth_in_front_tx, color_tx);
resources.color_tx.release();
resources.object_id_tx.release();
resources.depth_in_front_tx.release();
}
void draw_viewport(Manager &manager, GPUTexture *depth_tx, GPUTexture *color_tx)
void draw_viewport(Manager &manager,
GPUTexture *depth_tx,
GPUTexture *depth_in_front_tx,
GPUTexture *color_tx)
{
this->draw(manager, depth_tx, color_tx);
this->draw(manager, depth_tx, depth_in_front_tx, color_tx);
if (scene_state.sample + 1 < scene_state.samples_len) {
DRW_viewport_request_redraw();
@@ -568,7 +571,7 @@ static void workbench_draw_scene(void *vedata)
}
DefaultTextureList *dtxl = DRW_viewport_texture_list_get();
draw::Manager *manager = DRW_manager_get();
ved->instance->draw_viewport(*manager, dtxl->depth, dtxl->color);
ved->instance->draw_viewport(*manager, dtxl->depth, dtxl->depth_in_front, dtxl->color);
}
static void workbench_instance_free(void *instance)
@@ -172,10 +172,10 @@ void OpaquePass::draw(Manager &manager,
opaque_fb.bind();
manager.submit(gbuffer_in_front_ps_, view);
if (resources.depth_in_front_tx.is_valid()) {
/* Only needed when transparent infront is needed */
GPU_texture_copy(resources.depth_in_front_tx, resources.depth_tx);
}
}
if (resources.depth_in_front_tx.is_valid()) {
GPU_texture_copy(resources.depth_in_front_tx, resources.depth_tx);
}
if (!gbuffer_ps_.is_empty()) {
@@ -509,6 +509,7 @@ class AntiAliasingPass {
float weights_sum_ = 0;
Texture sample0_depth_tx_ = {"sample0_depth_tx"};
Texture sample0_depth_in_front_tx_ = {"sample0_depth_in_front_tx"};
GPUTexture *stencil_tx_ = nullptr;
Texture taa_accumulation_tx_ = {"taa_accumulation_tx"};
@@ -550,6 +551,7 @@ class AntiAliasingPass {
SceneResources &resources,
int2 resolution,
GPUTexture *depth_tx,
GPUTexture *depth_in_front_tx,
GPUTexture *color_tx);
};