From edde749850b4b660dec570fdb6367d1d51c3cb28 Mon Sep 17 00:00:00 2001 From: Brecht Van Lommel Date: Tue, 17 Sep 2013 13:22:42 +0000 Subject: [PATCH] Fix #36741: cycles AO pass giving values > 1.0 with transparency. --- intern/cycles/kernel/kernel_accumulate.h | 4 ++-- intern/cycles/kernel/kernel_passes.h | 4 ++-- intern/cycles/kernel/kernel_path.h | 9 ++++++--- intern/cycles/kernel/kernel_shader.h | 10 ++++++++++ 4 files changed, 20 insertions(+), 7 deletions(-) diff --git a/intern/cycles/kernel/kernel_accumulate.h b/intern/cycles/kernel/kernel_accumulate.h index 422de1f3df8..d7531be0d8a 100644 --- a/intern/cycles/kernel/kernel_accumulate.h +++ b/intern/cycles/kernel/kernel_accumulate.h @@ -210,14 +210,14 @@ __device_inline void path_radiance_accum_emission(PathRadiance *L, float3 throug #endif } -__device_inline void path_radiance_accum_ao(PathRadiance *L, float3 throughput, float3 bsdf, float3 ao, int bounce) +__device_inline void path_radiance_accum_ao(PathRadiance *L, float3 throughput, float3 alpha, float3 bsdf, float3 ao, int bounce) { #ifdef __PASSES__ if(L->use_light_pass) { if(bounce == 0) { /* directly visible lighting */ L->direct_diffuse += throughput*bsdf*ao; - L->ao += throughput*ao; + L->ao += alpha*throughput*ao; } else { /* indirectly visible lighting after BSDF bounce */ diff --git a/intern/cycles/kernel/kernel_passes.h b/intern/cycles/kernel/kernel_passes.h index 7b1c6681e0a..5e91b13f90c 100644 --- a/intern/cycles/kernel/kernel_passes.h +++ b/intern/cycles/kernel/kernel_passes.h @@ -108,8 +108,8 @@ __device_inline void kernel_write_data_passes(KernelGlobals *kg, __global float mist = powf(mist, mist_falloff); /* modulate by transparency */ - float3 alpha = throughput*(make_float3(1.0f, 1.0f, 1.0f) - shader_bsdf_transparency(kg, sd)); - L->mist += (1.0f - mist)*average(alpha); + float3 alpha = shader_bsdf_alpha(kg, sd); + L->mist += (1.0f - mist)*average(throughput*alpha); } #endif } diff --git a/intern/cycles/kernel/kernel_path.h b/intern/cycles/kernel/kernel_path.h index b33192a54cd..1afe8480616 100644 --- a/intern/cycles/kernel/kernel_path.h +++ b/intern/cycles/kernel/kernel_path.h @@ -229,6 +229,7 @@ __device void kernel_path_indirect(KernelGlobals *kg, RNG *rng, int sample, Ray float3 ao_bsdf = shader_bsdf_ao(kg, &sd, ao_factor, &ao_N); float3 ao_D; float ao_pdf; + float3 ao_alpha = make_float3(0.0f, 0.0f, 0.0f); sample_cos_hemisphere(ao_N, bsdf_u, bsdf_v, &ao_D, &ao_pdf); @@ -246,7 +247,7 @@ __device void kernel_path_indirect(KernelGlobals *kg, RNG *rng, int sample, Ray light_ray.dD = differential3_zero(); if(!shadow_blocked(kg, &state, &light_ray, &ao_shadow)) - path_radiance_accum_ao(L, throughput, ao_bsdf, ao_shadow, state.bounce); + path_radiance_accum_ao(L, throughput, ao_alpha, ao_bsdf, ao_shadow, state.bounce); } } #endif @@ -624,6 +625,7 @@ __device float4 kernel_path_integrate(KernelGlobals *kg, RNG *rng, int sample, R float3 ao_bsdf = shader_bsdf_ao(kg, &sd, ao_factor, &ao_N); float3 ao_D; float ao_pdf; + float3 ao_alpha = shader_bsdf_alpha(kg, &sd); sample_cos_hemisphere(ao_N, bsdf_u, bsdf_v, &ao_D, &ao_pdf); @@ -641,7 +643,7 @@ __device float4 kernel_path_integrate(KernelGlobals *kg, RNG *rng, int sample, R light_ray.dD = differential3_zero(); if(!shadow_blocked(kg, &state, &light_ray, &ao_shadow)) - path_radiance_accum_ao(&L, throughput, ao_bsdf, ao_shadow, state.bounce); + path_radiance_accum_ao(&L, throughput, ao_alpha, ao_bsdf, ao_shadow, state.bounce); } } #endif @@ -1076,6 +1078,7 @@ __device float4 kernel_branched_path_integrate(KernelGlobals *kg, RNG *rng, int float ao_factor = kernel_data.background.ao_factor; float3 ao_N; float3 ao_bsdf = shader_bsdf_ao(kg, &sd, ao_factor, &ao_N); + float3 ao_alpha = shader_bsdf_alpha(kg, &sd); for(int j = 0; j < num_samples; j++) { float bsdf_u, bsdf_v; @@ -1100,7 +1103,7 @@ __device float4 kernel_branched_path_integrate(KernelGlobals *kg, RNG *rng, int light_ray.dD = differential3_zero(); if(!shadow_blocked(kg, &state, &light_ray, &ao_shadow)) - path_radiance_accum_ao(&L, throughput*num_samples_inv, ao_bsdf, ao_shadow, state.bounce); + path_radiance_accum_ao(&L, throughput*num_samples_inv, ao_alpha, ao_bsdf, ao_shadow, state.bounce); } } } diff --git a/intern/cycles/kernel/kernel_shader.h b/intern/cycles/kernel/kernel_shader.h index bcc4c42c9cc..ee71a0cfcf4 100644 --- a/intern/cycles/kernel/kernel_shader.h +++ b/intern/cycles/kernel/kernel_shader.h @@ -602,6 +602,16 @@ __device float3 shader_bsdf_transparency(KernelGlobals *kg, ShaderData *sd) #endif } +__device float3 shader_bsdf_alpha(KernelGlobals *kg, ShaderData *sd) +{ + float3 alpha = make_float3(1.0f, 1.0f, 1.0f) - shader_bsdf_transparency(kg, sd); + + alpha = max(alpha, make_float3(0.0f, 0.0f, 0.0f)); + alpha = min(alpha, make_float3(1.0f, 1.0f, 1.0f)); + + return alpha; +} + __device float3 shader_bsdf_diffuse(KernelGlobals *kg, ShaderData *sd) { #ifdef __MULTI_CLOSURE__