gl4: depth test issue in non-autosort mode
Depth testing is done in the fragment shader so it shouldn't be done in the a-buffer shader for the first pixel, or until the depth is updated. Fixes flashlight and lightstorm effects in Alone in the Dark
This commit is contained in:
parent
d5e24d8aed
commit
632aa95c2d
|
@ -72,46 +72,53 @@ vec4 resolveAlphaBlend(ivec2 coords) { \n\
|
|||
vec4 secondaryBuffer = vec4(0.0); // Secondary accumulation buffer \n\
|
||||
float depth = 1.0; \n\
|
||||
\n\
|
||||
bool do_depth_test = false; \n\
|
||||
for (int i = 0; i < num_frag; i++) \n\
|
||||
{ \n\
|
||||
const Pixel pixel = pixels[pixel_list[i]]; \n\
|
||||
const PolyParam pp = tr_poly_params[getPolyNumber(pixel)]; \n\
|
||||
#if DEPTH_SORTED != 1 \n\
|
||||
const float frag_depth = pixel.depth; \n\
|
||||
switch (getDepthFunc(pp)) \n\
|
||||
if (do_depth_test) \n\
|
||||
{ \n\
|
||||
case 0: // Never \n\
|
||||
continue; \n\
|
||||
case 1: // Greater \n\
|
||||
if (frag_depth <= depth) \n\
|
||||
switch (getDepthFunc(pp)) \n\
|
||||
{ \n\
|
||||
case 0: // Never \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 2: // Equal \n\
|
||||
if (frag_depth != depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 3: // Greater or equal \n\
|
||||
if (frag_depth < depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 4: // Less \n\
|
||||
if (frag_depth >= depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 5: // Not equal \n\
|
||||
if (frag_depth == depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 6: // Less or equal \n\
|
||||
if (frag_depth > depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 7: // Always \n\
|
||||
break; \n\
|
||||
case 1: // Greater \n\
|
||||
if (frag_depth <= depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 2: // Equal \n\
|
||||
if (frag_depth != depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 3: // Greater or equal \n\
|
||||
if (frag_depth < depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 4: // Less \n\
|
||||
if (frag_depth >= depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 5: // Not equal \n\
|
||||
if (frag_depth == depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 6: // Less or equal \n\
|
||||
if (frag_depth > depth) \n\
|
||||
continue; \n\
|
||||
break; \n\
|
||||
case 7: // Always \n\
|
||||
break; \n\
|
||||
} \n\
|
||||
} \n\
|
||||
\n\
|
||||
if (getDepthMask(pp)) \n\
|
||||
{ \n\
|
||||
depth = frag_depth; \n\
|
||||
do_depth_test = true; \n\
|
||||
} \n\
|
||||
#endif \n\
|
||||
bool area1 = false; \n\
|
||||
bool shadowed = false; \n\
|
||||
|
@ -207,7 +214,7 @@ void main(void) \n\
|
|||
ivec2 coords = ivec2(gl_FragCoord.xy); \n\
|
||||
// Compute and output final color for the frame buffer \n\
|
||||
// Visualize the number of layers in use \n\
|
||||
//FragColor = vec4(float(fillFragmentArray(coords)) / MAX_PIXELS_PER_FRAGMENT, 0, 0, 1); \n\
|
||||
//FragColor = vec4(float(fillAndSortFragmentArray(coords)) / MAX_PIXELS_PER_FRAGMENT * 4, 0, 0, 1); \n\
|
||||
FragColor = resolveAlphaBlend(coords); \n\
|
||||
} \n\
|
||||
";
|
||||
|
|
|
@ -103,7 +103,7 @@ static void SetTextureRepeatMode(int index, GLuint dir, u32 clamp, u32 mirror)
|
|||
}
|
||||
|
||||
template <u32 Type, bool SortingEnabled>
|
||||
static void SetGPState(const PolyParam* gp, int pass, u32 cflip=0)
|
||||
static void SetGPState(PolyParam* gp, int pass)
|
||||
{
|
||||
if (gp->pcw.Texture && gp->tsp.FilterMode > 1)
|
||||
{
|
||||
|
@ -231,14 +231,14 @@ template <u32 Type, bool SortingEnabled>
|
|||
//set cull mode !
|
||||
//cflip is required when exploding triangles for triangle sorting
|
||||
//gcflip is global clip flip, needed for when rendering to texture due to mirrored Y direction
|
||||
SetCull(gp->isp.CullMode^cflip^gcflip);
|
||||
SetCull(gp->isp.CullMode ^ gcflip);
|
||||
|
||||
//set Z mode, only if required
|
||||
if (Type == ListType_Punch_Through || (Type == ListType_Translucent && SortingEnabled))
|
||||
if (Type == ListType_Punch_Through)
|
||||
{
|
||||
glcache.DepthFunc(Zfunction[6]); // Greater or equal
|
||||
}
|
||||
else
|
||||
else if (Type == ListType_Opaque)
|
||||
{
|
||||
glcache.DepthFunc(Zfunction[gp->isp.DepthMode]);
|
||||
}
|
||||
|
@ -246,7 +246,8 @@ template <u32 Type, bool SortingEnabled>
|
|||
// Depth buffer is updated in pass 0 (and also in pass 1 for OP PT)
|
||||
if (pass < 2)
|
||||
{
|
||||
// Ignore ZWriteDis for punch-through? fixes Worms World Party
|
||||
// Z Write Disable seems to be ignored for punch-through polys
|
||||
// Fixes Worms World Party, Bust-a-Move 4 and Re-Volt
|
||||
if (Type == ListType_Punch_Through)
|
||||
glcache.DepthMask(GL_TRUE);
|
||||
else
|
||||
|
@ -256,7 +257,7 @@ template <u32 Type, bool SortingEnabled>
|
|||
glcache.DepthMask(GL_FALSE);
|
||||
}
|
||||
|
||||
template <u32 Type, bool SortingEnabled>
|
||||
template <u32 Type, bool SortingEnabled, bool OnlyAlwaysDepth>
|
||||
static void DrawList(const List<PolyParam>& gply, int first, int count, int pass)
|
||||
{
|
||||
PolyParam* params = &gply.head()[first];
|
||||
|
@ -279,7 +280,7 @@ static void DrawList(const List<PolyParam>& gply, int first, int count, int pass
|
|||
continue;
|
||||
}
|
||||
}
|
||||
if (pass == 0 && Type == ListType_Translucent && (params->isp.DepthMode != 7 || params->isp.ZWriteDis))
|
||||
if (OnlyAlwaysDepth && (params->isp.DepthMode != 7 || params->isp.ZWriteDis))
|
||||
{
|
||||
params++;
|
||||
continue;
|
||||
|
@ -534,8 +535,8 @@ void gl4DrawStrips(GLuint output_fbo, int width, int height)
|
|||
glcache.Enable(GL_STENCIL_TEST);
|
||||
glcache.StencilOp(GL_KEEP, GL_KEEP, GL_REPLACE);
|
||||
|
||||
DrawList<ListType_Opaque, false>(pvrrc.global_param_op, previous_pass.op_count, current_pass.op_count - previous_pass.op_count, 0);
|
||||
DrawList<ListType_Punch_Through, false>(pvrrc.global_param_pt, previous_pass.pt_count, current_pass.pt_count - previous_pass.pt_count, 0);
|
||||
DrawList<ListType_Opaque, false, false>(pvrrc.global_param_op, previous_pass.op_count, current_pass.op_count - previous_pass.op_count, 0);
|
||||
DrawList<ListType_Punch_Through, false, false>(pvrrc.global_param_pt, previous_pass.pt_count, current_pass.pt_count - previous_pass.pt_count, 0);
|
||||
|
||||
// Modifier volumes
|
||||
if (settings.rend.ModifierVolumes)
|
||||
|
@ -570,10 +571,10 @@ void gl4DrawStrips(GLuint output_fbo, int width, int height)
|
|||
glCheck();
|
||||
|
||||
//Opaque
|
||||
DrawList<ListType_Opaque, false>(pvrrc.global_param_op, previous_pass.op_count, current_pass.op_count - previous_pass.op_count, 1);
|
||||
DrawList<ListType_Opaque, false, false>(pvrrc.global_param_op, previous_pass.op_count, current_pass.op_count - previous_pass.op_count, 1);
|
||||
|
||||
//Alpha tested
|
||||
DrawList<ListType_Punch_Through, false>(pvrrc.global_param_pt, previous_pass.pt_count, current_pass.pt_count - previous_pass.pt_count, 1);
|
||||
DrawList<ListType_Punch_Through, false, false>(pvrrc.global_param_pt, previous_pass.pt_count, current_pass.pt_count - previous_pass.pt_count, 1);
|
||||
|
||||
// Unbind stencil
|
||||
glActiveTexture(GL_TEXTURE3);
|
||||
|
@ -597,7 +598,7 @@ void gl4DrawStrips(GLuint output_fbo, int width, int height)
|
|||
glColorMask(GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE);
|
||||
glcache.Enable(GL_DEPTH_TEST);
|
||||
glcache.DepthMask(GL_TRUE);
|
||||
DrawList<ListType_Translucent, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
DrawList<ListType_Translucent, false, true>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
}
|
||||
//
|
||||
// PASS 3: Render TR to a-buffers
|
||||
|
@ -611,9 +612,9 @@ void gl4DrawStrips(GLuint output_fbo, int width, int height)
|
|||
|
||||
//Alpha blended
|
||||
if (current_pass.autosort)
|
||||
DrawList<ListType_Translucent, true>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 3); // 3 because pass 2 is no more
|
||||
DrawList<ListType_Translucent, true, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 3); // 3 because pass 2 is no more
|
||||
else
|
||||
DrawList<ListType_Translucent, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 3); // 3 because pass 2 is no more
|
||||
DrawList<ListType_Translucent, false, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 3); // 3 because pass 2 is no more
|
||||
glCheck();
|
||||
|
||||
// Translucent modifier volumes
|
||||
|
@ -632,9 +633,9 @@ void gl4DrawStrips(GLuint output_fbo, int width, int height)
|
|||
|
||||
glcache.Enable(GL_DEPTH_TEST);
|
||||
if (current_pass.autosort)
|
||||
DrawList<ListType_Translucent, true>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
DrawList<ListType_Translucent, true, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
else
|
||||
DrawList<ListType_Translucent, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
DrawList<ListType_Translucent, false, false>(pvrrc.global_param_tr, previous_pass.tr_count, current_pass.tr_count - previous_pass.tr_count, 0);
|
||||
|
||||
//
|
||||
// PASS 3c: Render a-buffer to temporary texture
|
||||
|
|
|
@ -264,7 +264,8 @@ __forceinline
|
|||
glcache.DepthMask(GL_FALSE);
|
||||
else
|
||||
{
|
||||
// Ignore ZWriteDis for punch-through? fixes Worms World Party
|
||||
// Z Write Disable seems to be ignored for punch-through.
|
||||
// Fixes Worms World Party, Bust-a-Move 4 and Re-Volt
|
||||
if (Type == ListType_Punch_Through)
|
||||
glcache.DepthMask(GL_TRUE);
|
||||
else
|
||||
|
|
Loading…
Reference in New Issue