diff --git a/Source/Core/VideoBackends/OGL/Render.cpp b/Source/Core/VideoBackends/OGL/Render.cpp index 5319e41cbd..945dbadcf1 100644 --- a/Source/Core/VideoBackends/OGL/Render.cpp +++ b/Source/Core/VideoBackends/OGL/Render.cpp @@ -1290,8 +1290,11 @@ void Renderer::SetAndClearFramebuffer(const AbstractFramebuffer* framebuffer, glClear(clear_mask); } -void Renderer::ApplyBlendingState(const BlendingState& state) +void Renderer::ApplyBlendingState(const BlendingState state, bool force) { + if (!force && m_current_blend_state == state) + return; + bool useDualSource = state.usedualsrc && g_ActiveConfig.backend_info.bSupportsDualSourceBlend && (!DriverDetails::HasBug(DriverDetails::BUG_BROKEN_DUAL_SOURCE_BLENDING) || state.dstalpha); @@ -1364,6 +1367,7 @@ void Renderer::ApplyBlendingState(const BlendingState& state) } glColorMask(state.colorupdate, state.colorupdate, state.colorupdate, state.alphaupdate); + m_current_blend_state = state; } // This function has the final picture. We adjust the aspect ratio here. @@ -1561,15 +1565,19 @@ void Renderer::RestoreAPIState() glEnable(GL_CLIP_DISTANCE0); glEnable(GL_CLIP_DISTANCE1); } - BPFunctions::SetGenerationMode(); BPFunctions::SetScissor(); BPFunctions::SetViewport(); - BPFunctions::SetDepthMode(); - BPFunctions::SetBlendMode(); + + ApplyRasterizationState(m_current_rasterization_state, true); + ApplyDepthState(m_current_depth_state, true); + ApplyBlendingState(m_current_blend_state, true); } -void Renderer::ApplyRasterizationState(const RasterizationState& state) +void Renderer::ApplyRasterizationState(const RasterizationState state, bool force) { + if (!force && m_current_rasterization_state == state) + return; + // none, ccw, cw, ccw if (state.cullmode != GenMode::CULL_NONE) { @@ -1581,10 +1589,15 @@ void Renderer::ApplyRasterizationState(const RasterizationState& state) { glDisable(GL_CULL_FACE); } + + m_current_rasterization_state = state; } -void Renderer::ApplyDepthState(const DepthState& state) +void Renderer::ApplyDepthState(const DepthState state, bool force) { + if (!force && m_current_depth_state == state) + return; + const GLenum glCmpFuncs[8] = {GL_NEVER, GL_LESS, GL_EQUAL, GL_LEQUAL, GL_GREATER, GL_NOTEQUAL, GL_GEQUAL, GL_ALWAYS}; @@ -1602,6 +1615,8 @@ void Renderer::ApplyDepthState(const DepthState& state) glDisable(GL_DEPTH_TEST); glDepthMask(GL_FALSE); } + + m_current_depth_state = state; } void Renderer::SetPipeline(const AbstractPipeline* pipeline) diff --git a/Source/Core/VideoBackends/OGL/Render.h b/Source/Core/VideoBackends/OGL/Render.h index 3f1277a0c2..d8882e2111 100644 --- a/Source/Core/VideoBackends/OGL/Render.h +++ b/Source/Core/VideoBackends/OGL/Render.h @@ -154,12 +154,15 @@ private: void CheckForSurfaceChange(); void CheckForSurfaceResize(); - void ApplyBlendingState(const BlendingState& state); - void ApplyRasterizationState(const RasterizationState& state); - void ApplyDepthState(const DepthState& state); + void ApplyBlendingState(const BlendingState state, bool force = false); + void ApplyRasterizationState(const RasterizationState state, bool force = false); + void ApplyDepthState(const DepthState state, bool force = false); void UploadUtilityUniforms(const void* uniforms, u32 uniforms_size); std::array m_bound_textures{}; const OGLPipeline* m_graphics_pipeline = nullptr; + RasterizationState m_current_rasterization_state = {}; + DepthState m_current_depth_state = {}; + BlendingState m_current_blend_state = {}; }; }