diff options
Diffstat (limited to 'servers/rendering/renderer_rd/renderer_scene_render_rd.cpp')
-rw-r--r-- | servers/rendering/renderer_rd/renderer_scene_render_rd.cpp | 26 |
1 files changed, 20 insertions, 6 deletions
diff --git a/servers/rendering/renderer_rd/renderer_scene_render_rd.cpp b/servers/rendering/renderer_rd/renderer_scene_render_rd.cpp index 07d56eae0c..d10443d6ad 100644 --- a/servers/rendering/renderer_rd/renderer_scene_render_rd.cpp +++ b/servers/rendering/renderer_rd/renderer_scene_render_rd.cpp @@ -260,15 +260,29 @@ void RendererSceneRenderRD::_render_buffers_copy_screen_texture(const RenderData RD::get_singleton()->draw_command_begin_label("Copy screen texture"); - rb->allocate_blur_textures(); - + StringName texture_name; bool can_use_storage = _render_buffers_can_be_storage(); Size2i size = rb->get_internal_size(); + // When upscaling, the blur texture needs to be at the target size for post-processing to work. We prefer to use a + // dedicated backbuffer copy texture instead if the blur texture is not an option so shader effects work correctly. + Size2i target_size = rb->get_target_size(); + bool internal_size_matches = (size.width == target_size.width) && (size.height == target_size.height); + bool reuse_blur_texture = !rb->has_upscaled_texture() || internal_size_matches; + if (reuse_blur_texture) { + rb->allocate_blur_textures(); + texture_name = RB_TEX_BLUR_0; + } else { + uint32_t usage_bits = RD::TEXTURE_USAGE_SAMPLING_BIT | RD::TEXTURE_USAGE_CAN_COPY_TO_BIT; + usage_bits |= can_use_storage ? RD::TEXTURE_USAGE_STORAGE_BIT : RD::TEXTURE_USAGE_COLOR_ATTACHMENT_BIT; + rb->create_texture(RB_SCOPE_BUFFERS, RB_TEX_BACK_COLOR, rb->get_base_data_format(), usage_bits); + texture_name = RB_TEX_BACK_COLOR; + } + for (uint32_t v = 0; v < rb->get_view_count(); v++) { RID texture = rb->get_internal_texture(v); - int mipmaps = int(rb->get_texture_format(RB_SCOPE_BUFFERS, RB_TEX_BLUR_0).mipmaps); - RID dest = rb->get_texture_slice(RB_SCOPE_BUFFERS, RB_TEX_BLUR_0, v, 0); + int mipmaps = int(rb->get_texture_format(RB_SCOPE_BUFFERS, texture_name).mipmaps); + RID dest = rb->get_texture_slice(RB_SCOPE_BUFFERS, texture_name, v, 0); if (can_use_storage) { copy_effects->copy_to_rect(texture, dest, Rect2i(0, 0, size.x, size.y)); @@ -279,8 +293,8 @@ void RendererSceneRenderRD::_render_buffers_copy_screen_texture(const RenderData for (int i = 1; i < mipmaps; i++) { RID source = dest; - dest = rb->get_texture_slice(RB_SCOPE_BUFFERS, RB_TEX_BLUR_0, v, i); - Size2i msize = rb->get_texture_slice_size(RB_SCOPE_BUFFERS, RB_TEX_BLUR_0, i); + dest = rb->get_texture_slice(RB_SCOPE_BUFFERS, texture_name, v, i); + Size2i msize = rb->get_texture_slice_size(RB_SCOPE_BUFFERS, texture_name, i); if (can_use_storage) { copy_effects->make_mipmap(source, dest, msize); |