/* * Apply stencil and depth testing to the span of pixels. * Both software and hardware stencil buffers are acceptable. * Input: n - number of pixels in the span * x, y - location of leftmost pixel in span * z - array [n] of z values * mask - array [n] of flags (1=test this pixel, 0=skip the pixel) * Output: mask - array [n] of flags (1=stencil and depth test passed) * Return: GL_TRUE - all fragments failed the testing * GL_FALSE - one or more fragments passed the testing * */ GLboolean _mesa_stencil_and_ztest_span( GLcontext *ctx, GLuint n, GLint x, GLint y, const GLdepth z[], GLubyte mask[] ) { GLstencil stencilRow[MAX_WIDTH]; GLstencil *stencil; GLboolean result; ASSERT(ctx->Stencil.Enabled); ASSERT(n <= MAX_WIDTH); /* Get initial stencil values */ if (ctx->Driver.WriteStencilSpan) { ASSERT(ctx->Driver.ReadStencilSpan); /* Get stencil values from the hardware stencil buffer */ (*ctx->Driver.ReadStencilSpan)(ctx, n, x, y, stencilRow); stencil = stencilRow; } else { /* software stencil buffer */ stencil = STENCIL_ADDRESS(x, y); } /* do all the stencil/depth testing/updating */ result = stencil_and_ztest_span( ctx, n, x, y, z, stencil, mask ); if (ctx->Driver.WriteStencilSpan) { /* Write updated stencil values into hardware stencil buffer */ (ctx->Driver.WriteStencilSpan)(ctx, n, x, y, stencil, mask ); } return result; }
/** * /return GL_TRUE = one or more fragments passed, * GL_FALSE = all fragments failed. */ GLboolean _swrast_stencil_and_ztest_span(GLcontext *ctx, SWspan *span) { if (span->arrayMask & SPAN_XY) return stencil_and_ztest_pixels(ctx, span, span->facing); else return stencil_and_ztest_span(ctx, span, span->facing); }
/** * /return GL_TRUE = one or more fragments passed, * GL_FALSE = all fragments failed. */ GLboolean _swrast_stencil_and_ztest_span(GLcontext *ctx, struct sw_span *span) { /* span->facing can only be non-zero if using two-sided stencil */ ASSERT(ctx->Stencil.TestTwoSide || span->facing == 0); if (span->arrayMask & SPAN_XY) return stencil_and_ztest_pixels(ctx, span, span->facing); else return stencil_and_ztest_span(ctx, span, span->facing); }
/** * /return GL_TRUE = one or more fragments passed, * GL_FALSE = all fragments failed. */ GLboolean _swrast_stencil_and_ztest_span(struct gl_context *ctx, SWspan *span) { const GLuint face = (span->facing == 0) ? 0 : ctx->Stencil._BackFace; if (span->arrayMask & SPAN_XY) return stencil_and_ztest_pixels(ctx, span, face); else return stencil_and_ztest_span(ctx, span, face); }