[Bf-blender-cvs] [5e7a56dc646] blender2.8: Eevee: Cleanup DoF implementation

Clément Foucault noreply at git.blender.org
Mon Sep 10 18:05:37 CEST 2018


Commit: 5e7a56dc646596c8cdac6f7ade8665c3ccbe201b
Author: Clément Foucault
Date:   Mon Sep 10 16:26:18 2018 +0200
Branches: blender2.8
https://developer.blender.org/rB5e7a56dc646596c8cdac6f7ade8665c3ccbe201b

Eevee: Cleanup DoF implementation

===================================================================

M	source/blender/draw/engines/eevee/shaders/effect_dof_frag.glsl
M	source/blender/draw/engines/eevee/shaders/effect_dof_vert.glsl

===================================================================

diff --git a/source/blender/draw/engines/eevee/shaders/effect_dof_frag.glsl b/source/blender/draw/engines/eevee/shaders/effect_dof_frag.glsl
index 4e47df04bd2..d816d72c1e3 100644
--- a/source/blender/draw/engines/eevee/shaders/effect_dof_frag.glsl
+++ b/source/blender/draw/engines/eevee/shaders/effect_dof_frag.glsl
@@ -31,12 +31,11 @@ uniform vec2 nearFar; /* Near & far view depths values */
 		? (nearFar.x  * nearFar.y) / (z * (nearFar.x - nearFar.y) + nearFar.y) \
 		: (z * 2.0 - 1.0) * nearFar.y)
 
-#define weighted_sum(a, b, c, d, e) (a * e.x + b * e.y + c * e.z + d * e.w)
+#define weighted_sum(a, b, c, d, e) (a * e.x + b * e.y + c * e.z + d * e.w) / max(1e-6, dot(e, vec4(1.0)));
 
 float max_v4(vec4 v) { return max(max(v.x, v.y), max(v.z, v.w)); }
 
-#define THRESHOLD 0.0
-#define SIMILAR_COC_THRESHOLD 2.0
+#define THRESHOLD 1.0
 
 #ifdef STEP_DOWNSAMPLE
 
@@ -70,23 +69,17 @@ void main(void)
 	vec4 coc_near = calculate_coc(zdepth);
 	vec4 coc_far = -coc_near;
 
-	/* now we need to write the near-far fields premultiplied by the coc */
-	/* Also reject pixels that have a much lower coc than the max coc pixel. */
-	vec4 near_weights = step(THRESHOLD, coc_near) * step(max_v4(coc_near) - SIMILAR_COC_THRESHOLD, coc_near);
-	vec4 far_weights = step(THRESHOLD, coc_far) * step(max_v4(coc_far) - SIMILAR_COC_THRESHOLD, coc_far);
+	cocData.x = max(max_v4(coc_near), 0.0);
+	cocData.y = max(max_v4(coc_far), 0.0);
+
+	/* now we need to write the near-far fields premultiplied by the coc
+	 * also use bilateral weighting by each coc values to avoid bleeding. */
+	vec4 near_weights = step(THRESHOLD, coc_near) * clamp(1.0 - abs(cocData.x - coc_near), 0.0, 1.0);
+	vec4 far_weights  = step(THRESHOLD, coc_far)  * clamp(1.0 - abs(cocData.y - coc_far),  0.0, 1.0);
 
 	/* now write output to weighted buffers. */
 	nearColor = weighted_sum(color1, color2, color3, color4, near_weights);
 	farColor = weighted_sum(color1, color2, color3, color4, far_weights);
-
-	/* Normalize the color (don't divide by 0.0) */
-	nearColor /= max(1e-6, dot(near_weights, near_weights));
-	farColor /= max(1e-6, dot(far_weights, far_weights));
-
-	float max_near_coc = max(max_v4(coc_near), 0.0);
-	float max_far_coc = max(max_v4(coc_far), 0.0);
-
-	cocData = vec2(max_near_coc, max_far_coc);
 }
 
 #elif defined(STEP_SCATTER)
@@ -199,26 +192,20 @@ void main(void)
 	float coc_far = max(-coc_signed, 0.0);
 	float coc_near = max(coc_signed, 0.0);
 
-	vec2 texelSize = vec2(0.5, 1.0) / vec2(textureSize(scatterBuffer, 0));
-	vec4 srccolor = textureLod(colorBuffer, uv, 0.0);
+	vec4 focus_col = textureLod(colorBuffer, uv, 0.0);
 
+	vec2 texelSize = vec2(0.5, 1.0) / vec2(textureSize(scatterBuffer, 0));
 	vec2 near_uv = uv * vec2(0.5, 1.0);
 	vec2 far_uv = near_uv + vec2(0.5, 0.0);
-	vec4 farcolor = upsample_filter(scatterBuffer, far_uv, texelSize);
-	vec4 nearcolor = upsample_filter(scatterBuffer, near_uv, texelSize);
-
-	float farweight = farcolor.a;
-	float nearweight = nearcolor.a;
-
-	if (farcolor.a > 0.0) farcolor /= farcolor.a;
-	if (nearcolor.a > 0.0) nearcolor /= nearcolor.a;
+	vec4 near_col = upsample_filter(scatterBuffer, near_uv, texelSize);
+	vec4 far_col = upsample_filter(scatterBuffer, far_uv, texelSize);
 
-	float mixfac = smoothstep(1.0, MERGE_THRESHOLD, abs(coc_signed));
+	float far_w = far_col.a;
+	float near_w = near_col.a;
+	float focus_w = 1.0 - smoothstep(1.0, MERGE_THRESHOLD, abs(coc_signed));
+	focus_col *= focus_w; /* Premul */
 
-	float totalweight = nearweight + farweight;
-	farcolor = mix(srccolor, farcolor, mixfac);
-	nearcolor = mix(srccolor, nearcolor, mixfac);
-	fragColor = mix(farcolor, nearcolor, nearweight / max(1e-6, totalweight));
+	fragColor = (far_col + near_col + focus_col) / (near_w + focus_w + far_w);
 }
 
 #endif
diff --git a/source/blender/draw/engines/eevee/shaders/effect_dof_vert.glsl b/source/blender/draw/engines/eevee/shaders/effect_dof_vert.glsl
index 6e43115d799..ec8b474b431 100644
--- a/source/blender/draw/engines/eevee/shaders/effect_dof_vert.glsl
+++ b/source/blender/draw/engines/eevee/shaders/effect_dof_vert.glsl
@@ -47,7 +47,9 @@ void main()
 			color = texelFetch(farBuffer, texelco, 0);
 		}
 		/* find the area the pixel will cover and divide the color by it */
-		color.a = 1.0 / (coc * coc * M_PI);
+		/* HACK: 4.0 out of nowhere (I suppose it's 4 pixels footprint for coc 0?)
+		 * Makes near in focus more closer to 1.0 alpha. */
+		color.a = 4.0 / (coc * coc * M_PI);
 		color.rgb *= color.a;
 
 		/* Compute edge to discard fragment that does not belong to the other layer. */
@@ -92,7 +94,9 @@ void main()
 	gl_Position.xy += (0.5 + vec2(texelco) * 2.0) * texel_size;
 
 	/* Push far plane to left side. */
-	gl_Position.x  += (!is_near) ? 1.0 : 0.0;
+	if (!is_near) {
+		gl_Position.x += 2.0 / 2.0;
+	}
 
 	/* don't do smoothing for small sprites */
 	if (coc > 3.0) {
@@ -101,6 +105,4 @@ void main()
 	else {
 		smoothFac = 1.0;
 	}
-
-	int tex_width = textureSize(cocBuffer, 0).x;
 }



More information about the Bf-blender-cvs mailing list