gl_state_tracker: Implement dirty flags for scissors
This commit is contained in:
parent
7f52efdf61
commit
ba6f390448
|
@ -1102,12 +1102,28 @@ void RasterizerOpenGL::SyncLogicOpState() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void RasterizerOpenGL::SyncScissorTest() {
|
void RasterizerOpenGL::SyncScissorTest() {
|
||||||
const auto& regs = system.GPU().Maxwell3D().regs;
|
auto& gpu = system.GPU().Maxwell3D();
|
||||||
|
auto& flags = gpu.dirty.flags;
|
||||||
|
if (!flags[Dirty::Scissors]) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
flags[Dirty::Scissors] = false;
|
||||||
|
|
||||||
|
const auto& regs = gpu.regs;
|
||||||
for (std::size_t index = 0; index < Maxwell::NumViewports; ++index) {
|
for (std::size_t index = 0; index < Maxwell::NumViewports; ++index) {
|
||||||
|
if (!flags[Dirty::Scissor0 + index]) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
flags[Dirty::Scissor0 + index] = false;
|
||||||
|
|
||||||
const auto& src = regs.scissor_test[index];
|
const auto& src = regs.scissor_test[index];
|
||||||
oglEnablei(GL_SCISSOR_TEST, src.enable, static_cast<GLuint>(index));
|
if (src.enable) {
|
||||||
glScissorIndexed(static_cast<GLuint>(index), src.min_x, src.min_y, src.max_x - src.min_x,
|
glEnablei(GL_SCISSOR_TEST, static_cast<GLuint>(index));
|
||||||
src.max_y - src.min_y);
|
glScissorIndexed(static_cast<GLuint>(index), src.min_x, src.min_y,
|
||||||
|
src.max_x - src.min_x, src.max_y - src.min_y);
|
||||||
|
} else {
|
||||||
|
glDisablei(GL_SCISSOR_TEST, static_cast<GLuint>(index));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -77,6 +77,14 @@ void SetupDirtyViewports(Tables& tables) {
|
||||||
tables[1][OFF(viewport_transform_enabled)] = Viewports;
|
tables[1][OFF(viewport_transform_enabled)] = Viewports;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void SetupDirtyScissors(Tables& tables) {
|
||||||
|
for (std::size_t i = 0; i < Regs::NumViewports; ++i) {
|
||||||
|
const std::size_t offset = OFF(scissor_test) + i * NUM(scissor_test[0]);
|
||||||
|
FillBlock(tables[0], offset, NUM(scissor_test[0]), Scissor0 + i);
|
||||||
|
}
|
||||||
|
FillBlock(tables[1], OFF(scissor_test), NUM(scissor_test), Scissors);
|
||||||
|
}
|
||||||
|
|
||||||
} // Anonymous namespace
|
} // Anonymous namespace
|
||||||
|
|
||||||
StateTracker::StateTracker(Core::System& system) : system{system} {}
|
StateTracker::StateTracker(Core::System& system) : system{system} {}
|
||||||
|
@ -97,6 +105,7 @@ void StateTracker::Initialize() {
|
||||||
auto& tables = dirty.tables;
|
auto& tables = dirty.tables;
|
||||||
SetupDirtyRenderTargets(tables);
|
SetupDirtyRenderTargets(tables);
|
||||||
SetupDirtyViewports(tables);
|
SetupDirtyViewports(tables);
|
||||||
|
SetupDirtyScissors(tables);
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace OpenGL
|
} // namespace OpenGL
|
||||||
|
|
|
@ -15,15 +15,30 @@ class System;
|
||||||
namespace OpenGL {
|
namespace OpenGL {
|
||||||
|
|
||||||
namespace Dirty {
|
namespace Dirty {
|
||||||
|
|
||||||
enum : u8 {
|
enum : u8 {
|
||||||
First = VideoCommon::Dirty::LastCommonEntry,
|
First = VideoCommon::Dirty::LastCommonEntry,
|
||||||
|
|
||||||
VertexFormats,
|
VertexFormats,
|
||||||
|
|
||||||
VertexBuffers,
|
VertexBuffers,
|
||||||
|
VertexBuffer0,
|
||||||
|
VertexBuffer31 = VertexBuffer0 + 31,
|
||||||
|
|
||||||
VertexInstances,
|
VertexInstances,
|
||||||
Shaders,
|
VertexInstance0,
|
||||||
Viewports,
|
VertexInstance31 = VertexInstance0 + 31,
|
||||||
|
|
||||||
ViewportTransform,
|
ViewportTransform,
|
||||||
|
Viewports,
|
||||||
|
Viewport0,
|
||||||
|
Viewport15 = Viewport0 + 15,
|
||||||
|
|
||||||
|
Scissors,
|
||||||
|
Scissor0,
|
||||||
|
Scissor15 = Scissor0 + 15,
|
||||||
|
|
||||||
|
Shaders,
|
||||||
CullTestEnable,
|
CullTestEnable,
|
||||||
FrontFace,
|
FrontFace,
|
||||||
CullFace,
|
CullFace,
|
||||||
|
@ -34,11 +49,11 @@ enum : u8 {
|
||||||
BlendState,
|
BlendState,
|
||||||
PolygonOffset,
|
PolygonOffset,
|
||||||
|
|
||||||
Viewport0,
|
Last
|
||||||
VertexBuffer0 = Viewport0 + 16,
|
|
||||||
VertexInstance0 = VertexBuffer0 + 32,
|
|
||||||
};
|
};
|
||||||
}
|
static_assert(Last <= 0xff);
|
||||||
|
|
||||||
|
} // namespace Dirty
|
||||||
|
|
||||||
class StateTracker {
|
class StateTracker {
|
||||||
public:
|
public:
|
||||||
|
@ -52,6 +67,12 @@ public:
|
||||||
flags[OpenGL::Dirty::Viewport0] = true;
|
flags[OpenGL::Dirty::Viewport0] = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void NotifyScissor0() {
|
||||||
|
auto& flags = system.GPU().Maxwell3D().dirty.flags;
|
||||||
|
flags[OpenGL::Dirty::Scissors] = true;
|
||||||
|
flags[OpenGL::Dirty::Scissor0] = true;
|
||||||
|
}
|
||||||
|
|
||||||
void NotifyFramebuffer() {
|
void NotifyFramebuffer() {
|
||||||
auto& flags = system.GPU().Maxwell3D().dirty.flags;
|
auto& flags = system.GPU().Maxwell3D().dirty.flags;
|
||||||
flags[VideoCommon::Dirty::RenderTargets] = true;
|
flags[VideoCommon::Dirty::RenderTargets] = true;
|
||||||
|
|
|
@ -519,6 +519,7 @@ void TextureCacheOpenGL::ImageBlit(View& src_view, View& dst_view,
|
||||||
UNIMPLEMENTED_IF(dst_params.target == SurfaceTarget::Texture3D);
|
UNIMPLEMENTED_IF(dst_params.target == SurfaceTarget::Texture3D);
|
||||||
|
|
||||||
// TODO: Signal state tracker about these changes
|
// TODO: Signal state tracker about these changes
|
||||||
|
state_tracker.NotifyScissor0();
|
||||||
state_tracker.NotifyFramebuffer();
|
state_tracker.NotifyFramebuffer();
|
||||||
|
|
||||||
if (dst_params.srgb_conversion) {
|
if (dst_params.srgb_conversion) {
|
||||||
|
|
|
@ -577,6 +577,7 @@ void RendererOpenGL::DrawScreen(const Layout::FramebufferLayout& layout) {
|
||||||
|
|
||||||
// TODO: Signal state tracker about these changes
|
// TODO: Signal state tracker about these changes
|
||||||
state_tracker.NotifyViewport0();
|
state_tracker.NotifyViewport0();
|
||||||
|
state_tracker.NotifyScissor0();
|
||||||
state_tracker.NotifyFramebuffer();
|
state_tracker.NotifyFramebuffer();
|
||||||
|
|
||||||
program_manager.UseVertexShader(vertex_program.handle);
|
program_manager.UseVertexShader(vertex_program.handle);
|
||||||
|
|
Reference in New Issue