[Bf-blender-cvs] [6f4a0c23ccb] blender-v2.79-release: Cycles: Mark pixels with negative values as outliers

Lukas Stockner noreply at git.blender.org
Mon Sep 4 13:12:17 CEST 2017


Commit: 6f4a0c23ccb2653a8a5ac1bb7cb5d3b240c9182d
Author: Lukas Stockner
Date:   Thu Aug 24 23:15:30 2017 +0200
Branches: blender-v2.79-release
https://developer.blender.org/rB6f4a0c23ccb2653a8a5ac1bb7cb5d3b240c9182d

Cycles: Mark pixels with negative values as outliers

If a pixel has negative components, something already went wrong, so the best option is to just ignore it.

Should be good for 2.79.

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

M	intern/cycles/kernel/filter/filter_prefilter.h

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

diff --git a/intern/cycles/kernel/filter/filter_prefilter.h b/intern/cycles/kernel/filter/filter_prefilter.h
index a0b89c1111f..8912630f766 100644
--- a/intern/cycles/kernel/filter/filter_prefilter.h
+++ b/intern/cycles/kernel/filter/filter_prefilter.h
@@ -120,49 +120,56 @@ ccl_device void kernel_filter_detect_outliers(int x, int y,
 {
 	int buffer_w = align_up(rect.z - rect.x, 4);
 
-	int n = 0;
-	float values[25];
-	for(int y1 = max(y-2, rect.y); y1 < min(y+3, rect.w); y1++) {
-		for(int x1 = max(x-2, rect.x); x1 < min(x+3, rect.z); x1++) {
-			int idx = (y1-rect.y)*buffer_w + (x1-rect.x);
-			float L = average(make_float3(image[idx], image[idx+pass_stride], image[idx+2*pass_stride]));
-
-			/* Find the position of L. */
-			int i;
-			for(i = 0; i < n; i++) {
-				if(values[i] > L) break;
-			}
-			/* Make space for L by shifting all following values to the right. */
-			for(int j = n; j > i; j--) {
-				values[j] = values[j-1];
-			}
-			/* Insert L. */
-			values[i] = L;
-			n++;
-		}
-	}
-
 	int idx = (y-rect.y)*buffer_w + (x-rect.x);
-	float L = average(make_float3(image[idx], image[idx+pass_stride], image[idx+2*pass_stride]));
+	float3 color = make_float3(image[idx], image[idx+pass_stride], image[idx+2*pass_stride]);
 
-	float ref = 2.0f*values[(int)(n*0.75f)];
 	float fac = 1.0f;
-	if(L > ref) {
-		/* The pixel appears to be an outlier.
-		 * However, it may just be a legitimate highlight. Therefore, it is checked how likely it is that the pixel
-		 * should actually be at the reference value:
-		 * If the reference is within the 3-sigma interval, the pixel is assumed to be a statistical outlier.
-		 * Otherwise, it is very unlikely that the pixel should be darker, which indicates a legitimate highlight.
-		 */
-		float stddev = sqrtf(average(make_float3(variance[idx], variance[idx+pass_stride], variance[idx+2*pass_stride])));
-		if(L - 3*stddev < ref) {
-			/* The pixel is an outlier, so negate the depth value to mark it as one.
-			 * Also, scale its brightness down to the outlier threshold to avoid trouble with the NLM weights. */
-			depth[idx] = -depth[idx];
-			fac = ref/L;
-			variance[idx              ] *= fac*fac;
-			variance[idx + pass_stride] *= fac*fac;
-			variance[idx+2*pass_stride] *= fac*fac;
+	if(color.x < 0.0f || color.y < 0.0f || color.z < 0.0f) {
+		depth[idx] = -depth[idx];
+		fac = 0.0f;
+	}
+	else {
+		float L = average(color);
+		int n = 0;
+		float values[25];
+		for(int y1 = max(y-2, rect.y); y1 < min(y+3, rect.w); y1++) {
+			for(int x1 = max(x-2, rect.x); x1 < min(x+3, rect.z); x1++) {
+				int idx = (y1-rect.y)*buffer_w + (x1-rect.x);
+				float L = average(make_float3(image[idx], image[idx+pass_stride], image[idx+2*pass_stride]));
+
+				/* Find the position of L. */
+				int i;
+				for(i = 0; i < n; i++) {
+					if(values[i] > L) break;
+				}
+				/* Make space for L by shifting all following values to the right. */
+				for(int j = n; j > i; j--) {
+					values[j] = values[j-1];
+				}
+				/* Insert L. */
+				values[i] = L;
+				n++;
+			}
+		}
+
+		float ref = 2.0f*values[(int)(n*0.75f)];
+		if(L > ref) {
+			/* The pixel appears to be an outlier.
+			 * However, it may just be a legitimate highlight. Therefore, it is checked how likely it is that the pixel
+			 * should actually be at the reference value:
+			 * If the reference is within the 3-sigma interval, the pixel is assumed to be a statistical outlier.
+			 * Otherwise, it is very unlikely that the pixel should be darker, which indicates a legitimate highlight.
+			 */
+			float stddev = sqrtf(average(make_float3(variance[idx], variance[idx+pass_stride], variance[idx+2*pass_stride])));
+			if(L - 3*stddev < ref) {
+				/* The pixel is an outlier, so negate the depth value to mark it as one.
+				 * Also, scale its brightness down to the outlier threshold to avoid trouble with the NLM weights. */
+				depth[idx] = -depth[idx];
+				fac = ref/L;
+				variance[idx              ] *= fac*fac;
+				variance[idx + pass_stride] *= fac*fac;
+				variance[idx+2*pass_stride] *= fac*fac;
+			}
 		}
 	}
 	out[idx              ] = fac*image[idx];



More information about the Bf-blender-cvs mailing list