I have troubles with the depth peeling technique and coplanar surfaces. The original algorithm is able to peel only one layer at the i-th depth, so if you have more than one, only one will be peeled.
Extending F2B: We present the Z-fighting free F2B (F2BZF) depth peeling by adapting the F2B algorithm to peel all fragments placed at the same depth.
When we have peeled all fragments at one depth, the next depth layer underneath is returned. To obtain all fragments at the same depth we discard the fragments that are not placed at this depth.
To distinguish among z-fighting fragments, we extract (peel) the color of the fragment which has the maximum primitive identifier (build-in variable glPrimitiveID of GLSL [Kessenich 2009]). One extra geometry pass is used to calculate the sum of the (remaining, not peeled) z-fighting fragments and find which of them should be extracted next. We discard peeled fragments of the same depth by eliminating all fragments that have a primitive identifier smaller than the maximum primitive id determined during the previous step. Both computations are performed in one pass using additive and maximum blending operations respectively.
I dont get how he can calculate the sum of the remaining z-fighting fragments and the next hightest id with the add and max blending…
// Descpiption:
// (1) Initialization of the depth layer.
#version 330 core
layout(location = 0, index = 0) out vec4 out_frag_depth;
void main(void)
{
out_frag_depth.r = -gl_FragCoord.z;
}
Peel:
// Descpiption:
// (1) Extract the color of the fragment with the maximum ID.
// (2) Calculate next depth layer.
#version 330 core
#extension GL_EXT_gpu_shader4 : enable
vec4 computePixelColor();
uniform sampler2DRect tex_depth;
uniform sampler2DRect tex_count_id;
layout(location = 0, index = 0) out vec4 out_frag_depth;
layout(location = 1, index = 0) out vec4 out_frag_color;
void main(void)
{
ivec2 count_id;
float depth;
depth = -texture(tex_depth , gl_FragCoord.xy).r;
count_id = ivec2(texture(tex_count_id, gl_FragCoord.xy).ra);
if (gl_FragCoord.z < depth)
discard;
out_frag_color = (gl_PrimitiveID == count_id.y) ? computePixelColor() : vec4(0.0f);
if (count_id.x <= 1 && gl_FragCoord.z == depth) out_frag_depth.r = -1.0f;
else if(count_id.x > 1 && gl_FragCoord.z > depth) out_frag_depth.r = -1.0f;
else out_frag_depth.r = -gl_FragCoord.z;
}
And blend:
// Descpiption:
// (1) Calculate the sum of the (remaining, not peeled) z-fighting fragments.
// (2) Find which of them should be extracted next.
#version 330 core
#extension GL_EXT_gpu_shader4 : enable
uniform sampler2DRect tex_depth;
uniform sampler2DRect tex_count_id;
layout(location = 0, index = 0) out vec4 out_frag_count_id;
void main(void)
{
float depth;
depth = -texture(tex_depth, gl_FragCoord.xy).r;
if(gl_FragCoord.z == depth)
{
ivec2 count_id;
count_id = ivec2(texture (tex_count_id, gl_FragCoord.xy).ra);
if(count_id.x <= 1 || count_id.y > gl_PrimitiveID)
out_frag_count_id.ra = vec2(1.0f, gl_PrimitiveID);
}
else
discard;
}
As far as I got it, he is encoding the number of layers to be peeled and the highest primitive id in the .r and .a component of tex_count_id
I need help, it is not clear to me and moreover I do not get why he claims he is using max blending for the peeling and max and add blending for the blending step…