diff --git a/include/PICA/regs.hpp b/include/PICA/regs.hpp index 85cfe60e..53f74a9e 100644 --- a/include/PICA/regs.hpp +++ b/include/PICA/regs.hpp @@ -53,6 +53,7 @@ namespace PICA { // Framebuffer registers ColourOperation = 0x100, BlendFunc = 0x101, + LogicOp = 0x102, BlendColour = 0x103, AlphaTestConfig = 0x104, StencilTest = 0x105, @@ -294,4 +295,4 @@ namespace PICA { GeometryPrimitive = 3, }; -} // namespace PICA \ No newline at end of file +} // namespace PICA diff --git a/include/renderer_gl/renderer_gl.hpp b/include/renderer_gl/renderer_gl.hpp index 18f52a1c..94720e92 100644 --- a/include/renderer_gl/renderer_gl.hpp +++ b/include/renderer_gl/renderer_gl.hpp @@ -62,6 +62,7 @@ class RendererGL final : public Renderer { MAKE_LOG_FUNCTION(log, rendererLogger) void setupBlending(); void setupStencilTest(bool stencilEnable); + void setupLogicOp(); void bindDepthBuffer(); void setupTextureEnvState(); void bindTexturesToSlots(); diff --git a/src/core/renderer_gl/renderer_gl.cpp b/src/core/renderer_gl/renderer_gl.cpp index 91c70bba..e67ef44d 100644 --- a/src/core/renderer_gl/renderer_gl.cpp +++ b/src/core/renderer_gl/renderer_gl.cpp @@ -250,6 +250,30 @@ void RendererGL::setupStencilTest(bool stencilEnable) { glStencilOp(stencilOps[stencilFailOp], stencilOps[depthFailOp], stencilOps[passOp]); } +void RendererGL::setupLogicOp() { + const u32 logicOp = getBits<0, 4>(regs[PICA::InternalRegs::LogicOp]); + static constexpr std::array logicOps = { + GL_CLEAR, + GL_AND, + GL_AND_REVERSE, + GL_COPY, + GL_SET, + GL_COPY_INVERTED, + GL_NOOP, + GL_INVERT, + GL_NAND, + GL_OR, + GL_NOR, + GL_XOR, + GL_EQUIV, + GL_AND_INVERTED, + GL_OR_REVERSE, + GL_OR_INVERTED, + }; + + glLogicOp(logicOps[logicOp]); +} + void RendererGL::setupTextureEnvState() { // TODO: Only update uniforms when the TEV config changed. Use an UBO potentially. @@ -427,6 +451,7 @@ void RendererGL::drawVertices(PICA::PrimType primType, std::span v } setupStencilTest(stencilEnable); + setupLogicOp(); vbo.bufferVertsSub(vertices); OpenGL::draw(primitiveTopology, GLsizei(vertices.size()));