Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorClément Foucault <foucault.clem@gmail.com>2022-04-14 19:47:58 +0300
committerClément Foucault <foucault.clem@gmail.com>2022-04-14 19:47:58 +0300
commit80859a6cb2726a39fb22cb49f06e0355dc9390a7 (patch)
treefd3f8ead5a247a79ea11e4aacc720843bbc5e2c2 /source/blender/gpu/shaders/material
parent66dc4d4efb88ecf2d18bfa08ab9c43b024ebd2fb (diff)
GPU: Make nodetree GLSL Codegen render engine agnostic
This commit removes all EEVEE specific code from the `gpu_shader_material*.glsl` files. It defines a clear interface to evaluate the closure nodes leaving more flexibility to the render engine. Some of the long standing workaround are fixed: - bump mapping support is no longer duplicating a lot of node and is instead compiled into a function call. - bump rewiring to Normal socket is no longer needed as we now use a global `g_data.N` for that. Closure sampling with upstread weight eval is now supported if the engine needs it. This also makes all the material GLSL sources use `GPUSource` for better debugging experience. The `GPUFunction` parsing now happens in `GPUSource` creation. The whole `GPUCodegen` now uses the `ShaderCreateInfo` and is object type agnostic. Is has also been rewritten in C++. This patch changes a view behavior for EEVEE: - Mix shader node factor imput is now clamped. - Tangent Vector displacement behavior is now matching cycles. - The chosen BSDF used for SSR might change. - Hair shading may have very small changes on very large hairs when using hair polygon stripes. - ShaderToRGB node will remove any SSR and SSS form a shader. - SSS radius input now is no longer a scaling factor but defines an average radius. The SSS kernel "shape" (radii) are still defined by the socket default values. Appart from the listed changes no other regressions are expected.
Diffstat (limited to 'source/blender/gpu/shaders/material')
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_ambient_occlusion.glsl18
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_anisotropic.glsl26
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_background.glsl16
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_bump.glsl38
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_camera.glsl8
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_combine_hsv.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_diffuse.glsl31
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_displacement.glsl8
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_eevee_specular.glsl101
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_emission.glsl15
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_fractal_noise.glsl3
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_fresnel.glsl7
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_gamma.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_geometry.glsl53
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_glass.glsl64
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_glossy.glsl39
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_hair.glsl46
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_hair_info.glsl26
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_holdout.glsl14
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_hue_sat_val.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_layer_weight.glsl10
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_light_path.glsl16
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_mapping.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_math.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_math_util.glsl69
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_mix_rgb.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_noise.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_normal_map.glsl14
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_object_info.glsl16
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_output_aov.glsl12
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_output_material.glsl36
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_output_world.glsl18
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_particle_info.glsl23
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_point_info.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl248
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_refraction.glsl37
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_separate_hsv.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_shader_to_rgba.glsl27
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_subsurface_scattering.glsl30
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tangent.glsl6
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_brick.glsl3
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_environment.glsl16
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_musgrave.glsl3
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_noise.glsl4
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_voronoi.glsl3
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_wave.glsl4
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_tex_white_noise.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_texture_coordinates.glsl84
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_toon.glsl20
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_translucent.glsl23
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_transparent.glsl17
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_vector_displacement.glsl32
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_vector_math.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_vector_rotate.glsl2
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_velvet.glsl19
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_volume_absorption.glsl13
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_volume_info.glsl24
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_volume_principled.glsl22
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_volume_scatter.glsl15
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_wireframe.glsl23
-rw-r--r--source/blender/gpu/shaders/material/gpu_shader_material_world_normals.glsl24
62 files changed, 638 insertions, 812 deletions
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_ambient_occlusion.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_ambient_occlusion.glsl
index 12921a31b23..4ba1f6f7368 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_ambient_occlusion.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_ambient_occlusion.glsl
@@ -1,4 +1,4 @@
-#ifndef VOLUMETRICS
+
void node_ambient_occlusion(vec4 color,
float dist,
vec3 normal,
@@ -7,20 +7,6 @@ void node_ambient_occlusion(vec4 color,
out vec4 result_color,
out float result_ao)
{
- vec3 bent_normal;
- vec4 rand = texelfetch_noise_tex(gl_FragCoord.xy);
- OcclusionData data = occlusion_search(viewPosition, maxzBuffer, dist, inverted, sample_count);
-
- vec3 V = cameraVec(worldPosition);
- vec3 N = normalize(normal);
- vec3 Ng = safe_normalize(cross(dFdx(worldPosition), dFdy(worldPosition)));
-
- float unused_error;
- vec3 unused;
- occlusion_eval(data, V, N, Ng, inverted, result_ao, unused_error, unused);
+ result_ao = ambient_occlusion_eval(normal, dist, inverted, sample_count);
result_color = result_ao * color;
}
-#else
-/* Stub ambient occlusion because it is not compatible with volumetrics. */
-# define node_ambient_occlusion(a, b, c, d, e, f) (e = vec4(0); f = 0.0)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_anisotropic.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_anisotropic.glsl
index ec49cc86761..77de9e096a6 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_anisotropic.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_anisotropic.glsl
@@ -1,17 +1,27 @@
-#ifndef VOLUMETRICS
+
void node_bsdf_anisotropic(vec4 color,
float roughness,
float anisotropy,
float rotation,
vec3 N,
vec3 T,
- const float use_multiscatter,
- const float ssr_id,
+ float weight,
+ const float do_multiscatter,
out Closure result)
{
- node_bsdf_glossy(color, roughness, N, use_multiscatter, ssr_id, result);
+ N = safe_normalize(N);
+ vec3 V = cameraVec(g_data.P);
+ float NV = dot(N, V);
+
+ vec2 split_sum = brdf_lut(NV, roughness);
+
+ ClosureReflection reflection_data;
+ reflection_data.weight = weight;
+ reflection_data.color = (do_multiscatter != 0.0) ?
+ F_brdf_multi_scatter(color.rgb, color.rgb, split_sum) :
+ F_brdf_single_scatter(color.rgb, color.rgb, split_sum);
+ reflection_data.N = N;
+ reflection_data.roughness = roughness;
+
+ result = closure_eval(reflection_data);
}
-#else
-/* Stub anisotropic because it is not compatible with volumetrics. */
-# define node_bsdf_anisotropic(a, b, c, d, e, f, g, h, result) (result = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_background.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_background.glsl
index 69ef4dcb7c7..2460bd63b38 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_background.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_background.glsl
@@ -1,11 +1,9 @@
-void node_background(vec4 color, float strength, out Closure result)
+
+void node_background(vec4 color, float strength, float weight, out Closure result)
{
-#ifndef VOLUMETRICS
- color *= strength;
- result = CLOSURE_DEFAULT;
- result.radiance = color.rgb;
- result.transmittance = vec3(0.0);
-#else
- result = CLOSURE_DEFAULT;
-#endif
+ ClosureEmission emission_data;
+ emission_data.weight = weight;
+ emission_data.emission = color.rgb * strength;
+
+ result = closure_eval(emission_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_bump.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_bump.glsl
index 9f73f654217..e0931128485 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_bump.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_bump.glsl
@@ -1,28 +1,19 @@
-void dfdx_v3(vec3 v, out vec3 dy)
-{
- dy = v + DFDX_SIGN * dFdx(v);
-}
-void dfdy_v3(vec3 v, out vec3 dy)
+void differentiate_texco(vec3 v, out vec3 df)
{
- dy = v + DFDY_SIGN * dFdy(v);
+ /* Implementation defined. */
+ df = v + dF_impl(v);
}
-void node_bump(float strength,
- float dist,
- float height,
- float height_dx,
- float height_dy,
- vec3 N,
- vec3 surf_pos,
- float invert,
- out vec3 result)
+void node_bump(
+ float strength, float dist, float height, vec3 N, vec2 dHd, float invert, out vec3 result)
{
- N = mat3(ViewMatrix) * normalize(N);
- dist *= gl_FrontFacing ? invert : -invert;
+ N = normalize(N);
+ dist *= FrontFacing ? invert : -invert;
- vec3 dPdx = dFdx(surf_pos);
- vec3 dPdy = dFdy(surf_pos);
+#ifdef GPU_FRAGMENT_SHADER
+ vec3 dPdx = dFdx(g_data.P);
+ vec3 dPdy = dFdy(g_data.P);
/* Get surface tangents from normal. */
vec3 Rx = cross(dPdy, N);
@@ -31,14 +22,13 @@ void node_bump(float strength,
/* Compute surface gradient and determinant. */
float det = dot(dPdx, Rx);
- float dHdx = height_dx - height;
- float dHdy = height_dy - height;
- vec3 surfgrad = dHdx * Rx + dHdy * Ry;
+ vec3 surfgrad = dHd.x * Rx + dHd.y * Ry;
strength = max(strength, 0.0);
result = normalize(abs(det) * N - dist * sign(det) * surfgrad);
result = normalize(mix(N, result, strength));
-
- result = mat3(ViewMatrixInverse) * result;
+#else
+ result = N;
+#endif
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_camera.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_camera.glsl
index 03e61e9f472..ff84a0a334c 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_camera.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_camera.glsl
@@ -1,6 +1,6 @@
-void camera(vec3 co, out vec3 outview, out float outdepth, out float outdist)
+void camera(out vec3 outview, out float outdepth, out float outdist)
{
- outdepth = abs(co.z);
- outdist = length(co);
- outview = normalize(co);
+ outdepth = abs(transform_point(ViewMatrix, g_data.P).z);
+ outdist = distance(g_data.P, cameraPos);
+ outview = normalize(g_data.P - cameraPos);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_combine_hsv.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_combine_hsv.glsl
index 2ce061da3cb..e8f444080b9 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_combine_hsv.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_combine_hsv.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_color_util.glsl)
+
void combine_hsv(float h, float s, float v, out vec4 col)
{
hsv_to_rgb(vec4(h, s, v, 1.0), col);
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_diffuse.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_diffuse.glsl
index ab6024b073d..bbdd86bd664 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_diffuse.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_diffuse.glsl
@@ -1,28 +1,11 @@
-#ifndef VOLUMETRICS
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_bsdf_diffuse, Diffuse)
-
-void node_bsdf_diffuse(vec4 color, float roughness, vec3 N, out Closure result)
+void node_bsdf_diffuse(vec4 color, float roughness, vec3 N, float weight, out Closure result)
{
- CLOSURE_VARS_DECLARE_1(Diffuse);
-
- in_Diffuse_0.N = N; /* Normalized during eval. */
- in_Diffuse_0.albedo = color.rgb;
-
- CLOSURE_EVAL_FUNCTION_1(node_bsdf_diffuse, Diffuse);
-
- result = CLOSURE_DEFAULT;
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = weight;
+ diffuse_data.color = color.rgb;
+ diffuse_data.N = N;
+ diffuse_data.sss_id = 0u;
- out_Diffuse_0.radiance = render_pass_diffuse_mask(vec3(1.0), out_Diffuse_0.radiance);
- out_Diffuse_0.radiance *= color.rgb;
-
- result.radiance = out_Diffuse_0.radiance;
-
- /* TODO(@fclem): Try to not use this. */
- closure_load_ssr_data(vec3(0.0), 0.0, in_Diffuse_0.N, -1.0, result);
+ result = closure_eval(diffuse_data);
}
-
-#else
-/* Stub diffuse because it is not compatible with volumetrics. */
-# define node_bsdf_diffuse(a, b, c, d) (d = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_displacement.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_displacement.glsl
index 0838b5c8b71..cdcdbe50917 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_displacement.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_displacement.glsl
@@ -1,9 +1,9 @@
-void node_displacement_object(
- float height, float midlevel, float scale, vec3 N, mat4 obmat, out vec3 result)
+void node_displacement_object(float height, float midlevel, float scale, vec3 N, out vec3 result)
{
- N = (vec4(N, 0.0) * obmat).xyz;
+ N = transform_direction(ModelMatrix, N);
result = (height - midlevel) * scale * normalize(N);
- result = (obmat * vec4(result, 0.0)).xyz;
+ /* Apply object scale and orientation. */
+ result = transform_direction(ModelMatrix, result);
}
void node_displacement_world(float height, float midlevel, float scale, vec3 N, out vec3 result)
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_eevee_specular.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_eevee_specular.glsl
index 0941482df45..c81880184e3 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_eevee_specular.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_eevee_specular.glsl
@@ -1,80 +1,69 @@
-#ifndef VOLUMETRICS
-
-CLOSURE_EVAL_FUNCTION_DECLARE_3(node_eevee_specular, Diffuse, Glossy, Glossy)
void node_eevee_specular(vec4 diffuse,
vec4 specular,
float roughness,
vec4 emissive,
float transp,
- vec3 normal,
+ vec3 N,
float clearcoat,
float clearcoat_roughness,
- vec3 clearcoat_normal,
+ vec3 CN,
float occlusion,
- float ssr_id,
+ float weight,
+ const float use_clearcoat,
out Closure result)
{
- CLOSURE_VARS_DECLARE_3(Diffuse, Glossy, Glossy);
-
- in_common.occlusion = occlusion;
-
- in_Diffuse_0.N = normal; /* Normalized during eval. */
- in_Diffuse_0.albedo = diffuse.rgb;
+ N = safe_normalize(N);
+ CN = safe_normalize(CN);
+ vec3 V = cameraVec(g_data.P);
- in_Glossy_1.N = normal; /* Normalized during eval. */
- in_Glossy_1.roughness = roughness;
+ ClosureEmission emission_data;
+ emission_data.weight = weight;
+ emission_data.emission = emissive.rgb;
- in_Glossy_2.N = clearcoat_normal; /* Normalized during eval. */
- in_Glossy_2.roughness = clearcoat_roughness;
+ ClosureTransparency transparency_data;
+ transparency_data.weight = weight;
+ transparency_data.transmittance = vec3(transp);
+ transparency_data.holdout = 0.0;
- CLOSURE_EVAL_FUNCTION_3(node_eevee_specular, Diffuse, Glossy, Glossy);
+ float alpha = (1.0 - transp) * weight;
- result = CLOSURE_DEFAULT;
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = alpha;
+ diffuse_data.color = diffuse.rgb;
+ diffuse_data.N = N;
+ diffuse_data.sss_id = 0u;
- vec3 V = cameraVec(worldPosition);
-
- {
- /* Diffuse. */
- out_Diffuse_0.radiance = render_pass_diffuse_mask(vec3(1), out_Diffuse_0.radiance);
- out_Diffuse_0.radiance *= in_Diffuse_0.albedo;
- result.radiance += out_Diffuse_0.radiance;
- }
- {
- /* Glossy. */
- float NV = dot(in_Glossy_1.N, V);
- vec2 split_sum = brdf_lut(NV, in_Glossy_1.roughness);
+ ClosureReflection reflection_data;
+ reflection_data.weight = alpha;
+ if (true) {
+ float NV = dot(N, V);
+ vec2 split_sum = brdf_lut(NV, roughness);
vec3 brdf = F_brdf_single_scatter(specular.rgb, vec3(1.0), split_sum);
- out_Glossy_1.radiance = closure_mask_ssr_radiance(out_Glossy_1.radiance, ssr_id);
- out_Glossy_1.radiance *= brdf;
- out_Glossy_1.radiance = render_pass_glossy_mask(specular.rgb, out_Glossy_1.radiance);
- closure_load_ssr_data(
- out_Glossy_1.radiance, in_Glossy_1.roughness, in_Glossy_1.N, ssr_id, result);
+ reflection_data.color = specular.rgb * brdf;
+ reflection_data.N = N;
+ reflection_data.roughness = roughness;
}
- {
- /* Clearcoat. */
- float NV = dot(in_Glossy_2.N, V);
- vec2 split_sum = brdf_lut(NV, in_Glossy_2.roughness);
+
+ ClosureReflection clearcoat_data;
+ clearcoat_data.weight = alpha * clearcoat * 0.25;
+ if (true) {
+ float NV = dot(CN, V);
+ vec2 split_sum = brdf_lut(NV, clearcoat_roughness);
vec3 brdf = F_brdf_single_scatter(vec3(0.04), vec3(1.0), split_sum);
- out_Glossy_2.radiance *= brdf * clearcoat * 0.25;
- out_Glossy_2.radiance = render_pass_glossy_mask(vec3(1), out_Glossy_2.radiance);
- result.radiance += out_Glossy_2.radiance;
- }
- {
- /* Emission. */
- vec3 out_emission_radiance = render_pass_emission_mask(emissive.rgb);
- result.radiance += out_emission_radiance;
+ clearcoat_data.color = brdf;
+ clearcoat_data.N = CN;
+ clearcoat_data.roughness = clearcoat_roughness;
}
- float alpha = 1.0 - transp;
- result.transmittance = vec3(transp);
- result.radiance *= alpha;
- result.ssr_data.rgb *= alpha;
+ if (use_clearcoat != 0.0f) {
+ result = closure_eval(diffuse_data, reflection_data, clearcoat_data);
+ }
+ else {
+ result = closure_eval(diffuse_data, reflection_data);
+ }
+ result = closure_add(result, closure_eval(emission_data));
+ result = closure_add(result, closure_eval(transparency_data));
}
-
-#else
-/* Stub specular because it is not compatible with volumetrics. */
-# define node_eevee_specular(a, b, c, d, e, f, g, h, i, j, k, result) (result = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_emission.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_emission.glsl
index f2de7c2da39..32484491abd 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_emission.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_emission.glsl
@@ -1,10 +1,9 @@
-void node_emission(vec4 color, float strength, vec3 vN, out Closure result)
+
+void node_emission(vec4 color, float strength, float weight, out Closure result)
{
- result = CLOSURE_DEFAULT;
-#ifndef VOLUMETRICS
- result.radiance = render_pass_emission_mask(color.rgb) * strength;
- result.ssr_normal = normal_encode(vN, viewCameraVec(viewPosition));
-#else
- result.emission = color.rgb * strength;
-#endif
+ ClosureEmission emission_data;
+ emission_data.weight = weight;
+ emission_data.emission = color.rgb * strength;
+
+ result = closure_eval(emission_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_fractal_noise.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_fractal_noise.glsl
index 95f2be4bd44..7f502f74c0c 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_fractal_noise.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_fractal_noise.glsl
@@ -1,3 +1,6 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_noise.glsl)
+
/* The fractal_noise functions are all exactly the same except for the input type. */
float fractal_noise(float p, float octaves, float roughness)
{
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_fresnel.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_fresnel.glsl
index 7a4d28f2dd6..9fb98d598ab 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_fresnel.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_fresnel.glsl
@@ -26,12 +26,11 @@ float fresnel_dielectric(vec3 Incoming, vec3 Normal, float eta)
return fresnel_dielectric_cos(dot(Incoming, Normal), eta);
}
-void node_fresnel(float ior, vec3 N, vec3 I, out float result)
+void node_fresnel(float ior, vec3 N, out float result)
{
N = normalize(N);
- /* handle perspective/orthographic */
- vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
+ vec3 V = cameraVec(g_data.P);
float eta = max(ior, 0.00001);
- result = fresnel_dielectric(I_view, N, (gl_FrontFacing) ? eta : 1.0 / eta);
+ result = fresnel_dielectric(V, N, (FrontFacing) ? eta : 1.0 / eta);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_gamma.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_gamma.glsl
index 5733992f8dd..29fb09ceebd 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_gamma.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_gamma.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
void node_gamma(vec4 col, float gamma, out vec4 outcol)
{
outcol = col;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_geometry.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_geometry.glsl
index a14ff5021bf..5e86a4577ee 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_geometry.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_geometry.glsl
@@ -1,9 +1,6 @@
-void node_geometry(vec3 I,
- vec3 N,
- vec3 orco,
- mat4 objmat,
- mat4 toworld,
- vec2 barycentric,
+#pragma BLENDER_REQUIRE(gpu_shader_material_tangent.glsl)
+
+void node_geometry(vec3 orco,
out vec3 position,
out vec3 normal,
out vec3 tangent,
@@ -15,39 +12,21 @@ void node_geometry(vec3 I,
out float random_per_island)
{
/* handle perspective/orthographic */
- vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
- incoming = -(toworld * vec4(I_view, 0.0)).xyz;
-
-#if defined(WORLD_BACKGROUND) || defined(PROBE_CAPTURE)
- position = -incoming;
- true_normal = normal = incoming;
- tangent = parametric = vec3(0.0);
- vec3(0.0);
- backfacing = 0.0;
- pointiness = 0.0;
-#else
-
- position = worldPosition;
-# ifndef VOLUMETRICS
- normal = normalize(N);
- vec3 B = dFdx(worldPosition);
- vec3 T = dFdy(worldPosition);
- true_normal = normalize(cross(B, T));
-# else
- normal = (toworld * vec4(N, 0.0)).xyz;
- true_normal = normal;
-# endif
+ incoming = coordinate_incoming(g_data.P);
+ position = g_data.P;
+ normal = g_data.N;
+ true_normal = g_data.Ng;
-# ifdef HAIR_SHADER
- tangent = -hairTangent;
-# else
- tangent_orco_z(orco, orco);
- node_tangent(N, orco, objmat, tangent);
-# endif
+ if (g_data.is_strand) {
+ tangent = g_data.T;
+ }
+ else {
+ tangent_orco_z(orco, orco);
+ node_tangent(orco, tangent);
+ }
- parametric = vec3(barycentric, 0.0);
- backfacing = (gl_FrontFacing) ? 0.0 : 1.0;
+ parametric = vec3(g_data.barycentric_coords, 0.0);
+ backfacing = (FrontFacing) ? 0.0 : 1.0;
pointiness = 0.5;
random_per_island = 0.0;
-#endif
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_glass.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_glass.glsl
index aa0a8873596..36c71c27837 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_glass.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_glass.glsl
@@ -1,57 +1,33 @@
-#ifndef VOLUMETRICS
-
-CLOSURE_EVAL_FUNCTION_DECLARE_2(node_bsdf_glass, Glossy, Refraction)
void node_bsdf_glass(vec4 color,
float roughness,
float ior,
vec3 N,
- const float do_multiscatter,
- const float ssr_id,
+ float weight,
+ float do_multiscatter,
out Closure result)
{
- CLOSURE_VARS_DECLARE_2(Glossy, Refraction);
-
- in_Glossy_0.N = N; /* Normalized during eval. */
- in_Glossy_0.roughness = roughness;
-
- in_Refraction_1.N = N; /* Normalized during eval. */
- in_Refraction_1.roughness = roughness;
- in_Refraction_1.ior = ior;
+ N = safe_normalize(N);
+ vec3 V = cameraVec(g_data.P);
+ float NV = dot(N, V);
- CLOSURE_EVAL_FUNCTION_2(node_bsdf_glass, Glossy, Refraction);
+ vec2 split_sum = btdf_lut(NV, roughness, ior);
- result = CLOSURE_DEFAULT;
+ float fresnel = (do_multiscatter != 0.0) ? split_sum.y : F_eta(ior, NV);
+ float btdf = (do_multiscatter != 0.0) ? 1.0 : split_sum.x;
- float NV = dot(in_Refraction_1.N, cameraVec(worldPosition));
+ ClosureReflection reflection_data;
+ reflection_data.weight = fresnel * weight;
+ reflection_data.color = color.rgb;
+ reflection_data.N = N;
+ reflection_data.roughness = roughness;
- float fresnel = (do_multiscatter != 0.0) ?
- btdf_lut(NV, in_Refraction_1.roughness, in_Refraction_1.ior).y :
- F_eta(in_Refraction_1.ior, NV);
+ ClosureRefraction refraction_data;
+ refraction_data.weight = (1.0 - fresnel) * weight;
+ refraction_data.color = color.rgb * btdf;
+ refraction_data.N = N;
+ refraction_data.roughness = roughness;
+ refraction_data.ior = ior;
- vec2 split_sum = brdf_lut(NV, in_Glossy_0.roughness);
- vec3 brdf = (do_multiscatter != 0.0) ? F_brdf_multi_scatter(vec3(1.0), vec3(1.0), split_sum) :
- F_brdf_single_scatter(vec3(1.0), vec3(1.0), split_sum);
-
- out_Glossy_0.radiance = closure_mask_ssr_radiance(out_Glossy_0.radiance, ssr_id);
- out_Glossy_0.radiance *= brdf;
- out_Glossy_0.radiance = render_pass_glossy_mask(vec3(1.0), out_Glossy_0.radiance);
- out_Glossy_0.radiance *= color.rgb * fresnel;
- closure_load_ssr_data(
- out_Glossy_0.radiance, in_Glossy_0.roughness, in_Glossy_0.N, ssr_id, result);
-
- float btdf = (do_multiscatter != 0.0) ?
- 1.0 :
- btdf_lut(NV, in_Refraction_1.roughness, in_Refraction_1.ior).x;
- out_Refraction_1.radiance *= btdf;
- out_Refraction_1.radiance = render_pass_glossy_mask(vec3(1.0), out_Refraction_1.radiance);
- out_Refraction_1.radiance *= color.rgb * (1.0 - fresnel);
- /* Simulate 2nd absorption event. */
- out_Refraction_1.radiance *= (refractionDepth > 0.0) ? color.rgb : vec3(1.0);
- result.radiance += out_Refraction_1.radiance;
+ result = closure_eval(reflection_data, refraction_data);
}
-
-#else
-/* Stub glass because it is not compatible with volumetrics. */
-# define node_bsdf_glass(a, b, c, d, e, f, result) (result = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_glossy.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_glossy.glsl
index fa83bfb6c7a..2e48ddd1c5e 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_glossy.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_glossy.glsl
@@ -1,33 +1,20 @@
-#ifndef VOLUMETRICS
-
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_bsdf_glossy, Glossy)
void node_bsdf_glossy(
- vec4 color, float roughness, vec3 N, float use_multiscatter, float ssr_id, out Closure result)
+ vec4 color, float roughness, vec3 N, float weight, float do_multiscatter, out Closure result)
{
- bool do_ssr = (ssrToggle && int(ssr_id) == outputSsrId);
-
- CLOSURE_VARS_DECLARE_1(Glossy);
+ N = safe_normalize(N);
+ vec3 V = cameraVec(g_data.P);
+ float NV = dot(N, V);
- in_Glossy_0.N = N; /* Normalized during eval. */
- in_Glossy_0.roughness = roughness;
+ vec2 split_sum = brdf_lut(NV, roughness);
- CLOSURE_EVAL_FUNCTION_1(node_bsdf_glossy, Glossy);
+ ClosureReflection reflection_data;
+ reflection_data.weight = weight;
+ reflection_data.color = (do_multiscatter != 0.0) ?
+ F_brdf_multi_scatter(color.rgb, color.rgb, split_sum) :
+ F_brdf_single_scatter(color.rgb, color.rgb, split_sum);
+ reflection_data.N = N;
+ reflection_data.roughness = roughness;
- result = CLOSURE_DEFAULT;
-
- vec2 split_sum = brdf_lut(dot(in_Glossy_0.N, cameraVec(worldPosition)), in_Glossy_0.roughness);
- vec3 brdf = (use_multiscatter != 0.0) ? F_brdf_multi_scatter(vec3(1.0), vec3(1.0), split_sum) :
- F_brdf_single_scatter(vec3(1.0), vec3(1.0), split_sum);
- out_Glossy_0.radiance = closure_mask_ssr_radiance(out_Glossy_0.radiance, ssr_id);
- out_Glossy_0.radiance *= brdf;
- out_Glossy_0.radiance = render_pass_glossy_mask(vec3(1.0), out_Glossy_0.radiance);
- out_Glossy_0.radiance *= color.rgb;
- closure_load_ssr_data(
- out_Glossy_0.radiance, in_Glossy_0.roughness, in_Glossy_0.N, ssr_id, result);
+ result = closure_eval(reflection_data);
}
-
-#else
-/* Stub glossy because it is not compatible with volumetrics. */
-# define node_bsdf_glossy(a, b, c, d, e, result) (result = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_hair.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_hair.glsl
new file mode 100644
index 00000000000..7bf8795495a
--- /dev/null
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_hair.glsl
@@ -0,0 +1,46 @@
+
+void node_bsdf_hair(vec4 color,
+ float offset,
+ float roughness_u,
+ float roughness_v,
+ vec3 T,
+ float weight,
+ out Closure result)
+{
+ ClosureHair hair_data;
+ hair_data.weight = weight;
+ hair_data.color = color.rgb;
+ hair_data.offset = offset;
+ hair_data.roughness = vec2(roughness_u, roughness_v);
+ hair_data.T = T;
+
+ result = closure_eval(hair_data);
+}
+
+void node_bsdf_hair_principled(vec4 color,
+ float melanin,
+ float melanin_redness,
+ vec4 tint,
+ vec3 absorption_coefficient,
+ float roughness,
+ float radial_roughness,
+ float coat,
+ float ior,
+ float offset,
+ float random_color,
+ float random_roughness,
+ float random,
+ float weight,
+ out Closure result)
+{
+ /* Placeholder closure.
+ * Some computation will have to happen here just like the Principled BSDF. */
+ ClosureHair hair_data;
+ hair_data.weight = weight;
+ hair_data.color = color.rgb;
+ hair_data.offset = offset;
+ hair_data.roughness = vec2(0.0);
+ hair_data.T = g_data.T;
+
+ result = closure_eval(hair_data);
+}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_hair_info.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_hair_info.glsl
index 59f0377869b..2885bf4e082 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_hair_info.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_hair_info.glsl
@@ -1,25 +1,19 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+
void node_hair_info(float hair_length,
out float is_strand,
out float intercept,
- out float length,
+ out float out_length,
out float thickness,
out vec3 tangent,
out float random)
{
- length = hair_length;
-#ifdef HAIR_SHADER
- is_strand = 1.0;
- intercept = hairTime;
- thickness = hairThickness;
- tangent = normalize(worldNormal);
- random = wang_hash_noise(
- uint(hairStrandID)); /* TODO: could be precomputed per strand instead. */
-#else
- is_strand = 0.0;
- intercept = 0.0;
- thickness = 0.0;
- tangent = vec3(1.0);
- random = 0.0;
-#endif
+ is_strand = float(g_data.is_strand);
+ intercept = g_data.hair_time;
+ thickness = g_data.hair_thickness;
+ out_length = hair_length;
+ tangent = g_data.T;
+ /* TODO: could be precomputed per strand instead. */
+ random = wang_hash_noise(uint(g_data.hair_strand_id));
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_holdout.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_holdout.glsl
index 50ce2bf2ab8..d022c1ced59 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_holdout.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_holdout.glsl
@@ -1,8 +1,10 @@
-void node_holdout(out Closure result)
+
+void node_holdout(float weight, out Closure result)
{
- result = CLOSURE_DEFAULT;
-#ifndef VOLUMETRICS
- result.holdout = 1.0;
- result.flag = CLOSURE_HOLDOUT_FLAG;
-#endif
+ ClosureTransparency transparency_data;
+ transparency_data.weight = weight;
+ transparency_data.transmittance = vec3(0.0);
+ transparency_data.holdout = 1.0;
+
+ result = closure_eval(transparency_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_hue_sat_val.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_hue_sat_val.glsl
index 64ac73ecdf3..30b808508e9 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_hue_sat_val.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_hue_sat_val.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_color_util.glsl)
+
void hue_sat(float hue, float sat, float value, float fac, vec4 col, out vec4 outcol)
{
vec4 hsv;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_layer_weight.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_layer_weight.glsl
index 588d295bcc4..2b61343a200 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_layer_weight.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_layer_weight.glsl
@@ -1,15 +1,17 @@
-void node_layer_weight(float blend, vec3 N, vec3 I, out float fresnel, out float facing)
+#pragma BLENDER_REQUIRE(gpu_shader_material_fresnel.glsl)
+
+void node_layer_weight(float blend, vec3 N, out float fresnel, out float facing)
{
N = normalize(N);
/* fresnel */
float eta = max(1.0 - blend, 0.00001);
- vec3 I_view = (ProjectionMatrix[3][3] == 0.0) ? normalize(I) : vec3(0.0, 0.0, -1.0);
+ vec3 V = cameraVec(g_data.P);
- fresnel = fresnel_dielectric(I_view, N, (gl_FrontFacing) ? 1.0 / eta : eta);
+ fresnel = fresnel_dielectric(V, N, (FrontFacing) ? 1.0 / eta : eta);
/* facing */
- facing = abs(dot(I_view, N));
+ facing = abs(dot(V, N));
if (blend != 0.5) {
blend = clamp(blend, 0.0, 0.99999);
blend = (blend < 0.5) ? 2.0 * blend : 0.5 / (1.0 - blend);
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_light_path.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_light_path.glsl
index 50c87e3f105..628a3d5e0e5 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_light_path.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_light_path.glsl
@@ -13,19 +13,19 @@ void node_light_path(out float is_camera_ray,
out float transmission_depth)
{
/* Supported. */
- is_camera_ray = (rayType == EEVEE_RAY_CAMERA) ? 1.0 : 0.0;
- is_shadow_ray = (rayType == EEVEE_RAY_SHADOW) ? 1.0 : 0.0;
- is_diffuse_ray = (rayType == EEVEE_RAY_DIFFUSE) ? 1.0 : 0.0;
- is_glossy_ray = (rayType == EEVEE_RAY_GLOSSY) ? 1.0 : 0.0;
+ is_camera_ray = float(g_data.ray_type == RAY_TYPE_CAMERA);
+ is_shadow_ray = float(g_data.ray_type == RAY_TYPE_SHADOW);
+ is_diffuse_ray = float(g_data.ray_type == RAY_TYPE_DIFFUSE);
+ is_glossy_ray = float(g_data.ray_type == RAY_TYPE_GLOSSY);
/* Kind of supported. */
is_singular_ray = is_glossy_ray;
is_reflection_ray = is_glossy_ray;
is_transmission_ray = is_glossy_ray;
- ray_depth = rayDepth;
- diffuse_depth = (is_diffuse_ray == 1.0) ? rayDepth : 0.0;
- glossy_depth = (is_glossy_ray == 1.0) ? rayDepth : 0.0;
+ ray_depth = g_data.ray_depth;
+ diffuse_depth = (is_diffuse_ray == 1.0) ? g_data.ray_depth : 0.0;
+ glossy_depth = (is_glossy_ray == 1.0) ? g_data.ray_depth : 0.0;
transmission_depth = (is_transmission_ray == 1.0) ? glossy_depth : 0.0;
+ ray_length = g_data.ray_length;
/* Not supported. */
- ray_length = 1.0;
transparent_depth = 0.0;
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl
index 1def3abec26..119ee3c0eaa 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_map_range.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
float smootherstep(float edge0, float edge1, float x)
{
x = clamp(safe_divide((x - edge0), (edge1 - edge0)), 0.0, 1.0);
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_mapping.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_mapping.glsl
index 07f152439fe..312c57231c5 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_mapping.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_mapping.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
void mapping_mat4(
vec3 vec, vec4 m0, vec4 m1, vec4 m2, vec4 m3, vec3 minvec, vec3 maxvec, out vec3 outvec)
{
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_math.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_math.glsl
index f200d666e28..0948ce2c9fa 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_math.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_math.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
void math_add(float a, float b, float c, out float result)
{
result = a + b;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_math_util.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_math_util.glsl
index 2a98d9fadd0..91a8996939a 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_math_util.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_math_util.glsl
@@ -140,17 +140,74 @@ mat3 euler_to_mat3(vec3 euler)
return mat;
}
-void direction_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
+void normal_transform_object_to_world(vec3 vin, out vec3 vout)
{
- vout = (mat * vec4(vin, 0.0)).xyz;
+ vout = normal_object_to_world(vin);
}
-void normal_transform_transposed_m4v3(vec3 vin, mat4 mat, out vec3 vout)
+void normal_transform_world_to_object(vec3 vin, out vec3 vout)
{
- vout = transpose(mat3(mat)) * vin;
+ vout = normal_world_to_object(vin);
}
-void point_transform_m4v3(vec3 vin, mat4 mat, out vec3 vout)
+void direction_transform_object_to_world(vec3 vin, out vec3 vout)
{
- vout = (mat * vec4(vin, 1.0)).xyz;
+ vout = transform_direction(ModelMatrix, vin);
+}
+
+void direction_transform_object_to_view(vec3 vin, out vec3 vout)
+{
+ vout = transform_direction(ModelMatrix, vin);
+ vout = transform_direction(ViewMatrix, vout);
+}
+
+void direction_transform_view_to_world(vec3 vin, out vec3 vout)
+{
+ vout = transform_direction(ViewMatrixInverse, vin);
+}
+
+void direction_transform_view_to_object(vec3 vin, out vec3 vout)
+{
+ vout = transform_direction(ViewMatrixInverse, vin);
+ vout = transform_direction(ModelMatrixInverse, vout);
+}
+
+void direction_transform_world_to_view(vec3 vin, out vec3 vout)
+{
+ vout = transform_direction(ViewMatrix, vin);
+}
+
+void direction_transform_world_to_object(vec3 vin, out vec3 vout)
+{
+ vout = transform_direction(ModelMatrixInverse, vin);
+}
+
+void point_transform_object_to_world(vec3 vin, out vec3 vout)
+{
+ vout = point_object_to_world(vin);
+}
+
+void point_transform_object_to_view(vec3 vin, out vec3 vout)
+{
+ vout = point_object_to_view(vin);
+}
+
+void point_transform_view_to_world(vec3 vin, out vec3 vout)
+{
+ vout = point_view_to_world(vin);
+}
+
+void point_transform_view_to_object(vec3 vin, out vec3 vout)
+{
+ vout = point_view_to_object(vin);
+}
+
+void point_transform_world_to_view(vec3 vin, out vec3 vout)
+{
+ vout = point_world_to_view(vin);
+}
+
+void point_transform_world_to_object(vec3 vin, out vec3 vout)
+{
+ vout = point_world_to_object(vin);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_mix_rgb.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_mix_rgb.glsl
index e089aec1d92..157a6a27c15 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_mix_rgb.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_mix_rgb.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_color_util.glsl)
+
void mix_blend(float fac, vec4 col1, vec4 col2, out vec4 outcol)
{
fac = clamp(fac, 0.0, 1.0);
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_noise.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_noise.glsl
index cc65b1eb57c..c84f34a834c 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_noise.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_noise.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+
/* clang-format off */
#define FLOORFRAC(x, x_int, x_fract) { float x_floor = floor(x); x_int = int(x_floor); x_fract = x - x_floor; }
/* clang-format on */
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_normal_map.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_normal_map.glsl
index 2b4a0204d97..e219e2b9bbe 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_normal_map.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_normal_map.glsl
@@ -1,13 +1,13 @@
-void node_normal_map(vec4 info, vec4 tangent, vec3 normal, vec3 texnormal, out vec3 outnormal)
+void node_normal_map(vec4 tangent, vec3 texnormal, out vec3 outnormal)
{
if (all(equal(tangent, vec4(0.0, 0.0, 0.0, 1.0)))) {
- outnormal = normal;
+ outnormal = g_data.N;
return;
}
- tangent *= (gl_FrontFacing ? 1.0 : -1.0);
- vec3 B = tangent.w * cross(normal, tangent.xyz) * sign(info.w);
+ tangent *= (FrontFacing ? 1.0 : -1.0);
+ vec3 B = tangent.w * cross(g_data.N, tangent.xyz) * sign(ObjectInfo.w);
- outnormal = texnormal.x * tangent.xyz + texnormal.y * B + texnormal.z * normal;
+ outnormal = texnormal.x * tangent.xyz + texnormal.y * B + texnormal.z * g_data.N;
outnormal = normalize(outnormal);
}
@@ -21,7 +21,7 @@ void color_to_blender_normal_new_shading(vec3 color, out vec3 normal)
normal = vec3(2.0, -2.0, -2.0) * color - vec3(1.0);
}
-void node_normal_map_mix(float strength, vec3 newnormal, vec3 oldnormal, out vec3 outnormal)
+void node_normal_map_mix(float strength, vec3 newnormal, out vec3 outnormal)
{
- outnormal = normalize(mix(oldnormal, newnormal, max(strength, 0.0)));
+ outnormal = normalize(mix(g_data.N, newnormal, max(strength, 0.0)));
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_object_info.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_object_info.glsl
index 607cf119b36..2dd2993ceb0 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_object_info.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_object_info.glsl
@@ -1,7 +1,4 @@
-void node_object_info(mat4 obmat,
- vec4 obcolor,
- vec4 info,
- float mat_index,
+void node_object_info(float mat_index,
out vec3 location,
out vec4 color,
out float alpha,
@@ -9,10 +6,11 @@ void node_object_info(mat4 obmat,
out float material_index,
out float random)
{
- location = obmat[3].xyz;
- color = obcolor;
- alpha = obcolor.w;
- object_index = info.x;
+ location = ModelMatrix[3].xyz;
+ color = ObjectColor;
+ alpha = ObjectColor.a;
+ object_index = ObjectInfo.x;
+ /* TODO(fclem): Put that inside the Material UBO. */
material_index = mat_index;
- random = info.z;
+ random = ObjectInfo.z;
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_output_aov.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_output_aov.glsl
index 648994739bf..b166c3e4e9f 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_output_aov.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_output_aov.glsl
@@ -1,13 +1,5 @@
-void node_output_aov(vec4 color, float value, out Closure result)
+void node_output_aov(vec4 color, float value, float hash, out Closure dummy)
{
- result = CLOSURE_DEFAULT;
-#ifndef VOLUMETRICS
- if (render_pass_aov_is_color()) {
- result.radiance = color.rgb;
- }
- else {
- result.radiance = vec3(value);
- }
-#endif
+ output_aov(color, value, floatBitsToUint(hash));
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_output_material.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_output_material.glsl
index 14271f9d107..2c24f50264c 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_output_material.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_output_material.glsl
@@ -1,20 +1,20 @@
-void node_output_material(Closure surface,
- Closure volume,
- vec3 displacement,
- float alpha_threshold,
- float shadow_threshold,
- out Closure result)
+
+void node_output_material_surface(Closure surface, out Closure out_surface)
{
-#ifdef VOLUMETRICS
- result = volume;
-#else
- result = surface;
-# if defined(USE_ALPHA_HASH)
- /* Alpha clip emulation. */
- if ((rayType != EEVEE_RAY_SHADOW) ? (alpha_threshold >= 0.0) : (shadow_threshold >= 0.0)) {
- float alpha = saturate(1.0 - avg(result.transmittance));
- result.transmittance = vec3(step(alpha, max(alpha_threshold, shadow_threshold)));
- }
-# endif
-#endif
+ out_surface = surface;
+}
+
+void node_output_material_volume(Closure volume, out Closure out_volume)
+{
+ out_volume = volume;
+}
+
+void node_output_material_displacement(vec3 displacement, out vec3 out_displacement)
+{
+ out_displacement = displacement;
+}
+
+void node_output_material_thickness(float thickness, out float out_thickness)
+{
+ out_thickness = thickness;
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_output_world.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_output_world.glsl
index 5eb853a4c1a..37c34a4f0d7 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_output_world.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_output_world.glsl
@@ -1,14 +1,10 @@
-uniform float backgroundAlpha;
-void node_output_world(Closure surface, Closure volume, out Closure result)
+void node_output_world_surface(Closure surface, out Closure out_surface)
{
-#ifndef VOLUMETRICS
- float alpha = renderPassEnvironment ? 1.0 : backgroundAlpha;
- result = CLOSURE_DEFAULT;
- result.radiance = surface.radiance * alpha;
- result.transmittance = vec3(0.0);
- result.holdout = (1.0 - alpha);
-#else
- result = volume;
-#endif /* VOLUMETRICS */
+ out_surface = surface;
+}
+
+void node_output_world_volume(Closure volume, out Closure out_volume)
+{
+ out_volume = volume;
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_particle_info.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_particle_info.glsl
index bdd60c20a81..5602345ea4a 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_particle_info.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_particle_info.glsl
@@ -1,8 +1,4 @@
-void particle_info(vec4 sprops,
- vec4 loc,
- vec3 vel,
- vec3 avel,
- out float index,
+void particle_info(out float index,
out float random,
out float age,
out float life_time,
@@ -11,13 +7,14 @@ void particle_info(vec4 sprops,
out vec3 velocity,
out vec3 angular_velocity)
{
- index = sprops.x;
- random = loc.w;
- age = sprops.y;
- life_time = sprops.z;
- size = sprops.w;
+ /* Unsupported for now. */
+ index = 0.0;
+ random = 0.0;
+ age = 0.0;
+ life_time = 0.0;
+ size = 0.0;
- location = loc.xyz;
- velocity = vel;
- angular_velocity = avel;
+ location = vec3(0.0);
+ velocity = vec3(0.0);
+ angular_velocity = vec3(0.0);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_point_info.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_point_info.glsl
index d717ac97b28..1b1fed9502e 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_point_info.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_point_info.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+
void node_point_info(out vec3 position, out float radius, out float random)
{
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 c97fc090fe2..033dc05c57d 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_principled.glsl
@@ -1,4 +1,4 @@
-#ifndef VOLUMETRICS
+
vec3 tint_from_color(vec3 color)
{
float lum = dot(color, vec3(0.3, 0.6, 0.1)); /* luminance approx. */
@@ -13,8 +13,6 @@ float principled_sheen(float NV)
return sheen;
}
-CLOSURE_EVAL_FUNCTION_DECLARE_4(node_bsdf_principled, Diffuse, Glossy, Glossy, Refraction)
-
void node_bsdf_principled(vec4 base_color,
float subsurface,
vec3 subsurface_radius,
@@ -40,169 +38,137 @@ void node_bsdf_principled(vec4 base_color,
vec3 N,
vec3 CN,
vec3 T,
+ float weight,
const float do_diffuse,
const float do_clearcoat,
const float do_refraction,
const float do_multiscatter,
- float ssr_id,
- float sss_id,
- vec3 sss_scale,
+ float do_sss,
out Closure result)
{
/* Match cycles. */
- metallic = saturate(metallic);
- transmission = saturate(transmission);
+ metallic = clamp(metallic, 0.0, 1.0);
+ transmission = clamp(transmission, 0.0, 1.0) * (1.0 - metallic);
float diffuse_weight = (1.0 - transmission) * (1.0 - metallic);
- transmission *= (1.0 - metallic);
float specular_weight = (1.0 - transmission);
- clearcoat = max(clearcoat, 0.0);
+ float clearcoat_weight = max(clearcoat, 0.0) * 0.25;
transmission_roughness = 1.0 - (1.0 - roughness) * (1.0 - transmission_roughness);
specular = max(0.0, specular);
- CLOSURE_VARS_DECLARE_4(Diffuse, Glossy, Glossy, Refraction);
-
- in_Diffuse_0.N = N; /* Normalized during eval. */
- in_Diffuse_0.albedo = mix(base_color.rgb, subsurface_color.rgb, subsurface);
-
- in_Glossy_1.N = N; /* Normalized during eval. */
- in_Glossy_1.roughness = roughness;
-
- in_Glossy_2.N = CN; /* Normalized during eval. */
- in_Glossy_2.roughness = clearcoat_roughness;
-
- in_Refraction_3.N = N; /* Normalized during eval. */
- in_Refraction_3.roughness = do_multiscatter != 0.0 ? roughness : transmission_roughness;
- in_Refraction_3.ior = ior;
+ N = safe_normalize(N);
+ CN = safe_normalize(CN);
+ vec3 V = cameraVec(g_data.P);
+ float NV = dot(N, V);
- CLOSURE_EVAL_FUNCTION_4(node_bsdf_principled, Diffuse, Glossy, Glossy, Refraction);
+ float fresnel = (do_multiscatter != 0.0) ? btdf_lut(NV, roughness, ior).y : F_eta(ior, NV);
+ float glass_reflection_weight = fresnel * transmission;
+ float glass_transmission_weight = (1.0 - fresnel) * transmission;
- result = CLOSURE_DEFAULT;
+ vec3 base_color_tint = tint_from_color(base_color.rgb);
- /* This will tag the whole eval for optimisation. */
- if (do_diffuse == 0.0) {
- out_Diffuse_0.radiance = vec3(0);
- }
- if (do_clearcoat == 0.0) {
- out_Glossy_2.radiance = vec3(0);
- }
- if (do_refraction == 0.0) {
- out_Refraction_3.radiance = vec3(0);
+ vec2 split_sum = brdf_lut(NV, roughness);
+
+ ClosureTransparency transparency_data;
+ transparency_data.weight = weight;
+ transparency_data.transmittance = vec3(1.0 - alpha);
+ transparency_data.holdout = 0.0;
+
+ weight *= alpha;
+
+ ClosureEmission emission_data;
+ emission_data.weight = weight;
+ emission_data.emission = emission.rgb * emission_strength;
+
+ /* Diffuse. */
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = diffuse_weight * weight;
+ diffuse_data.color = mix(base_color.rgb, subsurface_color.rgb, subsurface);
+ /* Sheen Coarse approximation: We reuse the diffuse radiance and just scale it. */
+ vec3 sheen_color = mix(vec3(1.0), base_color_tint, sheen_tint);
+ diffuse_data.color += sheen * sheen_color * principled_sheen(NV);
+ diffuse_data.N = N;
+ diffuse_data.sss_radius = subsurface_radius * subsurface;
+ diffuse_data.sss_id = uint(do_sss);
+
+ /* NOTE(@fclem): We need to blend the reflection color but also need to avoid applying the
+ * weights so we compule the ratio. */
+ float reflection_weight = specular_weight + glass_reflection_weight;
+ float reflection_weight_inv = safe_rcp(reflection_weight);
+ specular_weight *= reflection_weight_inv;
+ glass_reflection_weight *= reflection_weight_inv;
+
+ /* Reflection. */
+ ClosureReflection reflection_data;
+ reflection_data.weight = reflection_weight * weight;
+ reflection_data.N = N;
+ reflection_data.roughness = roughness;
+ if (true) {
+ vec3 dielectric_f0_color = mix(vec3(1.0), base_color_tint, specular_tint);
+ vec3 metallic_f0_color = base_color.rgb;
+ vec3 f0 = mix((0.08 * specular) * dielectric_f0_color, metallic_f0_color, metallic);
+ /* Cycles does this blending using the microfacet fresnel factor. However, our fresnel
+ * is already baked inside the split sum LUT. We approximate by changing the f90 color
+ * directly in a non linear fashion. */
+ vec3 f90 = mix(f0, vec3(1.0), fast_sqrt(specular));
+
+ vec3 reflection_brdf = (do_multiscatter != 0.0) ? F_brdf_multi_scatter(f0, f90, split_sum) :
+ F_brdf_single_scatter(f0, f90, split_sum);
+ reflection_data.color = reflection_brdf * specular_weight;
}
+ if (true) {
+ /* Poor approximation since we baked the LUT using a fixed IOR. */
+ vec3 f0 = mix(vec3(1.0), base_color.rgb, specular_tint);
+ vec3 f90 = vec3(1.0);
- vec3 V = cameraVec(worldPosition);
+ vec3 glass_brdf = (do_multiscatter != 0.0) ? F_brdf_multi_scatter(f0, f90, split_sum) :
+ F_brdf_single_scatter(f0, f90, split_sum);
- /* Glossy_1 will always be evaluated. */
- float NV = dot(in_Glossy_1.N, V);
-
- vec3 base_color_tint = tint_from_color(base_color.rgb);
+ /* Avoid 3 glossy evaluation. Use the same closure for glass reflection. */
+ reflection_data.color += glass_brdf * glass_reflection_weight;
+ }
- float fresnel = (do_multiscatter != 0.0) ?
- btdf_lut(NV, in_Glossy_1.roughness, in_Refraction_3.ior).y :
- F_eta(in_Refraction_3.ior, NV);
-
- {
- /* Glossy reflections.
- * Separate Glass reflections and main specular reflections to match Cycles renderpasses. */
- out_Glossy_1.radiance = closure_mask_ssr_radiance(out_Glossy_1.radiance, ssr_id);
-
- vec2 split_sum = brdf_lut(NV, roughness);
-
- vec3 glossy_radiance_final = vec3(0.0);
- if (transmission > 1e-5) {
- /* Glass Reflection: Reuse radiance from Glossy1. */
- vec3 out_glass_refl_radiance = out_Glossy_1.radiance;
-
- /* Poor approximation since we baked the LUT using a fixed IOR. */
- vec3 f0 = mix(vec3(1.0), base_color.rgb, specular_tint);
- vec3 f90 = vec3(1);
-
- vec3 brdf = (do_multiscatter != 0.0) ? F_brdf_multi_scatter(f0, f90, split_sum) :
- F_brdf_single_scatter(f0, f90, split_sum);
-
- out_glass_refl_radiance *= brdf;
- out_glass_refl_radiance = render_pass_glossy_mask(vec3(1), out_glass_refl_radiance);
- out_glass_refl_radiance *= fresnel * transmission;
- glossy_radiance_final += out_glass_refl_radiance;
- }
- if (specular_weight > 1e-5) {
- vec3 dielectric_f0_color = mix(vec3(1.0), base_color_tint, specular_tint);
- vec3 metallic_f0_color = base_color.rgb;
- vec3 f0 = mix((0.08 * specular) * dielectric_f0_color, metallic_f0_color, metallic);
- /* Cycles does this blending using the microfacet fresnel factor. However, our fresnel
- * is already baked inside the split sum LUT. We approximate using by modifying the
- * changing the f90 color directly in a non linear fashion. */
- vec3 f90 = mix(f0, vec3(1), fast_sqrt(specular));
-
- vec3 brdf = (do_multiscatter != 0.0) ? F_brdf_multi_scatter(f0, f90, split_sum) :
- F_brdf_single_scatter(f0, f90, split_sum);
-
- out_Glossy_1.radiance *= brdf;
- out_Glossy_1.radiance = render_pass_glossy_mask(vec3(1), out_Glossy_1.radiance);
- out_Glossy_1.radiance *= specular_weight;
- glossy_radiance_final += out_Glossy_1.radiance;
- }
-
- closure_load_ssr_data(
- glossy_radiance_final, in_Glossy_1.roughness, in_Glossy_1.N, ssr_id, result);
+ ClosureReflection clearcoat_data;
+ clearcoat_data.weight = clearcoat_weight * weight;
+ clearcoat_data.N = CN;
+ clearcoat_data.roughness = clearcoat_roughness;
+ if (true) {
+ float NV = dot(clearcoat_data.N, V);
+ vec2 split_sum = brdf_lut(NV, clearcoat_data.roughness);
+ vec3 brdf = F_brdf_single_scatter(vec3(0.04), vec3(1.0), split_sum);
+ clearcoat_data.color = brdf;
}
- if (diffuse_weight > 1e-5) {
- /* Mask over all diffuse radiance. */
- out_Diffuse_0.radiance *= diffuse_weight;
+ /* Refraction. */
+ ClosureRefraction refraction_data;
+ refraction_data.weight = glass_transmission_weight * weight;
+ float btdf = (do_multiscatter != 0.0) ? 1.0 : btdf_lut(NV, roughness, ior).x;
- /* Sheen Coarse approximation: We reuse the diffuse radiance and just scale it. */
- vec3 sheen_color = mix(vec3(1), base_color_tint, sheen_tint);
- vec3 out_sheen_radiance = out_Diffuse_0.radiance * principled_sheen(NV);
- out_sheen_radiance = render_pass_diffuse_mask(vec3(1), out_sheen_radiance);
- out_sheen_radiance *= sheen * sheen_color;
- result.radiance += out_sheen_radiance;
+ refraction_data.color = base_color.rgb * btdf;
+ refraction_data.N = N;
+ refraction_data.roughness = do_multiscatter != 0.0 ? roughness :
+ max(roughness, transmission_roughness);
+ refraction_data.ior = ior;
- /* Diffuse / Subsurface. */
- float scale = avg(sss_scale) * subsurface;
- closure_load_sss_data(scale, out_Diffuse_0.radiance, in_Diffuse_0.albedo, int(sss_id), result);
+ if (do_diffuse == 0.0 && do_refraction == 0.0 && do_clearcoat != 0.0) {
+ /* Metallic & Clearcoat case. */
+ result = closure_eval(reflection_data, clearcoat_data);
}
-
- if (transmission > 1e-5) {
- float btdf = (do_multiscatter != 0.0) ?
- 1.0 :
- btdf_lut(NV, in_Refraction_3.roughness, in_Refraction_3.ior).x;
- /* TODO(@fclem): This could be going to a transmission render pass instead. */
- out_Refraction_3.radiance *= btdf;
- out_Refraction_3.radiance = render_pass_glossy_mask(vec3(1), out_Refraction_3.radiance);
- out_Refraction_3.radiance *= base_color.rgb;
- /* Simulate 2nd transmission event. */
- out_Refraction_3.radiance *= (refractionDepth > 0.0) ? base_color.rgb : vec3(1);
- out_Refraction_3.radiance *= (1.0 - fresnel) * transmission;
- result.radiance += out_Refraction_3.radiance;
+ else if (do_diffuse == 0.0 && do_refraction == 0.0 && do_clearcoat == 0.0) {
+ /* Metallic case. */
+ result = closure_eval(reflection_data);
}
-
- if (clearcoat > 1e-5) {
- float NV = dot(in_Glossy_2.N, V);
- vec2 split_sum = brdf_lut(NV, in_Glossy_2.roughness);
- vec3 brdf = F_brdf_single_scatter(vec3(0.04), vec3(1.0), split_sum);
-
- out_Glossy_2.radiance *= brdf * clearcoat * 0.25;
- out_Glossy_2.radiance = render_pass_glossy_mask(vec3(1), out_Glossy_2.radiance);
- result.radiance += out_Glossy_2.radiance;
+ else if (do_diffuse != 0.0 && do_refraction == 0.0 && do_clearcoat == 0.0) {
+ /* Dielectric case. */
+ result = closure_eval(diffuse_data, reflection_data);
}
-
- {
- vec3 out_emission_radiance = render_pass_emission_mask(emission.rgb);
- out_emission_radiance *= emission_strength;
- result.radiance += out_emission_radiance;
+ else if (do_diffuse == 0.0 && do_refraction != 0.0 && do_clearcoat == 0.0) {
+ /* Glass case. */
+ result = closure_eval(reflection_data, refraction_data);
}
-
- result.transmittance = vec3(1.0 - alpha);
- result.radiance *= alpha;
- result.ssr_data.rgb *= alpha;
-# ifdef USE_SSS
- result.sss_albedo *= alpha;
-# endif
+ else {
+ /* Un-optimized case. */
+ result = closure_eval(diffuse_data, reflection_data, clearcoat_data, refraction_data);
+ }
+ result = closure_add(result, closure_eval(emission_data));
+ result = closure_add(result, closure_eval(transparency_data));
}
-
-#else
-/* clang-format off */
-/* Stub principled because it is not compatible with volumetrics. */
-# define node_bsdf_principled(a, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, y, z, aa, bb, cc, dd, ee, ff, result) (result = CLOSURE_DEFAULT)
-/* clang-format on */
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_refraction.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_refraction.glsl
index 8a42a131f43..871fa00b3d4 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_refraction.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_refraction.glsl
@@ -1,32 +1,15 @@
-#ifndef VOLUMETRICS
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_bsdf_refraction, Refraction)
-
-void node_bsdf_refraction(vec4 color, float roughness, float ior, vec3 N, out Closure result)
+void node_bsdf_refraction(
+ vec4 color, float roughness, float ior, vec3 N, float weight, out Closure result)
{
- CLOSURE_VARS_DECLARE_1(Refraction);
-
- in_Refraction_0.N = N; /* Normalized during eval. */
- in_Refraction_0.roughness = roughness;
- in_Refraction_0.ior = ior;
-
- CLOSURE_EVAL_FUNCTION_1(node_bsdf_refraction, Refraction);
+ N = safe_normalize(N);
- result = CLOSURE_DEFAULT;
+ ClosureRefraction refraction_data;
+ refraction_data.weight = weight;
+ refraction_data.color = color.rgb;
+ refraction_data.N = N;
+ refraction_data.roughness = roughness;
+ refraction_data.ior = ior;
- out_Refraction_0.radiance = render_pass_glossy_mask(vec3(1.0), out_Refraction_0.radiance);
- out_Refraction_0.radiance *= color.rgb;
- /* Simulate 2nd absorption event. */
- out_Refraction_0.radiance *= (refractionDepth > 0.0) ? color.rgb : vec3(1.0);
-
- result.radiance = out_Refraction_0.radiance;
-
- /* TODO(@fclem): Try to not use this. */
- result.ssr_normal = normal_encode(mat3(ViewMatrix) * in_Refraction_0.N,
- viewCameraVec(viewPosition));
+ result = closure_eval(refraction_data);
}
-
-#else
-/* Stub refraction because it is not compatible with volumetrics. */
-# define node_bsdf_refraction(a, b, c, d, e) (e = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_separate_hsv.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_separate_hsv.glsl
index fb64e424c6c..180e0fd1940 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_separate_hsv.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_separate_hsv.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_color_util.glsl)
+
void separate_hsv(vec4 col, out float h, out float s, out float v)
{
vec4 hsv;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_shader_to_rgba.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_shader_to_rgba.glsl
index f0f2f79c60e..d791f067821 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_shader_to_rgba.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_shader_to_rgba.glsl
@@ -1,29 +1,6 @@
-#ifndef VOLUMETRICS
-
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_shader_to_rgba, Glossy)
void node_shader_to_rgba(Closure cl, out vec4 outcol, out float outalpha)
{
- vec4 spec_accum = vec4(0.0);
- if (ssrToggle && FLAG_TEST(cl.flag, CLOSURE_SSR_FLAG)) {
- CLOSURE_VARS_DECLARE_1(Glossy);
-
- vec3 vN = normal_decode(cl.ssr_normal, viewCameraVec(viewPosition));
- vec3 N = transform_direction(ViewMatrixInverse, vN);
-
- in_Glossy_0.N = N; /* Normalized during eval. */
- in_Glossy_0.roughness = cl.ssr_data.a;
-
- CLOSURE_EVAL_FUNCTION_1(node_shader_to_rgba, Glossy);
-
- spec_accum.rgb = out_Glossy_0.radiance;
- }
-
- outalpha = saturate(1.0 - avg(cl.transmittance));
- outcol = vec4((spec_accum.rgb * cl.ssr_data.rgb) + cl.radiance, 1.0);
-
-# ifdef USE_SSS
- outcol.rgb += cl.sss_irradiance.rgb * cl.sss_albedo;
-# endif
+ outcol = closure_to_rgba(cl);
+ outalpha = outcol.a;
}
-#endif /* VOLUMETRICS */
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_subsurface_scattering.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_subsurface_scattering.glsl
index 20b634aa801..c560dd01c4f 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_subsurface_scattering.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_subsurface_scattering.glsl
@@ -1,6 +1,3 @@
-#ifndef VOLUMETRICS
-
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_subsurface_scattering, Diffuse)
void node_subsurface_scattering(vec4 color,
float scale,
@@ -8,25 +5,18 @@ void node_subsurface_scattering(vec4 color,
float ior,
float anisotropy,
vec3 N,
- float sss_id,
+ float weight,
+ float do_sss,
out Closure result)
{
- CLOSURE_VARS_DECLARE_1(Diffuse);
-
- in_Diffuse_0.N = N; /* Normalized during eval. */
- in_Diffuse_0.albedo = color.rgb;
-
- CLOSURE_EVAL_FUNCTION_1(node_subsurface_scattering, Diffuse);
+ N = safe_normalize(N);
- result = CLOSURE_DEFAULT;
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = weight;
+ diffuse_data.color = color.rgb;
+ diffuse_data.N = N;
+ diffuse_data.sss_radius = radius * scale;
+ diffuse_data.sss_id = uint(do_sss);
- closure_load_sss_data(scale, out_Diffuse_0.radiance, color.rgb, int(sss_id), result);
-
- /* TODO(@fclem): Try to not use this. */
- closure_load_ssr_data(vec3(0.0), 0.0, in_Diffuse_0.N, -1.0, result);
+ result = closure_eval(diffuse_data);
}
-
-#else
-/* Stub subsurface scattering because it is not compatible with volumetrics. */
-# define node_subsurface_scattering(a, b, c, d, e, f, g, h) (h = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tangent.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tangent.glsl
index ff2dbc7ead3..4e4bf759ec9 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tangent.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tangent.glsl
@@ -18,8 +18,8 @@ void node_tangentmap(vec4 attr_tangent, out vec3 tangent)
tangent = normalize(attr_tangent.xyz);
}
-void node_tangent(vec3 N, vec3 orco, mat4 objmat, out vec3 T)
+void node_tangent(vec3 orco, out vec3 T)
{
- T = (objmat * vec4(orco, 0.0)).xyz;
- T = cross(N, normalize(cross(T, N)));
+ T = transform_direction(ModelMatrix, orco);
+ T = cross(g_data.N, normalize(cross(T, g_data.N)));
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_brick.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_brick.glsl
index e252e5ba726..edc2fa32177 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_brick.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_brick.glsl
@@ -1,3 +1,6 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+
vec2 calc_brick_texture(vec3 p,
float mortar_size,
float mortar_smooth,
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_environment.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_environment.glsl
index 434e07e7b86..89091316823 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_environment.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_environment.glsl
@@ -1,19 +1,5 @@
-void node_tex_environment_texco(vec3 viewvec, out vec3 worldvec)
-{
-#ifdef MESH_SHADER
- worldvec = worldPosition;
-#else
- vec4 v = (ProjectionMatrix[3][3] == 0.0) ? vec4(viewvec, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
- vec4 co_homogeneous = (ProjectionMatrixInverse * v);
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
- vec3 co = co_homogeneous.xyz / co_homogeneous.w;
-# if defined(WORLD_BACKGROUND) || defined(PROBE_CAPTURE)
- worldvec = mat3(ViewMatrixInverse) * co;
-# else
- worldvec = mat3(ModelMatrixInverse) * (mat3(ViewMatrixInverse) * co);
-# endif
-#endif
-}
void node_tex_environment_equirectangular(vec3 co, out vec3 uv)
{
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_musgrave.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_musgrave.glsl
index 586385b7e86..1552a2facc3 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_musgrave.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_musgrave.glsl
@@ -1,3 +1,6 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_noise.glsl)
+
/* 1D Musgrave fBm
*
* H: fractal increment parameter
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_noise.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_noise.glsl
index 5745f11ede4..c90b2211dcf 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_noise.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_noise.glsl
@@ -1,3 +1,7 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_noise.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_fractal_noise.glsl)
+
/* The following offset functions generate random offsets to be added to texture
* coordinates to act as a seed since the noise functions don't have seed values.
* A seed value is needed for generating distortion textures and color outputs.
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_voronoi.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_voronoi.glsl
index c8219848e29..dd12b602edf 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_voronoi.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_voronoi.glsl
@@ -1,3 +1,6 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
/*
* Original code is under the MIT License, Copyright (c) 2013 Inigo Quilez.
*
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_wave.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_wave.glsl
index 070f42a5e30..eed98232d0b 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_wave.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_wave.glsl
@@ -1,3 +1,7 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_noise.glsl)
+#pragma BLENDER_REQUIRE(gpu_shader_material_fractal_noise.glsl)
+
float calc_wave(vec3 p,
float distortion,
float detail,
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_tex_white_noise.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_tex_white_noise.glsl
index b11d13a0413..030b58f0736 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_tex_white_noise.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_tex_white_noise.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_hash.glsl)
+
/* White Noise */
void node_white_noise_1d(vec3 vector, float w, out float value, out vec4 color)
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_texture_coordinates.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_texture_coordinates.glsl
index a8ef9687b0a..a3666164cf7 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_texture_coordinates.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_texture_coordinates.glsl
@@ -1,38 +1,5 @@
-vec3 mtex_2d_mapping(vec3 vec)
-{
- return vec3(vec.xy * 0.5 + vec2(0.5), vec.z);
-}
-
-void generated_from_orco(vec3 orco, out vec3 generated)
-{
-#ifdef VOLUMETRICS
-# ifdef MESH_SHADER
- generated = volumeObjectLocalCoord;
-# else
- generated = worldPosition;
-# endif
-#else
- generated = orco;
-#endif
-}
-void generated_texco(vec3 I, vec3 attr_orco, out vec3 generated)
-{
- vec4 v = (ProjectionMatrix[3][3] == 0.0) ? vec4(I, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
- vec4 co_homogeneous = (ProjectionMatrixInverse * v);
- vec4 co = vec4(co_homogeneous.xyz / co_homogeneous.w, 0.0);
- co.xyz = normalize(co.xyz);
-#if defined(WORLD_BACKGROUND) || defined(PROBE_CAPTURE)
- generated = (ViewMatrixInverse * co).xyz;
-#else
- generated_from_orco(attr_orco, generated);
-#endif
-}
-
-void node_tex_coord(vec3 I,
- vec3 wN,
- mat4 obmatinv,
- vec4 camerafac,
+void node_tex_coord(mat4 obmatinv,
vec3 attr_orco,
vec3 attr_uv,
out vec3 generated,
@@ -44,49 +11,10 @@ void node_tex_coord(vec3 I,
out vec3 reflection)
{
generated = attr_orco;
- normal = normalize(normal_world_to_object(wN));
+ normal = normal_world_to_object(g_data.N);
uv = attr_uv;
- object = (obmatinv * (ViewMatrixInverse * vec4(I, 1.0))).xyz;
- camera = vec3(I.xy, -I.z);
- vec4 projvec = ProjectionMatrix * vec4(I, 1.0);
- window = vec3(mtex_2d_mapping(projvec.xyz / projvec.w).xy * camerafac.xy + camerafac.zw, 0.0);
- reflection = -reflect(cameraVec(worldPosition), normalize(wN));
-}
-
-void node_tex_coord_background(vec3 I,
- vec3 N,
- mat4 obmatinv,
- vec4 camerafac,
- vec3 attr_orco,
- vec3 attr_uv,
- out vec3 generated,
- out vec3 normal,
- out vec3 uv,
- out vec3 object,
- out vec3 camera,
- out vec3 window,
- out vec3 reflection)
-{
- vec4 v = (ProjectionMatrix[3][3] == 0.0) ? vec4(I, 1.0) : vec4(0.0, 0.0, 1.0, 1.0);
- vec4 co_homogeneous = (ProjectionMatrixInverse * v);
-
- vec4 co = vec4(co_homogeneous.xyz / co_homogeneous.w, 0.0);
-
- co = normalize(co);
-
- vec3 coords = (ViewMatrixInverse * co).xyz;
-
- generated = coords;
- normal = -coords;
- uv = vec3(attr_uv.xy, 0.0);
- object = (obmatinv * vec4(coords, 1.0)).xyz;
-
- camera = vec3(co.xy, -co.z);
- window = vec3(mtex_2d_mapping(I).xy * camerafac.xy + camerafac.zw, 0.0);
-
- reflection = -coords;
+ object = transform_point((obmatinv[3][3] == 0.0) ? ModelMatrixInverse : obmatinv, g_data.P);
+ camera = coordinate_camera(g_data.P);
+ window = coordinate_screen(g_data.P);
+ reflection = coordinate_reflect(g_data.P, g_data.N);
}
-
-#if defined(WORLD_BACKGROUND) || (defined(PROBE_CAPTURE) && !defined(MESH_SHADER))
-# define node_tex_coord node_tex_coord_background
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_toon.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_toon.glsl
index bbfc99ccc73..ae7d4fc5631 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_toon.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_toon.glsl
@@ -1,9 +1,15 @@
-#ifndef VOLUMETRICS
-void node_bsdf_toon(vec4 color, float size, float tsmooth, vec3 N, out Closure result)
+
+void node_bsdf_toon(
+ vec4 color, float size, float tsmooth, vec3 N, float weight, out Closure result)
{
- node_bsdf_diffuse(color, 0.0, N, result);
+ N = safe_normalize(N);
+
+ /* Fallback to diffuse. */
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = weight;
+ diffuse_data.color = color.rgb;
+ diffuse_data.N = N;
+ diffuse_data.sss_id = 0u;
+
+ result = closure_eval(diffuse_data);
}
-#else
-/* Stub toon because it is not compatible with volumetrics. */
-# define node_bsdf_toon(a, b, c, d, e) (e = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_translucent.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_translucent.glsl
index 80bd3941b22..0cc162f42f5 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_translucent.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_translucent.glsl
@@ -1,21 +1,12 @@
-#ifndef VOLUMETRICS
-CLOSURE_EVAL_FUNCTION_DECLARE_1(node_bsdf_translucent, Translucent)
-
-void node_bsdf_translucent(vec4 color, vec3 N, out Closure result)
+void node_bsdf_translucent(vec4 color, vec3 N, float weight, out Closure result)
{
- CLOSURE_VARS_DECLARE_1(Translucent);
-
- in_Translucent_0.N = -N; /* Normalized during eval. */
+ N = safe_normalize(N);
- CLOSURE_EVAL_FUNCTION_1(node_bsdf_translucent, Translucent);
+ ClosureTranslucent translucent_data;
+ translucent_data.weight = weight;
+ translucent_data.color = color.rgb;
+ translucent_data.N = -N;
- result = CLOSURE_DEFAULT;
- closure_load_ssr_data(vec3(0.0), 0.0, -in_Translucent_0.N, -1.0, result);
- result.radiance = render_pass_diffuse_mask(color.rgb, out_Translucent_0.radiance * color.rgb);
+ result = closure_eval(translucent_data);
}
-
-#else
-/* Stub translucent because it is not compatible with volumetrics. */
-# define node_bsdf_translucent(a, b, c) (c = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_transparent.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_transparent.glsl
index 9040f62bd3f..c650f10b6e4 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_transparent.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_transparent.glsl
@@ -1,11 +1,10 @@
-#ifndef VOLUMETRICS
-void node_bsdf_transparent(vec4 color, out Closure result)
+
+void node_bsdf_transparent(vec4 color, float weight, out Closure result)
{
- result = CLOSURE_DEFAULT;
- result.radiance = vec3(0.0);
- result.transmittance = abs(color.rgb);
+ ClosureTransparency transparency_data;
+ transparency_data.weight = weight;
+ transparency_data.transmittance = color.rgb;
+ transparency_data.holdout = 0.0;
+
+ result = closure_eval(transparency_data);
}
-#else
-/* Stub transparent because it is not compatible with volumetrics. */
-# define node_bsdf_transparent(a, b) (b = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_vector_displacement.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_vector_displacement.glsl
index 4b5ed172081..0ff074bc04f 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_vector_displacement.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_vector_displacement.glsl
@@ -1,30 +1,22 @@
-void node_vector_displacement_tangent(vec4 vector,
- float midlevel,
- float scale,
- vec4 tangent,
- vec3 normal,
- mat4 obmat,
- mat4 viewmat,
- out vec3 result)
+void node_vector_displacement_tangent(
+ vec4 vector, float midlevel, float scale, vec4 T, out vec3 result)
{
- /* TODO(fclem): this is broken. revisit latter. */
- vec3 N_object = normalize(((vec4(normal, 0.0) * viewmat) * obmat).xyz);
- vec3 T_object = normalize(((vec4(tangent.xyz, 0.0) * viewmat) * obmat).xyz);
- vec3 B_object = tangent.w * normalize(cross(N_object, T_object));
+ vec3 oN = normalize(normal_world_to_object(g_data.N));
+ vec3 oT = normalize(normal_world_to_object(T.xyz));
+ vec3 oB = T.w * normalize(cross(oN, oT));
- vec3 offset = (vector.xyz - vec3(midlevel)) * scale;
- result = offset.x * T_object + offset.y * N_object + offset.z * B_object;
- result = (obmat * vec4(result, 0.0)).xyz;
+ result = (vector.xyz - midlevel) * scale;
+ result = result.x * oT + result.y * oN + result.z * oB;
+ result = transform_point(ModelMatrix, result);
}
-void node_vector_displacement_object(
- vec4 vector, float midlevel, float scale, mat4 obmat, out vec3 result)
+void node_vector_displacement_object(vec4 vector, float midlevel, float scale, out vec3 result)
{
- result = (vector.xyz - vec3(midlevel)) * scale;
- result = (obmat * vec4(result, 0.0)).xyz;
+ result = (vector.xyz - midlevel) * scale;
+ result = transform_point(ModelMatrix, result);
}
void node_vector_displacement_world(vec4 vector, float midlevel, float scale, out vec3 result)
{
- result = (vector.xyz - vec3(midlevel)) * scale;
+ result = (vector.xyz - midlevel) * scale;
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_vector_math.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_vector_math.glsl
index 4ad5d4232de..8f6bf17f195 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_vector_math.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_vector_math.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
void vector_math_add(vec3 a, vec3 b, vec3 c, float scale, out vec3 outVector, out float outValue)
{
outVector = a + b;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_vector_rotate.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_vector_rotate.glsl
index 41ad16cce0b..ff0fb1c0418 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_vector_rotate.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_vector_rotate.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_math_util.glsl)
+
vec3 rotate_around_axis(vec3 p, vec3 axis, float angle)
{
float costheta = cos(angle);
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_velvet.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_velvet.glsl
index 989f18b881a..97726bfe66f 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_velvet.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_velvet.glsl
@@ -1,9 +1,14 @@
-#ifndef VOLUMETRICS
-void node_bsdf_velvet(vec4 color, float sigma, vec3 N, out Closure result)
+
+void node_bsdf_velvet(vec4 color, float roughness, vec3 N, float weight, out Closure result)
{
- node_bsdf_diffuse(color, 0.0, N, result);
+ N = safe_normalize(N);
+
+ /* Fallback to diffuse. */
+ ClosureDiffuse diffuse_data;
+ diffuse_data.weight = weight;
+ diffuse_data.color = color.rgb;
+ diffuse_data.N = N;
+ diffuse_data.sss_id = 0u;
+
+ result = closure_eval(diffuse_data);
}
-#else
-/* Stub velvet because it is not compatible with volumetrics. */
-# define node_bsdf_velvet(a, b, c, d) (d = CLOSURE_DEFAULT)
-#endif
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_volume_absorption.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_volume_absorption.glsl
index e6c0880cd07..8fd2e179187 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_volume_absorption.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_volume_absorption.glsl
@@ -1,8 +1,9 @@
-void node_volume_absorption(vec4 color, float density, out Closure result)
+
+void node_volume_absorption(vec4 color, float density, float weight, out Closure result)
{
-#ifdef VOLUMETRICS
- result = Closure((1.0 - color.rgb) * density, vec3(0.0), vec3(0.0), 0.0);
-#else
- result = CLOSURE_DEFAULT;
-#endif
+ ClosureVolumeAbsorption volume_absorption_data;
+ volume_absorption_data.weight = weight;
+ volume_absorption_data.absorption = (1.0 - color.rgb) * density;
+
+ result = closure_eval(volume_absorption_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_volume_info.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_volume_info.glsl
index e6d7b9d3721..464cf5227b4 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_volume_info.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_volume_info.glsl
@@ -4,14 +4,8 @@ uniform vec3 volumeColor = vec3(1.0);
uniform vec2 volumeTemperature = vec2(0.0);
/* Generic volume attribute. */
-void node_attribute_volume(sampler3D tex, mat4 transform, out vec3 outvec)
+void node_attribute_volume(sampler3D tex, mat4 transform, vec3 cos, out vec3 outvec)
{
-#if defined(MESH_SHADER) && defined(VOLUMETRICS)
- vec3 cos = volumeObjectLocalCoord;
-#else
- vec3 cos = vec3(0.0);
-#endif
-
/* Optional per-grid transform. */
if (transform[3][3] != 0.0) {
cos = (transform * vec4(cos, 1.0)).xyz;
@@ -21,14 +15,8 @@ void node_attribute_volume(sampler3D tex, mat4 transform, out vec3 outvec)
}
/* Special color attribute for smoke. */
-void node_attribute_volume_color(sampler3D tex, mat4 transform, out vec3 outvec)
+void node_attribute_volume_color(sampler3D tex, mat4 transform, vec3 cos, out vec3 outvec)
{
-#if defined(MESH_SHADER) && defined(VOLUMETRICS)
- vec3 cos = volumeObjectLocalCoord;
-#else
- vec3 cos = vec3(0.0);
-#endif
-
/* Optional per-grid transform. */
if (transform[3][3] != 0.0) {
cos = (transform * vec4(cos, 1.0)).xyz;
@@ -44,14 +32,8 @@ void node_attribute_volume_color(sampler3D tex, mat4 transform, out vec3 outvec)
}
/* Special temperature attribute for smoke. */
-void node_attribute_volume_temperature(sampler3D tex, mat4 transform, out float outf)
+void node_attribute_volume_temperature(sampler3D tex, mat4 transform, vec3 cos, out float outf)
{
-#if defined(MESH_SHADER) && defined(VOLUMETRICS)
- vec3 cos = volumeObjectLocalCoord;
-#else
- vec3 cos = vec3(0.0);
-#endif
-
/* Optional per-grid transform. */
if (transform[3][3] != 0.0) {
cos = (transform * vec4(cos, 1.0)).xyz;
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_volume_principled.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_volume_principled.glsl
index 884d5415c51..1127c34b3ac 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_volume_principled.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_volume_principled.glsl
@@ -1,3 +1,5 @@
+#pragma BLENDER_REQUIRE(gpu_shader_material_blackbody.glsl)
+
void node_volume_principled(vec4 color,
float density,
float anisotropy,
@@ -7,6 +9,7 @@ void node_volume_principled(vec4 color,
float blackbody_intensity,
vec4 blackbody_tint,
float temperature,
+ float weight,
float density_attribute,
vec4 color_attribute,
float temperature_attribute,
@@ -14,7 +17,6 @@ void node_volume_principled(vec4 color,
float layer,
out Closure result)
{
-#ifdef VOLUMETRICS
vec3 absorption_coeff = vec3(0.0);
vec3 scatter_coeff = vec3(0.0);
vec3 emission_coeff = vec3(0.0);
@@ -60,8 +62,18 @@ void node_volume_principled(vec4 color,
}
}
- result = Closure(absorption_coeff, scatter_coeff, emission_coeff, anisotropy);
-#else
- result = CLOSURE_DEFAULT;
-#endif
+ ClosureVolumeScatter volume_scatter_data;
+ volume_scatter_data.weight = weight;
+ volume_scatter_data.scattering = scatter_coeff;
+ volume_scatter_data.anisotropy = anisotropy;
+
+ ClosureVolumeAbsorption volume_absorption_data;
+ volume_absorption_data.weight = weight;
+ volume_absorption_data.absorption = absorption_coeff;
+
+ ClosureEmission emission_data;
+ emission_data.weight = weight;
+ emission_data.emission = emission_coeff;
+
+ result = closure_eval(volume_scatter_data, volume_absorption_data, emission_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_volume_scatter.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_volume_scatter.glsl
index 02c54658be5..f01ead3618f 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_volume_scatter.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_volume_scatter.glsl
@@ -1,8 +1,11 @@
-void node_volume_scatter(vec4 color, float density, float anisotropy, out Closure result)
+
+void node_volume_scatter(
+ vec4 color, float density, float anisotropy, float weight, out Closure result)
{
-#ifdef VOLUMETRICS
- result = Closure(vec3(0.0), color.rgb * density, vec3(0.0), anisotropy);
-#else
- result = CLOSURE_DEFAULT;
-#endif
+ ClosureVolumeScatter volume_scatter_data;
+ volume_scatter_data.weight = weight;
+ volume_scatter_data.scattering = color.rgb * density;
+ volume_scatter_data.anisotropy = anisotropy;
+
+ result = closure_eval(volume_scatter_data);
}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_wireframe.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_wireframe.glsl
index e2789e046e1..0c02dab3ae4 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_wireframe.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_wireframe.glsl
@@ -1,20 +1,21 @@
-#ifndef VOLUMETRICS
-void node_wireframe(float size, vec2 barycentric, vec3 barycentric_dist, out float fac)
+
+void node_wireframe(float size, out float fac)
{
- vec3 barys = barycentric.xyy;
- barys.z = 1.0 - barycentric.x - barycentric.y;
+ vec3 barys = g_data.barycentric_coords.xyy;
+ barys.z = 1.0 - barys.x - barys.y;
size *= 0.5;
- vec3 s = step(-size, -barys * barycentric_dist);
+ vec3 s = step(-size, -barys * g_data.barycentric_dists);
fac = max(s.x, max(s.y, s.z));
}
-void node_wireframe_screenspace(float size, vec2 barycentric, out float fac)
+void node_wireframe_screenspace(float size, out float fac)
{
- vec3 barys = barycentric.xyy;
- barys.z = 1.0 - barycentric.x - barycentric.y;
+ vec3 barys = g_data.barycentric_coords.xyy;
+ barys.z = 1.0 - barys.x - barys.y;
+#ifdef GPU_FRAGMENT_SHADER
size *= (1.0 / 3.0);
vec3 dx = dFdx(barys);
vec3 dy = dFdy(barys);
@@ -23,9 +24,7 @@ void node_wireframe_screenspace(float size, vec2 barycentric, out float fac)
vec3 s = step(-deltas * size, -barys);
fac = max(s.x, max(s.y, s.z));
-}
#else
-/* Stub wireframe because it is not compatible with volumetrics. */
-# define node_wireframe(a, b, c, d) (d = 0.0)
-# define node_wireframe_screenspace(a, b, c) (c = 0.0)
+ fac = 1.0;
#endif
+}
diff --git a/source/blender/gpu/shaders/material/gpu_shader_material_world_normals.glsl b/source/blender/gpu/shaders/material/gpu_shader_material_world_normals.glsl
index 40e46bc250c..5a0aeb2f932 100644
--- a/source/blender/gpu/shaders/material/gpu_shader_material_world_normals.glsl
+++ b/source/blender/gpu/shaders/material/gpu_shader_material_world_normals.glsl
@@ -1,25 +1,5 @@
-/* TODO: clean this `ifdef` mess. */
+
void world_normals_get(out vec3 N)
{
-#ifndef VOLUMETRICS
-# ifdef HAIR_SHADER
- vec3 B = normalize(cross(worldNormal, hairTangent));
- float cos_theta;
- if (hairThicknessRes == 1) {
- vec4 rand = texelfetch_noise_tex(gl_FragCoord.xy);
- /* Random cosine normal distribution on the hair surface. */
- cos_theta = rand.x * 2.0 - 1.0;
- }
- else {
- /* Shade as a cylinder. */
- cos_theta = hairThickTime / hairThickness;
- }
- float sin_theta = sqrt(max(0.0, 1.0 - cos_theta * cos_theta));
- N = normalize(worldNormal * sin_theta + B * cos_theta);
-# else
- N = gl_FrontFacing ? worldNormal : -worldNormal;
-# endif
-#else
- generated_from_orco(vec3(0.0), N);
-#endif
+ N = g_data.N;
}