diff --git a/radiantcore/CMakeLists.txt b/radiantcore/CMakeLists.txt index 56108cff58..62c97fde59 100644 --- a/radiantcore/CMakeLists.txt +++ b/radiantcore/CMakeLists.txt @@ -211,6 +211,7 @@ add_library(radiantcore MODULE rendersystem/backend/glprogram/GLSLDepthFillAlphaProgram.cpp rendersystem/backend/OpenGLShader.cpp rendersystem/backend/OpenGLShaderPass.cpp + rendersystem/backend/DepthFillPass.cpp rendersystem/debug/SpacePartitionRenderer.cpp rendersystem/GLFont.cpp rendersystem/OpenGLModule.cpp diff --git a/radiantcore/rendersystem/backend/DepthFillPass.cpp b/radiantcore/rendersystem/backend/DepthFillPass.cpp new file mode 100644 index 0000000000..209f899fc8 --- /dev/null +++ b/radiantcore/rendersystem/backend/DepthFillPass.cpp @@ -0,0 +1,35 @@ +#include "DepthFillPass.h" + +#include "../OpenGLRenderSystem.h" +#include "GLProgramFactory.h" + +namespace render +{ + +DepthFillPass::DepthFillPass(OpenGLShader& owner, OpenGLRenderSystem& renderSystem) : + OpenGLShaderPass(owner) +{ + // Mask colour => we only write to the depth buffer + _glState.setRenderFlag(RENDER_MASKCOLOUR); + + _glState.setRenderFlag(RENDER_FILL); + _glState.setRenderFlag(RENDER_CULLFACE); + _glState.setRenderFlag(RENDER_DEPTHTEST); + _glState.setRenderFlag(RENDER_DEPTHWRITE); + _glState.setRenderFlag(RENDER_PROGRAM); + + // Our shader will discard any fragments not passing the alphatest (if active) + _glState.setRenderFlag(RENDER_ALPHATEST); + + // We need texture coords and the full vertex attribute stack + _glState.setRenderFlag(RENDER_TEXTURE_2D); + _glState.setRenderFlag(RENDER_BUMP); + + // ZFILL will make this pass pretty much top priority + _glState.setSortPosition(OpenGLState::SORT_ZFILL); + + // Load the GLSL program tailored for this pass + _glState.glProgram = renderSystem.getGLProgramFactory().getBuiltInProgram("depthFillAlpha"); +} + +} diff --git a/radiantcore/rendersystem/backend/DepthFillPass.h b/radiantcore/rendersystem/backend/DepthFillPass.h new file mode 100644 index 0000000000..e5351fabd0 --- /dev/null +++ b/radiantcore/rendersystem/backend/DepthFillPass.h @@ -0,0 +1,21 @@ +#pragma once + +#include "OpenGLShaderPass.h" + +namespace render +{ + +class OpenGLRenderSystem; + +/** + * Special render pass filling the depth buffer. + * This is the first pass before any interaction shaders are run. + */ +class DepthFillPass : + public OpenGLShaderPass +{ +public: + DepthFillPass(OpenGLShader& owner, OpenGLRenderSystem& renderSystem); +}; + +} diff --git a/radiantcore/rendersystem/backend/OpenGLShader.cpp b/radiantcore/rendersystem/backend/OpenGLShader.cpp index fc5e94d069..c615c1216c 100644 --- a/radiantcore/rendersystem/backend/OpenGLShader.cpp +++ b/radiantcore/rendersystem/backend/OpenGLShader.cpp @@ -2,6 +2,7 @@ #include "GLProgramFactory.h" #include "../OpenGLRenderSystem.h" +#include "DepthFillPass.h" #include "icolourscheme.h" #include "ishaders.h" @@ -256,6 +257,12 @@ OpenGLState& OpenGLShader::appendDefaultPass() return state; } +OpenGLState& OpenGLShader::appendDepthFillPass() +{ + auto& pass = _shaderPasses.emplace_back(std::make_shared(*this, _renderSystem)); + return pass->state(); +} + // Test if we can render in bump map mode bool OpenGLShader::canUseLightingMode() const { @@ -316,23 +323,14 @@ void OpenGLShader::appendInteractionLayer(const DBSTriplet& triplet) if (triplet.needDepthFill && triplet.diffuse) { // Create depth-buffer fill pass with alpha test - OpenGLState& zPass = appendDefaultPass(); - zPass.setRenderFlag(RENDER_MASKCOLOUR); - zPass.setRenderFlag(RENDER_FILL); - zPass.setRenderFlag(RENDER_CULLFACE); - zPass.setRenderFlag(RENDER_DEPTHTEST); - zPass.setRenderFlag(RENDER_DEPTHWRITE); - zPass.setRenderFlag(RENDER_PROGRAM); - zPass.setRenderFlag(RENDER_ALPHATEST); - zPass.setRenderFlag(RENDER_TEXTURE_2D); - zPass.setRenderFlag(RENDER_BUMP); + OpenGLState& zPass = appendDepthFillPass(); + + // Store the alpha test value zPass.alphaThreshold = static_cast(alphaTest); - zPass.setSortPosition(OpenGLState::SORT_ZFILL); + // We need a diffuse stage to be able to performthe alpha test zPass.stage0 = triplet.diffuse; zPass.texture0 = getTextureOrInteractionDefault(triplet.diffuse)->getGLTexNum(); - - zPass.glProgram = _renderSystem.getGLProgramFactory().getBuiltInProgram("depthFillAlpha"); } // Add the DBS pass diff --git a/radiantcore/rendersystem/backend/OpenGLShader.h b/radiantcore/rendersystem/backend/OpenGLShader.h index aa6caaa3d6..d99eae75bc 100644 --- a/radiantcore/rendersystem/backend/OpenGLShader.h +++ b/radiantcore/rendersystem/backend/OpenGLShader.h @@ -70,6 +70,7 @@ class OpenGLShader final : // Add a shader pass to the end of the list, and return its state object OpenGLState& appendDefaultPass(); + OpenGLState& appendDepthFillPass(); // Test if we can render using lighting mode bool canUseLightingMode() const; diff --git a/radiantcore/rendersystem/backend/OpenGLShaderPass.h b/radiantcore/rendersystem/backend/OpenGLShaderPass.h index 910bfd25fd..73422704b6 100644 --- a/radiantcore/rendersystem/backend/OpenGLShaderPass.h +++ b/radiantcore/rendersystem/backend/OpenGLShaderPass.h @@ -25,6 +25,7 @@ class OpenGLShader; */ class OpenGLShaderPass { +protected: OpenGLShader& _owner; // The state applied to this bucket diff --git a/tools/msvc/DarkRadiantCore.vcxproj b/tools/msvc/DarkRadiantCore.vcxproj index d94f9e38e3..d34dc83165 100644 --- a/tools/msvc/DarkRadiantCore.vcxproj +++ b/tools/msvc/DarkRadiantCore.vcxproj @@ -598,6 +598,7 @@ + @@ -928,6 +929,7 @@ + diff --git a/tools/msvc/DarkRadiantCore.vcxproj.filters b/tools/msvc/DarkRadiantCore.vcxproj.filters index d7529927da..14c4e1a762 100644 --- a/tools/msvc/DarkRadiantCore.vcxproj.filters +++ b/tools/msvc/DarkRadiantCore.vcxproj.filters @@ -1042,6 +1042,9 @@ src\rendersystem\backend\glprogram + + src\rendersystem\backend + @@ -2127,5 +2130,8 @@ src\rendersystem\backend\glprogram + + src\rendersystem\backend + \ No newline at end of file