1
0
mirror of https://github.com/RPCS3/rpcs3.git synced 2024-11-22 18:53:28 +01:00

rsx: Do not clip scissor to viewport when doing buffer clear

This commit is contained in:
kd-11 2019-07-20 14:58:05 +03:00 committed by kd-11
parent 4e4c896136
commit 9a7c2784f0
7 changed files with 48 additions and 28 deletions

View File

@ -650,10 +650,10 @@ void GLGSRender::set_viewport()
glViewport(0, 0, clip_width, clip_height);
}
void GLGSRender::set_scissor()
void GLGSRender::set_scissor(bool clip_viewport)
{
areau scissor;
if (get_scissor(scissor))
if (get_scissor(scissor, clip_viewport))
{
// NOTE: window origin does not affect scissor region (probably only affects viewport matrix; already applied)
// See LIMBO [NPUB-30373] which uses shader window origin = top
@ -1784,7 +1784,7 @@ void GLGSRender::flip(int buffer, bool emu_flip)
// Always restore the active framebuffer
m_draw_fbo->bind();
set_viewport();
set_scissor();
set_scissor(!!(m_graphics_state & rsx::pipeline_state::scissor_setup_clipped));
}
// If we are skipping the next frame, do not reset perf counters

View File

@ -1,4 +1,4 @@
#pragma once
#pragma once
#include "Emu/RSX/GSRender.h"
#include "GLHelpers.h"
#include "GLTexture.h"
@ -373,7 +373,7 @@ private:
public:
void read_buffers();
void set_viewport();
void set_scissor();
void set_scissor(bool clip_viewport);
work_item& post_flush_request(u32 address, gl::texture_cache::thrashed_set& flush_data);

View File

@ -172,11 +172,12 @@ namespace
void GLGSRender::init_buffers(rsx::framebuffer_creation_context context, bool skip_reading)
{
const bool clipped_scissor = (context == rsx::framebuffer_creation_context::context_draw);
if (m_current_framebuffer_context == context && !m_rtts_dirty && m_draw_fbo)
{
// Fast path
// Framebuffer usage has not changed, framebuffer exists and config regs have not changed
set_scissor();
set_scissor(clipped_scissor);
return;
}
@ -196,7 +197,7 @@ void GLGSRender::init_buffers(rsx::framebuffer_creation_context context, bool sk
// Update flags to match current
m_draw_fbo->bind();
set_viewport();
set_scissor();
set_scissor(clipped_scissor);
return;
}
@ -364,7 +365,7 @@ void GLGSRender::init_buffers(rsx::framebuffer_creation_context context, bool sk
check_zcull_status(true);
set_viewport();
set_scissor();
set_scissor(clipped_scissor);
m_gl_texture_cache.clear_ro_tex_invalidate_intr();

View File

@ -1302,31 +1302,48 @@ namespace rsx
return layout;
}
bool thread::get_scissor(areau& region)
bool thread::get_scissor(areau& region, bool clip_viewport)
{
if (!(m_graphics_state & rsx::pipeline_state::scissor_config_state_dirty))
{
// Nothing to do
return false;
if (clip_viewport == !!(m_graphics_state & rsx::pipeline_state::scissor_setup_clipped))
{
// Nothing to do
return false;
}
}
m_graphics_state &= ~rsx::pipeline_state::scissor_config_state_dirty;
m_graphics_state &= ~(rsx::pipeline_state::scissor_config_state_dirty | rsx::pipeline_state::scissor_setup_clipped);
u16 x1, x2, y1, y2;
u16 scissor_x = rsx::method_registers.scissor_origin_x();
u16 scissor_w = rsx::method_registers.scissor_width();
u16 scissor_y = rsx::method_registers.scissor_origin_y();
u16 scissor_h = rsx::method_registers.scissor_height();
u16 raster_x = rsx::method_registers.viewport_origin_x();
u16 raster_w = rsx::method_registers.viewport_width();
u16 raster_y = rsx::method_registers.viewport_origin_y();
u16 raster_h = rsx::method_registers.viewport_height();
if (clip_viewport)
{
u16 raster_x = rsx::method_registers.viewport_origin_x();
u16 raster_w = rsx::method_registers.viewport_width();
u16 raster_y = rsx::method_registers.viewport_origin_y();
u16 raster_h = rsx::method_registers.viewport_height();
// Get the minimum area between these two
u16 x1 = std::max(scissor_x, raster_x);
u16 y1 = std::max(scissor_y, raster_y);
u16 x2 = std::min(scissor_x + scissor_w, raster_x + raster_w);
u16 y2 = std::min(scissor_y + scissor_h, raster_y + raster_h);
// Get the minimum area between these two
x1 = std::max(scissor_x, raster_x);
y1 = std::max(scissor_y, raster_y);
x2 = std::min(scissor_x + scissor_w, raster_x + raster_w);
y2 = std::min(scissor_y + scissor_h, raster_y + raster_h);
m_graphics_state |= rsx::pipeline_state::scissor_setup_clipped;
}
else
{
x1 = scissor_x;
x2 = scissor_x + scissor_w;
y1 = scissor_y;
y2 = scissor_y + scissor_h;
}
if (x2 <= x1 ||
y2 <= y1 ||

View File

@ -76,6 +76,7 @@ namespace rsx
scissor_config_state_dirty = 0x200, // Scissor region changed
scissor_setup_invalid = 0x400, // Scissor configuration is broken
scissor_setup_clipped = 0x800, // Scissor region is cropped by viewport constraint
invalidate_pipeline_bits = fragment_program_dirty | vertex_program_dirty,
memory_barrier_bits = framebuffer_reads_dirty,
@ -521,7 +522,7 @@ namespace rsx
u32 get_zeta_surface_address() const;
framebuffer_layout get_framebuffer_layout(rsx::framebuffer_creation_context context);
bool get_scissor(areau& region);
bool get_scissor(areau& region, bool clip_viewport);
/**
* Analyze vertex inputs and group all interleaved blocks

View File

@ -1797,10 +1797,10 @@ void VKGSRender::set_viewport()
m_viewport.maxDepth = 1.f;
}
void VKGSRender::set_scissor()
void VKGSRender::set_scissor(bool clip_viewport)
{
areau scissor;
if (get_scissor(scissor))
if (get_scissor(scissor, clip_viewport))
{
m_scissor.extent.height = scissor.height();
m_scissor.extent.width = scissor.width();
@ -2824,11 +2824,12 @@ void VKGSRender::open_command_buffer()
void VKGSRender::prepare_rtts(rsx::framebuffer_creation_context context)
{
const bool clipped_scissor = (context == rsx::framebuffer_creation_context::context_draw);
if (m_current_framebuffer_context == context && !m_rtts_dirty && m_draw_fbo)
{
// Fast path
// Framebuffer usage has not changed, framebuffer exists and config regs have not changed
set_scissor();
set_scissor(clipped_scissor);
return;
}
@ -2846,7 +2847,7 @@ void VKGSRender::prepare_rtts(rsx::framebuffer_creation_context context)
{
// Nothing has changed, we're still using the same framebuffer
// Update flags to match current
set_scissor();
set_scissor(clipped_scissor);
return;
}
@ -3022,7 +3023,7 @@ void VKGSRender::prepare_rtts(rsx::framebuffer_creation_context context)
m_draw_fbo->add_ref();
set_viewport();
set_scissor();
set_scissor(clipped_scissor);
check_zcull_status(true);
}

View File

@ -460,7 +460,7 @@ public:
void read_buffers();
void write_buffers();
void set_viewport();
void set_scissor();
void set_scissor(bool clip_viewport);
void bind_viewport();
void sync_hint(rsx::FIFO_hint hint) override;