[Bf-blender-cvs] [cac43e1765a] blender2.8: Eevee: Use "constant folding" for the principle shader
Clément Foucault
noreply at git.blender.org
Wed Aug 8 21:37:59 CEST 2018
Commit: cac43e1765ab128880bd410d3b8387dc7143f740
Author: Clément Foucault
Date: Wed Aug 8 18:34:25 2018 +0200
Branches: blender2.8
https://developer.blender.org/rBcac43e1765ab128880bd410d3b8387dc7143f740
Eevee: Use "constant folding" for the principle shader
This is more like a static optimisation when some parameters are set to 1.0
or 0.0. In theses case we use a more optimized version of the node.
This also revisit the transmission parameter behaviour to make it closer to
cycles.
===================================================================
M source/blender/draw/engines/eevee/eevee_materials.c
M source/blender/draw/engines/eevee/shaders/bsdf_common_lib.glsl
M source/blender/draw/engines/eevee/shaders/lit_surface_frag.glsl
M source/blender/gpu/GPU_material.h
M source/blender/gpu/shaders/gpu_shader_material.glsl
M source/blender/nodes/shader/nodes/node_shader_bsdf_principled.c
M source/blender/nodes/shader/nodes/node_shader_eevee_specular.c
===================================================================
diff --git a/source/blender/draw/engines/eevee/eevee_materials.c b/source/blender/draw/engines/eevee/eevee_materials.c
index 769ac11736d..cd6b5db5b56 100644
--- a/source/blender/draw/engines/eevee/eevee_materials.c
+++ b/source/blender/draw/engines/eevee/eevee_materials.c
@@ -405,7 +405,7 @@ static void add_standard_uniforms(
DRW_shgroup_uniform_int(shgrp, "outputSsrId", ssr_id, 1);
}
- if (use_ssrefraction) {
+ if (use_refract || use_ssrefraction) {
BLI_assert(refract_depth != NULL);
DRW_shgroup_uniform_float(shgrp, "refractionDepth", refract_depth, 1);
DRW_shgroup_uniform_texture_ref(shgrp, "colorBuffer", &vedata->txl->refract_color);
@@ -563,6 +563,8 @@ void EEVEE_materials_init(EEVEE_ViewLayerData *sldata, EEVEE_StorageList *stl, E
datatoc_lit_surface_frag_glsl,
datatoc_lit_surface_frag_glsl,
datatoc_lit_surface_frag_glsl,
+ datatoc_lit_surface_frag_glsl,
+ datatoc_lit_surface_frag_glsl,
datatoc_volumetric_lib_glsl);
e_data.volume_shader_lib = BLI_string_joinN(
diff --git a/source/blender/draw/engines/eevee/shaders/bsdf_common_lib.glsl b/source/blender/draw/engines/eevee/shaders/bsdf_common_lib.glsl
index 8b232bf14a4..286f00783d9 100644
--- a/source/blender/draw/engines/eevee/shaders/bsdf_common_lib.glsl
+++ b/source/blender/draw/engines/eevee/shaders/bsdf_common_lib.glsl
@@ -548,6 +548,14 @@ float F_eta(float eta, float cos_theta)
return result;
}
+/* Fresnel color blend base on fresnel factor */
+vec3 F_color_blend(float eta, float fresnel, vec3 f0_color)
+{
+ float f0 = F_eta(eta, 1.0);
+ float fac = saturate((fresnel - f0) / max(1e-8, 1.0 - f0));
+ return mix(f0_color, vec3(1.0), fac);
+}
+
/* Fresnel */
vec3 F_schlick(vec3 f0, float cos_theta)
{
diff --git a/source/blender/draw/engines/eevee/shaders/lit_surface_frag.glsl b/source/blender/draw/engines/eevee/shaders/lit_surface_frag.glsl
index 22194c22f39..c2e45ebb879 100644
--- a/source/blender/draw/engines/eevee/shaders/lit_surface_frag.glsl
+++ b/source/blender/draw/engines/eevee/shaders/lit_surface_frag.glsl
@@ -54,6 +54,13 @@ uniform int hairThicknessRes = 1;
#define CLOSURE_SUBSURFACE
#endif /* SURFACE_PRINCIPLED */
+#if !defined(SURFACE_CLEARCOAT) && !defined(CLOSURE_NAME)
+ #define SURFACE_CLEARCOAT
+ #define CLOSURE_NAME eevee_closure_clearcoat
+ #define CLOSURE_GLOSSY
+ #define CLOSURE_CLEARCOAT
+#endif /* SURFACE_CLEARCOAT */
+
#if !defined(SURFACE_DIFFUSE) && !defined(CLOSURE_NAME)
#define SURFACE_DIFFUSE
#define CLOSURE_NAME eevee_closure_diffuse
@@ -67,6 +74,14 @@ uniform int hairThicknessRes = 1;
#define CLOSURE_SUBSURFACE
#endif /* SURFACE_SUBSURFACE */
+#if !defined(SURFACE_SKIN) && !defined(CLOSURE_NAME)
+ #define SURFACE_SKIN
+ #define CLOSURE_NAME eevee_closure_skin
+ #define CLOSURE_DIFFUSE
+ #define CLOSURE_SUBSURFACE
+ #define CLOSURE_GLOSSY
+#endif /* SURFACE_SKIN */
+
#if !defined(SURFACE_GLOSSY) && !defined(CLOSURE_NAME)
#define SURFACE_GLOSSY
#define CLOSURE_NAME eevee_closure_glossy
diff --git a/source/blender/gpu/GPU_material.h b/source/blender/gpu/GPU_material.h
index cc1150b6d77..9dcf308a414 100644
--- a/source/blender/gpu/GPU_material.h
+++ b/source/blender/gpu/GPU_material.h
@@ -128,6 +128,7 @@ typedef enum GPUMatFlag {
GPU_MATFLAG_DIFFUSE = (1 << 0),
GPU_MATFLAG_GLOSSY = (1 << 1),
GPU_MATFLAG_REFRACT = (1 << 2),
+ GPU_MATFLAG_SSS = (1 << 3),
} GPUMatFlag;
typedef enum GPUBlendMode {
diff --git a/source/blender/gpu/shaders/gpu_shader_material.glsl b/source/blender/gpu/shaders/gpu_shader_material.glsl
index 808d2f73659..c9564a21d15 100644
--- a/source/blender/gpu/shaders/gpu_shader_material.glsl
+++ b/source/blender/gpu/shaders/gpu_shader_material.glsl
@@ -1069,11 +1069,11 @@ void convert_metallic_to_specular_tinted(
vec3 basecol, float metallic, float specular_fac, float specular_tint,
out vec3 diffuse, out vec3 f0)
{
- vec3 dielectric = vec3(0.034) * specular_fac * 2.0;
float lum = dot(basecol, vec3(0.3, 0.6, 0.1)); /* luminance approx. */
vec3 tint = lum > 0 ? basecol / lum : vec3(1.0); /* normalize lum. to isolate hue+sat */
- f0 = mix(dielectric * mix(vec3(1.0), tint, specular_tint), basecol, metallic);
- diffuse = mix(basecol, vec3(0.0), metallic);
+ vec3 tmp_col = mix(vec3(1.0), tint, specular_tint);
+ f0 = mix((0.08 * specular_fac) * tmp_col, basecol, metallic);
+ diffuse = basecol * (1.0 - metallic);
}
#ifndef VOLUMETRICS
@@ -1126,52 +1126,142 @@ void node_bsdf_toon(vec4 color, float size, float tsmooth, vec3 N, out Closure r
node_bsdf_diffuse(color, 0.0, N, result);
}
-void node_bsdf_principled_clearcoat(vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
- float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
- float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
- float sss_id, vec3 sss_scale, out Closure result)
+void node_bsdf_principled(
+ vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
+ float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
+ float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
+ float sss_id, vec3 sss_scale, out Closure result)
{
+ ior = max(ior, 1e-5);
metallic = saturate(metallic);
transmission = saturate(transmission);
+ float dielectric = 1.0 - metallic;
+ transmission *= dielectric;
+ subsurface_color *= dielectric;
vec3 diffuse, f0, out_diff, out_spec, out_trans, out_refr, ssr_spec;
convert_metallic_to_specular_tinted(base_color.rgb, metallic, specular, specular_tint, diffuse, f0);
- transmission *= 1.0 - metallic;
- subsurface *= 1.0 - metallic;
-
- clearcoat *= 0.25;
- clearcoat *= 1.0 - transmission;
+ /* Far from being accurate, but 2 glossy evaluation is too expensive.
+ * Most noticeable difference is at grazing angles since the bsdf lut
+ * f0 color interpolation is done on top of this interpolation. */
+ vec3 f0_glass = mix(vec3(1.0), base_color.rgb, specular_tint);
+ float fresnel = F_eta(ior, dot(N, cameraVec));
+ vec3 spec_col = F_color_blend(ior, fresnel, f0_glass) * fresnel;
+ f0 = mix(f0, spec_col, transmission);
vec3 mixed_ss_base_color = mix(diffuse, subsurface_color.rgb, subsurface);
-#ifdef USE_SSS
- diffuse = vec3(0.0);
-#else
- diffuse = mixed_ss_base_color;
-#endif
-
- f0 = mix(f0, vec3(1.0), transmission);
-
float sss_scalef = dot(sss_scale, vec3(1.0 / 3.0)) * subsurface;
eevee_closure_principled(N, mixed_ss_base_color, f0, int(ssr_id), roughness,
- CN, clearcoat, clearcoat_roughness, 1.0, sss_scalef, ior,
+ CN, clearcoat * 0.25, clearcoat_roughness, 1.0, sss_scalef, ior,
out_diff, out_trans, out_spec, out_refr, ssr_spec);
vec3 refr_color = base_color.rgb;
refr_color *= (refractionDepth > 0.0) ? refr_color : vec3(1.0); /* Simulate 2 transmission event */
+ out_refr *= refr_color * (1.0 - fresnel) * transmission;
- float fresnel = F_eta(ior, dot(N, cameraVec));
- vec3 refr_spec_color = base_color.rgb * fresnel;
- /* This bit maybe innacurate. */
- out_refr = out_refr * refr_color * (1.0 - fresnel) + out_spec * refr_spec_color;
+ vec3 vN = normalize(mat3(ViewMatrix) * N);
+ result = CLOSURE_DEFAULT;
+ result.radiance = out_spec + out_refr;
+#ifndef USE_SSS
+ result.radiance += (out_diff + out_trans) * mixed_ss_base_color * (1.0 - transmission);
+#endif
+ result.ssr_data = vec4(ssr_spec, roughness);
+ result.ssr_normal = normal_encode(vN, viewCameraVec);
+ result.ssr_id = int(ssr_id);
+#ifdef USE_SSS
+ result.sss_data.a = sss_scalef;
+ result.sss_data.rgb = out_diff + out_trans;
+# ifdef USE_SSS_ALBEDO
+ result.sss_albedo.rgb = mixed_ss_base_color;
+# else
+ result.sss_data.rgb *= mixed_ss_base_color;
+# endif
+ result.sss_data.rgb *= (1.0 - transmission);
+#endif
+}
+
+void node_bsdf_principled_dielectric(
+ vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
+ float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
+ float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
+ float sss_id, vec3 sss_scale, out Closure result)
+{
+ metallic = saturate(metallic);
+ float dielectric = 1.0 - metallic;
+
+ vec3 diffuse, f0, out_diff, out_spec, ssr_spec;
+ convert_metallic_to_specular_tinted(base_color.rgb, metallic, specular, specular_tint, diffuse, f0);
- ssr_spec = mix(ssr_spec, refr_spec_color, transmission);
+ eevee_closure_default(N, diffuse, f0, int(ssr_id), roughness, 1.0, out_diff, out_spec, ssr_spec);
vec3 vN = normalize(mat3(ViewMatrix) * N);
result = CLOSURE_DEFAULT;
result.radiance = out_spec + out_diff * diffuse;
- result.radiance = mix(result.radiance, out_refr, transmission);
+ result.ssr_data = vec4(ssr_spec, roughness);
+ result.ssr_normal = normal_encode(vN, viewCameraVec);
+ result.ssr_id = int(ssr_id);
+}
+
+void node_bsdf_principled_metallic(
+ vec4 base_color, float subsurface, vec3 subsurface_radius, vec4 subsurface_color, float metallic, float specular,
+ float specular_tint, float roughness, float anisotropic, float anisotropic_rotation, float sheen, float sheen_tint, float clearcoat,
+ float clearcoat_roughness, float ior, float transmission, float transmission_roughness, vec3 N, vec3 CN, vec3 T, vec3 I, float ssr_id,
+ float sss_id, vec3 sss_scale, out Closure result)
+{
+ vec3 out_spec, ssr_spec;
+
+ eevee_closure_glossy(N, base_color.rgb, int(ssr_id), roughness, 1.0, out_spec, ssr_spec);
+
+ vec3 vN = normalize(mat3(ViewMatrix) * N);
+ result = CLOSURE_DEFAULT;
+ result.radiance = out_spec;
+ result.ssr_data = vec4(ssr_spec, roughness);
+
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list