mirror of
https://github.com/wheremyfoodat/Panda3DS.git
synced 2025-04-06 22:25:41 +12:00
renderer_gl: Implement stencil testing
This commit is contained in:
parent
037d16ae7c
commit
95a8917589
3 changed files with 59 additions and 1 deletions
|
@ -55,6 +55,8 @@ namespace PICA {
|
|||
BlendFunc = 0x101,
|
||||
BlendColour = 0x103,
|
||||
AlphaTestConfig = 0x104,
|
||||
StencilTest = 0x105,
|
||||
StencilOp = 0x106,
|
||||
DepthAndColorMask = 0x107,
|
||||
DepthBufferFormat = 0x116,
|
||||
ColourBufferFormat = 0x117,
|
||||
|
|
|
@ -61,6 +61,7 @@ class RendererGL final : public Renderer {
|
|||
|
||||
MAKE_LOG_FUNCTION(log, rendererLogger)
|
||||
void setupBlending();
|
||||
void setupStencilTest(bool stencilEnable);
|
||||
void bindDepthBuffer();
|
||||
void setupTextureEnvState();
|
||||
void bindTexturesToSlots();
|
||||
|
@ -79,4 +80,4 @@ class RendererGL final : public Renderer {
|
|||
|
||||
// Take a screenshot of the screen and store it in a file
|
||||
void screenshot(const std::string& name) override;
|
||||
};
|
||||
};
|
||||
|
|
|
@ -205,6 +205,51 @@ void RendererGL::setupBlending() {
|
|||
}
|
||||
}
|
||||
|
||||
void RendererGL::setupStencilTest(bool stencilEnable) {
|
||||
if (!stencilEnable) {
|
||||
OpenGL::disableStencil();
|
||||
return;
|
||||
}
|
||||
|
||||
static constexpr std::array<GLenum, 8> stencilFuncs = {
|
||||
GL_NEVER,
|
||||
GL_ALWAYS,
|
||||
GL_EQUAL,
|
||||
GL_NOTEQUAL,
|
||||
GL_LESS,
|
||||
GL_LEQUAL,
|
||||
GL_GREATER,
|
||||
GL_GEQUAL
|
||||
};
|
||||
OpenGL::enableStencil();
|
||||
|
||||
const u32 stencilConfig = regs[PICA::InternalRegs::StencilTest];
|
||||
const u32 stencilFunc = getBits<4, 3>(stencilConfig);
|
||||
const u32 stencilBufferMask = getBits<8, 8>(stencilConfig);
|
||||
const s32 reference = s8(getBits<16, 8>(stencilConfig)); // Signed reference value
|
||||
const u32 stencilRefMask = getBits<24, 8>(stencilConfig);
|
||||
|
||||
glStencilFunc(stencilFuncs[stencilFunc], reference, stencilRefMask);
|
||||
glStencilMask(stencilBufferMask);
|
||||
|
||||
static constexpr std::array<GLenum, 8> stencilOps = {
|
||||
GL_KEEP,
|
||||
GL_ZERO,
|
||||
GL_REPLACE,
|
||||
GL_INCR,
|
||||
GL_DECR,
|
||||
GL_INVERT,
|
||||
GL_INCR_WRAP,
|
||||
GL_DECR_WRAP
|
||||
};
|
||||
const u32 stencilOpConfig = regs[PICA::InternalRegs::StencilOp];
|
||||
const u32 stencilFailOp = getBits<0, 3>(stencilOpConfig);
|
||||
const u32 depthFailOp = getBits<4, 3>(stencilOpConfig);
|
||||
const u32 passOp = getBits<8, 3>(stencilOpConfig);
|
||||
|
||||
glStencilOp(stencilOps[stencilFailOp], stencilOps[depthFailOp], stencilOps[passOp]);
|
||||
}
|
||||
|
||||
void RendererGL::setupTextureEnvState() {
|
||||
// TODO: Only update uniforms when the TEV config changed. Use an UBO potentially.
|
||||
|
||||
|
@ -356,6 +401,9 @@ void RendererGL::drawVertices(PICA::PrimType primType, std::span<const Vertex> v
|
|||
GLsizei viewportHeight = GLsizei(f24::fromRaw(regs[PICA::InternalRegs::ViewportHeight] & 0xffffff).toFloat32() * 2.0f);
|
||||
OpenGL::setViewport(viewportWidth, viewportHeight);
|
||||
|
||||
const u32 stencilConfig = regs[PICA::InternalRegs::StencilTest];
|
||||
const bool stencilEnable = getBit<0>(stencilConfig);
|
||||
|
||||
// Note: The code below must execute after we've bound the colour buffer & its framebuffer
|
||||
// Because it attaches a depth texture to the aforementioned colour buffer
|
||||
if (depthEnable) {
|
||||
|
@ -371,9 +419,15 @@ void RendererGL::drawVertices(PICA::PrimType primType, std::span<const Vertex> v
|
|||
bindDepthBuffer();
|
||||
} else {
|
||||
gl.disableDepth();
|
||||
|
||||
if (stencilEnable) {
|
||||
bindDepthBuffer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setupStencilTest(stencilEnable);
|
||||
|
||||
vbo.bufferVertsSub(vertices);
|
||||
OpenGL::draw(primitiveTopology, GLsizei(vertices.size()));
|
||||
}
|
||||
|
@ -476,6 +530,7 @@ void RendererGL::displayTransfer(u32 inputAddr, u32 outputAddr, u32 inputSize, u
|
|||
gl.disableBlend();
|
||||
gl.disableDepth();
|
||||
gl.disableScissor();
|
||||
OpenGL::disableStencil();
|
||||
gl.setColourMask(true, true, true, true);
|
||||
gl.useProgram(displayProgram);
|
||||
gl.bindVAO(dummyVAO);
|
||||
|
|
Loading…
Add table
Reference in a new issue