From 6409cbad092e93c12d43930721a73e38fd8e7f7e Mon Sep 17 00:00:00 2001 From: Steveplays28 Date: Thu, 5 Oct 2023 20:18:09 +0200 Subject: [PATCH] fix: Fix depth test and GL state restoration --- .../core/config/gui/OpenGLConfigScreen.java | 2 +- .../core/render/glObject/GLState.java | 88 +++++++++++-------- .../core/render/renderer/DebugRenderer.java | 2 +- .../core/render/renderer/LodRenderer.java | 62 ++++++++----- .../core/render/renderer/SSAORenderer.java | 4 +- .../core/render/renderer/TestRenderer.java | 2 +- .../render/renderer/shaders/DarkShader.java | 2 +- .../render/renderer/shaders/FogShader.java | 2 +- 8 files changed, 95 insertions(+), 69 deletions(-) diff --git a/core/src/main/java/com/seibel/distanthorizons/core/config/gui/OpenGLConfigScreen.java b/core/src/main/java/com/seibel/distanthorizons/core/config/gui/OpenGLConfigScreen.java index 7f9b82011..586438062 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/config/gui/OpenGLConfigScreen.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/config/gui/OpenGLConfigScreen.java @@ -120,7 +120,7 @@ public class OpenGLConfigScreen extends AbstractScreen GL32.glDrawArrays(GL32.GL_TRIANGLE_FAN, 0, 4); GL32.glClear(GL32.GL_DEPTH_BUFFER_BIT); - state.restore(SingletonInjector.INSTANCE.get(IMinecraftRenderWrapper.class).getTargetFrameBuffer()); + state.restore(); } @Override diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/glObject/GLState.java b/core/src/main/java/com/seibel/distanthorizons/core/render/glObject/GLState.java index e025e4ded..216a2067f 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/glObject/GLState.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/glObject/GLState.java @@ -30,7 +30,6 @@ public class GLState public int vbo; public int ebo; public int[] fbo; - public int depthBuffer; public int texture2D; /** IE: GL_TEXTURE0, GL_TEXTURE1, etc. */ public int activeTextureNumber; @@ -56,19 +55,9 @@ public class GLState public int polyMode; - public GLState() - { + public GLState() { this.fbo = new int[FBO_MAX]; - for (int i = 0; i < FBO_MAX; i++) - { - this.fbo[i] = GL32.glGenFramebuffers(); - } - - GL32.glEnable(GL32.GL_DEPTH_TEST); - GL32.glDepthFunc(GL32.GL_LESS); - GL32.glDepthMask(true); - this.saveState(); } @@ -80,11 +69,18 @@ public class GLState this.ebo = GL32.glGetInteger(GL32.GL_ELEMENT_ARRAY_BUFFER_BINDING); GL32.glGetIntegerv(GL32.GL_FRAMEBUFFER_BINDING, this.fbo); - + this.texture2D = GL32.glGetInteger(GL32.GL_TEXTURE_BINDING_2D); - this.texture0 = GL32.glGenTextures(); - this.texture1 = GL32.glGenTextures(); - + this.activeTextureNumber = GL32.glGetInteger(GL32.GL_ACTIVE_TEXTURE); + + GL32.glActiveTexture(GL32.GL_TEXTURE0); + this.texture0 = GL32.glGetInteger(GL32.GL_TEXTURE_BINDING_2D); + + GL32.glActiveTexture(GL32.GL_TEXTURE1); + this.texture1 = GL32.glGetInteger(GL32.GL_TEXTURE_BINDING_2D); + + GL32.glActiveTexture(this.activeTextureNumber); + this.blend = GL32.glIsEnabled(GL32.GL_BLEND); this.blendEqRGB = GL32.glGetInteger(GL32.GL_BLEND_EQUATION_RGB); this.blendEqAlpha = GL32.glGetInteger(GL32.GL_BLEND_EQUATION_ALPHA); @@ -110,7 +106,7 @@ public class GLState public String toString() { return "GLState{" + - "program=" + this.program + ", vao=" + this.vao + ", vbo=" + this.vbo + ", ebo=" + this.ebo + ", fbo=" + this.fbo + + "program=" + this.program + ", vao=" + this.vao + ", vbo=" + this.vbo + ", ebo=" + this.ebo + ", fbo=" + this.fbo[0] + ", text=" + GLEnums.getString(this.texture2D) + "@" + this.activeTextureNumber + ", text0=" + GLEnums.getString(this.texture0) + ", blend=" + this.blend + ", blendMode=" + GLEnums.getString(this.blendSrcColor) + "," + GLEnums.getString(this.blendDstColor) + ", depth=" + this.depth + @@ -122,15 +118,23 @@ public class GLState '}'; } - public void restoreFrameBuffer() + public void RestoreFrameBuffer() { - GL32.glBindTexture(GL32.GL_TEXTURE_2D, 0); - GL32.glBindBuffer(GL32.GL_ARRAY_BUFFER, 0); + // explicitly unbinding the frame buffer is necessary to prevent GL_CLEAR calls from hitting the wrong buffer + GL32.glBindFramebuffer(GL32.GL_FRAMEBUFFER, 0); + + for (int i = 0; i < FBO_MAX; i++) + { + int buffer = this.fbo[i]; + if (i > 0 && buffer == 0) break; + + GL32.glBindFramebuffer(GL32.GL_FRAMEBUFFER, GL32.glIsFramebuffer(buffer) ? buffer : 0); + } } - public void restore(int minecraftFramebufferId) + public void restore() { - this.restoreFrameBuffer(); + this.RestoreFrameBuffer(); if (this.blend) { @@ -141,26 +145,35 @@ public class GLState GL32.glDisable(GL32.GL_BLEND); } - //GL32.glActiveTexture(GL32.GL_TEXTURE0); - //GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture0) ? this.texture0 : 0); - // - //GL32.glActiveTexture(GL32.GL_TEXTURE1); - //GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture1) ? this.texture1 : 0); - - //GL32.glActiveTexture(this.activeTextureNumber); - GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture2D) ? this.texture2D : 0); - - GL32.glBindVertexArray(0); - GL32.glBindFramebuffer(GL32.GL_FRAMEBUFFER, minecraftFramebufferId); - //GL32.glBindBuffer(GL32.GL_ARRAY_BUFFER, GL32.glIsBuffer(this.vbo) ? this.vbo : 0); - //GL32.glBindBuffer(GL32.GL_ELEMENT_ARRAY_BUFFER, GL32.glIsBuffer(this.ebo) ? this.ebo : 0); - //GL32.glUseProgram(GL32.glIsProgram(this.program) ? this.program : 0); + GL32.glActiveTexture(GL32.GL_TEXTURE0); + GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture0) ? this.texture0 : 0); - //GL32.glDepthMask(this.writeToDepthBuffer); + GL32.glActiveTexture(GL32.GL_TEXTURE1); + GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture1) ? this.texture1 : 0); + + GL32.glActiveTexture(this.activeTextureNumber); + GL32.glBindTexture(GL32.GL_TEXTURE_2D, GL32.glIsTexture(this.texture2D) ? this.texture2D : 0); + + GL32.glBindVertexArray(GL32.glIsVertexArray(this.vao) ? this.vao : 0); + GL32.glBindBuffer(GL32.GL_ARRAY_BUFFER, GL32.glIsBuffer(this.vbo) ? this.vbo : 0); + GL32.glBindBuffer(GL32.GL_ELEMENT_ARRAY_BUFFER, GL32.glIsBuffer(this.ebo) ? this.ebo: 0); + GL32.glUseProgram(GL32.glIsProgram(this.program) ? this.program : 0); + + GL32.glDepthMask(this.writeToDepthBuffer); //GL32.glBlendFunc(this.blendSrcColor, this.blendDstColor); GL32.glBlendEquationSeparate(this.blendEqRGB, this.blendEqAlpha); GL32.glBlendFuncSeparate(this.blendSrcColor, this.blendDstColor, this.blendSrcAlpha, this.blendDstAlpha); + if (this.depth) + { + GL32.glEnable(GL32.GL_DEPTH_TEST); + } + else + { + GL32.glDisable(GL32.GL_DEPTH_TEST); + } + GL32.glDepthFunc(this.depthFunc); + if (this.stencil) { GL32.glEnable(GL32.GL_STENCIL_TEST); @@ -183,5 +196,4 @@ public class GLState GL32.glCullFace(this.cullMode); GL32.glPolygonMode(GL32.GL_FRONT_AND_BACK, this.polyMode); } - } diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/DebugRenderer.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/DebugRenderer.java index 2491f3705..8b8396237 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/DebugRenderer.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/DebugRenderer.java @@ -228,7 +228,7 @@ public class DebugRenderer } - glState.restore(MC_RENDER.getTargetFrameBuffer()); + glState.restore(); } public void renderBox(Box box) diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/LodRenderer.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/LodRenderer.java index b581b05ab..8c0a0018c 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/LodRenderer.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/LodRenderer.java @@ -220,14 +220,15 @@ public class LodRenderer profiler.push("LOD draw setup"); + if (!this.isSetupComplete) + { + this.setup(); + } - // Generate and bind framebuffer, color texture, and depth render buffer as depth attachment - this.framebufferId = GL32.glGenFramebuffers(); - GL32.glClear(GL32.GL_COLOR_BUFFER_BIT | GL32.GL_DEPTH_BUFFER_BIT); + // Bind LOD color buffer GL32.glBindFramebuffer(GL32.GL_FRAMEBUFFER, this.framebufferId); - GL32.glViewport(0, 0, MC_RENDER.getTargetFrameBufferViewportWidth(), MC_RENDER.getTargetFrameBufferViewportHeight()); - this.colorTextureId = GL32.glGenTextures(); + // Bind LOD color texture GL32.glBindTexture(GL32.GL_TEXTURE_2D, this.colorTextureId); GL32.glTexImage2D(GL32.GL_TEXTURE_2D, 0, @@ -241,11 +242,17 @@ public class LodRenderer GL32.glTexParameteri(GL32.GL_TEXTURE_2D, GL32.GL_TEXTURE_MAG_FILTER, GL32.GL_LINEAR); GL32.glFramebufferTexture2D(GL32.GL_DRAW_FRAMEBUFFER, GL32.GL_COLOR_ATTACHMENT0, GL32.GL_TEXTURE_2D, this.colorTextureId, 0); - this.depthRenderbufferId = GL32.glGenRenderbuffers(); + // Bind LOD depth buffer GL32.glBindRenderbuffer(GL32.GL_RENDERBUFFER, this.depthRenderbufferId); - GL32.glRenderbufferStorage(GL32.GL_RENDERBUFFER, GL32.GL_DEPTH_COMPONENT32, MC_RENDER.getTargetFrameBufferViewportWidth(), MC_RENDER.getTargetFrameBufferViewportHeight()); + GL32.glRenderbufferStorage(GL32.GL_RENDERBUFFER, GL32.GL_DEPTH_COMPONENT24, MC_RENDER.getTargetFrameBufferViewportWidth(), MC_RENDER.getTargetFrameBufferViewportHeight()); GL32.glFramebufferRenderbuffer(GL32.GL_FRAMEBUFFER, GL32.GL_DEPTH_ATTACHMENT, GL32.GL_RENDERBUFFER, this.depthRenderbufferId); + // Clear LOD framebuffer and depth buffer + GL32.glClear(GL32.GL_COLOR_BUFFER_BIT | GL32.GL_DEPTH_BUFFER_BIT); + + GL32.glEnable(GL32.GL_DEPTH_TEST); + GL32.glDepthFunc(GL32.GL_LESS); + // Set OpenGL polygon mode boolean renderWireframe = Config.Client.Advanced.Debugging.renderWireframe.get(); if (renderWireframe) @@ -259,16 +266,14 @@ public class LodRenderer GL32.glEnable(GL32.GL_CULL_FACE); } - GL32.glDisable(GL32.GL_DEPTH_TEST); - - // Enable depth test + // Enable depth test and depth mask GL32.glEnable(GL32.GL_DEPTH_TEST); - // TODO: Fix depth test always failing - GL32.glDepthFunc(GL32.GL_ALWAYS); + GL32.glDepthFunc(GL32.GL_LESS); + GL32.glDepthMask(true); - // Disable blending and enable depth mask - GL32.glDisable(GL32.GL_BLEND); // We render opaque first, then transparent - GL32.glDepthMask(false); + // Disable blending + // We render opaque first, then transparent + GL32.glDisable(GL32.GL_BLEND); /*---------Bind required objects--------*/ // Setup LodRenderProgram and the LightmapTexture if it has not yet been done @@ -358,19 +363,16 @@ public class LodRenderer drawLagSpikeCatcher.end("LodDraw"); + profiler.popPush("LOD Blit"); + // Blit the LOD framebuffer onto Minecraft's framebuffer - GL32.glBindFramebuffer(GL32.GL_READ_FRAMEBUFFER, framebufferId); + GL32.glBindFramebuffer(GL32.GL_READ_FRAMEBUFFER, this.framebufferId); GL32.glBindFramebuffer(GL32.GL_DRAW_FRAMEBUFFER, MC_RENDER.getTargetFrameBuffer()); - GL32.glBlitFramebuffer(0, 0, MC_RENDER.getScreenWidth(), MC_RENDER.getScreenHeight(), - 0, 0, MC_RENDER.getScreenWidth(), MC_RENDER.getScreenHeight(), + GL32.glBlitFramebuffer(0, 0, MC_RENDER.getTargetFrameBufferViewportWidth(), MC_RENDER.getTargetFrameBufferViewportHeight(), + 0, 0, MC_RENDER.getTargetFrameBufferViewportWidth(), MC_RENDER.getTargetFrameBufferViewportHeight(), GL32.GL_COLOR_BUFFER_BIT, GL32.GL_NEAREST); - // Delete framebuffer, color texture, and depth texture - //GL32.glBindRenderbuffer(GL32.GL_RENDERBUFFER, 0); - GL32.glDeleteFramebuffers(this.framebufferId); - GL32.glDeleteTextures(this.colorTextureId); - GL32.glDeleteRenderbuffers(this.depthRenderbufferId); //================// @@ -395,7 +397,7 @@ public class LodRenderer profiler.popPush("LOD cleanup"); } - //minecraftGlState.restore(MC_RENDER.getTargetFrameBuffer()); + minecraftGlState.restore(); drawCleanup.end("LodDrawCleanup"); // end of internal LOD profiling @@ -437,6 +439,12 @@ public class LodRenderer this.quadIBO = new QuadElementBuffer(); this.quadIBO.reserve(AbstractRenderBuffer.MAX_QUADS_PER_BUFFER); } + + // Generate framebuffer, color texture, and depth render buffer + this.framebufferId = GL32.glGenFramebuffers(); + this.colorTextureId = GL32.glGenTextures(); + this.depthRenderbufferId = GL32.glGenRenderbuffers(); + EVENT_LOGGER.info("Renderer setup complete"); } @@ -493,6 +501,12 @@ public class LodRenderer this.quadIBO.destroy(false); } + // Delete framebuffer, color texture, and depth texture + //GL32.glBindRenderbuffer(GL32.GL_RENDERBUFFER, 0); + GL32.glDeleteFramebuffers(this.framebufferId); + GL32.glDeleteTextures(this.colorTextureId); + GL32.glDeleteRenderbuffers(this.depthRenderbufferId); + EVENT_LOGGER.info("Renderer Cleanup Complete"); }); } diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/SSAORenderer.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/SSAORenderer.java index d05e1c702..299fb03f4 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/SSAORenderer.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/SSAORenderer.java @@ -109,12 +109,12 @@ public class SSAORenderer SSAOShader.INSTANCE.FrameBuffer = this.ssaoFramebuffer; SSAOShader.INSTANCE.render(partialTicks); - primaryState.restoreFrameBuffer(); + primaryState.restore(); SSAOApplyShader.INSTANCE.BufferTexture = this.ssaoTexture; SSAOApplyShader.INSTANCE.render(partialTicks); - state.restore(MC_RENDER.getTargetFrameBuffer()); + state.restore(); } public void free() diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/TestRenderer.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/TestRenderer.java index dbc25a89d..fd91d5dfa 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/TestRenderer.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/TestRenderer.java @@ -136,7 +136,7 @@ public class TestRenderer GL32.glDrawArrays(GL32.GL_TRIANGLE_FAN, 0, 4); GL32.glClear(GL32.GL_DEPTH_BUFFER_BIT); - state.restore(MC_RENDER.getTargetFrameBuffer()); + state.restore(); spamLogger.incLogTries(); } diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/DarkShader.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/DarkShader.java index f61b0171a..0e9341faa 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/DarkShader.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/DarkShader.java @@ -58,6 +58,6 @@ public class DarkShader extends AbstractShaderRenderer ScreenQuad.INSTANCE.render(); - state.restore(MC_RENDER.getTargetFrameBuffer()); + state.restore(); } } diff --git a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/FogShader.java b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/FogShader.java index 770ac5212..d66b06eb8 100644 --- a/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/FogShader.java +++ b/core/src/main/java/com/seibel/distanthorizons/core/render/renderer/shaders/FogShader.java @@ -158,6 +158,6 @@ public class FogShader extends AbstractShaderRenderer ScreenQuad.INSTANCE.render(); - state.restore(MC_RENDER.getTargetFrameBuffer()); + state.restore(); } }