diff --git a/source/blender/draw/engines/eevee/shaders/eevee_gbuffer_write_lib.glsl b/source/blender/draw/engines/eevee/shaders/eevee_gbuffer_write_lib.glsl index 38764557316..f542876158e 100644 --- a/source/blender/draw/engines/eevee/shaders/eevee_gbuffer_write_lib.glsl +++ b/source/blender/draw/engines/eevee/shaders/eevee_gbuffer_write_lib.glsl @@ -24,6 +24,21 @@ #include "eevee_gbuffer_lib.glsl" +/* Allows to reduce shader complexity and compilation time. + * Prefer removing the defines to let the loading lib have all cases by default. */ +#ifndef MAT_REFLECTION +# undef GBUFFER_HAS_REFLECTION +#endif +#ifndef MAT_REFRACTION +# undef GBUFFER_HAS_REFRACTION +#endif +#ifndef MAT_SUBSURFACE +# undef GBUFFER_HAS_SUBSURFACE +#endif +#ifndef MAT_TRANSLUCENT +# undef GBUFFER_HAS_TRANSLUCENT +#endif + namespace gbuffer { using ClosurePacking = gbuffer::ClosurePacking; diff --git a/source/blender/draw/engines/eevee/shaders/infos/eevee_common_info.hh b/source/blender/draw/engines/eevee/shaders/infos/eevee_common_info.hh index 26ee433804f..c67e83fd39c 100644 --- a/source/blender/draw/engines/eevee/shaders/infos/eevee_common_info.hh +++ b/source/blender/draw/engines/eevee/shaders/infos/eevee_common_info.hh @@ -164,6 +164,10 @@ GPU_SHADER_CREATE_END() GPU_SHADER_CREATE_INFO(eevee_tests_data) TYPEDEF_SOURCE("eevee_defines.hh") +DEFINE("MAT_REFLECTION") +DEFINE("MAT_REFRACTION") +DEFINE("MAT_SUBSURFACE") +DEFINE("MAT_TRANSLUCENT") GPU_SHADER_CREATE_END() /** \} */ diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl index 76d15591c3f..e96b326b84c 100644 --- a/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl +++ b/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl @@ -114,6 +114,7 @@ void node_bsdf_principled(float4 base_color, weight *= max((1.0f - math_reduce_max(sheen_color)), 0.0f); } +#ifdef MAT_CLEARCOAT /* Second layer: Coat */ if (coat_weight > 0.0f) { float coat_NV = dot(CN, V); @@ -140,6 +141,9 @@ void node_bsdf_principled(float4 base_color, else { coat_tint.rgb = float3(1.0f); } +#else + coat_tint.rgb = float3(1.0f); +#endif /* Emission component. * Attenuated by sheen and coat. @@ -164,6 +168,7 @@ void node_bsdf_principled(float4 base_color, weight *= max((1.0f - metallic), 0.0f); } +#ifdef MAT_REFRACTION /* Transmission component */ if (transmission_weight > 0.0f) { float3 F0 = float3(F0_from_ior(ior)) * reflection_tint; @@ -192,6 +197,7 @@ void node_bsdf_principled(float4 base_color, /* Attenuate lower layers */ weight *= max((1.0f - transmission_weight), 0.0f); } +#endif /* Specular component */ if (true) { @@ -224,6 +230,7 @@ void node_bsdf_principled(float4 base_color, weight *= max((1.0f - math_reduce_max(reflectance)), 0.0f); } +#ifdef MAT_SUBSURFACE /* Subsurface component */ if (subsurface_weight > 0.0f) { ClosureSubsurface sss_data; @@ -241,7 +248,9 @@ void node_bsdf_principled(float4 base_color, /* Attenuate lower layers */ weight *= max((1.0f - subsurface_weight), 0.0f); } +#endif +#ifdef MAT_DIFFUSE /* Diffuse component */ if (true) { ClosureDiffuse diffuse_data; @@ -253,6 +262,7 @@ void node_bsdf_principled(float4 base_color, diffuse_data.weight = 1.0f; closure_eval(diffuse_data); } +#endif result = Closure(0); } diff --git a/source/blender/nodes/shader/nodes/node_shader_bsdf_principled.cc b/source/blender/nodes/shader/nodes/node_shader_bsdf_principled.cc index 0037beec44d..f061ae8ce2e 100644 --- a/source/blender/nodes/shader/nodes/node_shader_bsdf_principled.cc +++ b/source/blender/nodes/shader/nodes/node_shader_bsdf_principled.cc @@ -351,6 +351,22 @@ static int node_shader_gpu_bsdf_principled(GPUMaterial *mat, flag |= GPU_MATFLAG_COAT; } + /* Make constant link for the cases we optimize. This allows the driver to constant fold. + * Note that doing so specialize the final tree topology, and thus the shader becomes less + * reusable. So to be used with care. + * Also note that we do note override existing links. This is because it would leak the current + * nodes otherwise. */ + const float zero = 0.0f; + if (!use_coat && in[SOCK_COAT_WEIGHT_ID].link == nullptr) { + in[SOCK_COAT_WEIGHT_ID].link = GPU_constant(&zero); + } + if (!use_subsurf && in[SOCK_SUBSURFACE_WEIGHT_ID].link == nullptr) { + in[SOCK_SUBSURFACE_WEIGHT_ID].link = GPU_constant(&zero); + } + if (!use_refract && in[SOCK_TRANSMISSION_WEIGHT_ID].link == nullptr) { + in[SOCK_TRANSMISSION_WEIGHT_ID].link = GPU_constant(&zero); + } + float use_multi_scatter = (node->custom1 == SHD_GLOSSY_MULTI_GGX) ? 1.0f : 0.0f; GPU_material_flag_set(mat, flag);