diff options
author | Bartosz Moniewski <monio> | 2020-03-26 16:43:53 +0300 |
---|---|---|
committer | Brecht Van Lommel <brecht@blender.org> | 2020-04-09 22:48:03 +0300 |
commit | 054950def946ed7638c2d9c18ef850cbba94d9d7 (patch) | |
tree | 6c38c89f8c04be9259a4246b5b0cd5e842951052 /intern/cycles/kernel/shaders | |
parent | f3433fcd3bf87c9405fb05c96fde036eb658e8aa (diff) |
Shading: add Roughness input to Noise and Wave texture nodes
Currently in fractal_noise functions, each subsequent octave doubles the
frequency and reduces the amplitude by half. This patch introduces Roughness
input to Noise and Wave nodes. This multiplier determines how quickly the
amplitudes of the subsequent octaves decrease.
Value of 0.5 will be the default, generating identical noise we had before.
Values above 0.5 will increase influence of each octave resulting in more
"rough" noise, most interesting pattern changes happen there. Values below
0.5 will result in more "smooth" noise.
Differential Revision: https://developer.blender.org/D7065
Diffstat (limited to 'intern/cycles/kernel/shaders')
-rw-r--r-- | intern/cycles/kernel/shaders/node_noise.h | 52 | ||||
-rw-r--r-- | intern/cycles/kernel/shaders/node_noise_texture.osl | 44 | ||||
-rw-r--r-- | intern/cycles/kernel/shaders/node_wave_texture.osl | 9 |
3 files changed, 58 insertions, 47 deletions
diff --git a/intern/cycles/kernel/shaders/node_noise.h b/intern/cycles/kernel/shaders/node_noise.h index 23d1987a00e..ab4cd7792cc 100644 --- a/intern/cycles/kernel/shaders/node_noise.h +++ b/intern/cycles/kernel/shaders/node_noise.h @@ -84,114 +84,118 @@ float safe_snoise(vector4 p) } /* The fractal_noise functions are all exactly the same except for the input type. */ -float fractal_noise(float p, float details) +float fractal_noise(float p, float details, float roughness) { float fscale = 1.0; float amp = 1.0; + float maxamp = 0.0; float sum = 0.0; float octaves = clamp(details, 0.0, 16.0); int n = (int)octaves; for (int i = 0; i <= n; i++) { float t = safe_noise(fscale * p); sum += t * amp; - amp *= 0.5; + maxamp += amp; + amp *= clamp(roughness, 0.0, 1.0); fscale *= 2.0; } float rmd = octaves - floor(octaves); if (rmd != 0.0) { float t = safe_noise(fscale * p); float sum2 = sum + t * amp; - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - sum2 *= ((float)(1 << (n + 1)) / (float)((1 << (n + 2)) - 1)); + sum /= maxamp; + sum2 /= maxamp + amp; return (1.0 - rmd) * sum + rmd * sum2; } else { - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - return sum; + return sum / maxamp; } } /* The fractal_noise functions are all exactly the same except for the input type. */ -float fractal_noise(vector2 p, float details) +float fractal_noise(vector2 p, float details, float roughness) { float fscale = 1.0; float amp = 1.0; + float maxamp = 0.0; float sum = 0.0; float octaves = clamp(details, 0.0, 16.0); int n = (int)octaves; for (int i = 0; i <= n; i++) { float t = safe_noise(fscale * p); sum += t * amp; - amp *= 0.5; + maxamp += amp; + amp *= clamp(roughness, 0.0, 1.0); fscale *= 2.0; } float rmd = octaves - floor(octaves); if (rmd != 0.0) { float t = safe_noise(fscale * p); float sum2 = sum + t * amp; - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - sum2 *= ((float)(1 << (n + 1)) / (float)((1 << (n + 2)) - 1)); + sum /= maxamp; + sum2 /= maxamp + amp; return (1.0 - rmd) * sum + rmd * sum2; } else { - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - return sum; + return sum / maxamp; } } /* The fractal_noise functions are all exactly the same except for the input type. */ -float fractal_noise(vector3 p, float details) +float fractal_noise(vector3 p, float details, float roughness) { float fscale = 1.0; float amp = 1.0; + float maxamp = 0.0; float sum = 0.0; float octaves = clamp(details, 0.0, 16.0); int n = (int)octaves; for (int i = 0; i <= n; i++) { float t = safe_noise(fscale * p); sum += t * amp; - amp *= 0.5; + maxamp += amp; + amp *= clamp(roughness, 0.0, 1.0); fscale *= 2.0; } float rmd = octaves - floor(octaves); if (rmd != 0.0) { float t = safe_noise(fscale * p); float sum2 = sum + t * amp; - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - sum2 *= ((float)(1 << (n + 1)) / (float)((1 << (n + 2)) - 1)); + sum /= maxamp; + sum2 /= maxamp + amp; return (1.0 - rmd) * sum + rmd * sum2; } else { - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - return sum; + return sum / maxamp; } } /* The fractal_noise functions are all exactly the same except for the input type. */ -float fractal_noise(vector4 p, float details) +float fractal_noise(vector4 p, float details, float roughness) { float fscale = 1.0; float amp = 1.0; + float maxamp = 0.0; float sum = 0.0; float octaves = clamp(details, 0.0, 16.0); int n = (int)octaves; for (int i = 0; i <= n; i++) { float t = safe_noise(fscale * p); sum += t * amp; - amp *= 0.5; + maxamp += amp; + amp *= clamp(roughness, 0.0, 1.0); fscale *= 2.0; } float rmd = octaves - floor(octaves); if (rmd != 0.0) { float t = safe_noise(fscale * p); float sum2 = sum + t * amp; - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - sum2 *= ((float)(1 << (n + 1)) / (float)((1 << (n + 2)) - 1)); + sum /= maxamp; + sum2 /= maxamp + amp; return (1.0 - rmd) * sum + rmd * sum2; } else { - sum *= ((float)(1 << n) / (float)((1 << (n + 1)) - 1)); - return sum; + return sum / maxamp; } } diff --git a/intern/cycles/kernel/shaders/node_noise_texture.osl b/intern/cycles/kernel/shaders/node_noise_texture.osl index 4121b415673..61c0216910b 100644 --- a/intern/cycles/kernel/shaders/node_noise_texture.osl +++ b/intern/cycles/kernel/shaders/node_noise_texture.osl @@ -55,21 +55,22 @@ vector4 random_vector4_offset(float seed) 100.0 + noise("hash", seed, 3.0) * 100.0); } -float noise_texture(float co, float detail, float distortion, output color Color) +float noise_texture(float co, float detail, float roughness, float distortion, output color Color) { float p = co; if (distortion != 0.0) { p += safe_snoise(p + random_float_offset(0.0)) * distortion; } - float value = fractal_noise(p, detail); + float value = fractal_noise(p, detail, roughness); Color = color(value, - fractal_noise(p + random_float_offset(1.0), detail), - fractal_noise(p + random_float_offset(2.0), detail)); + fractal_noise(p + random_float_offset(1.0), detail, roughness), + fractal_noise(p + random_float_offset(2.0), detail, roughness)); return value; } -float noise_texture(vector2 co, float detail, float distortion, output color Color) +float noise_texture( + vector2 co, float detail, float roughness, float distortion, output color Color) { vector2 p = co; if (distortion != 0.0) { @@ -77,14 +78,15 @@ float noise_texture(vector2 co, float detail, float distortion, output color Col safe_snoise(p + random_vector2_offset(1.0)) * distortion); } - float value = fractal_noise(p, detail); + float value = fractal_noise(p, detail, roughness); Color = color(value, - fractal_noise(p + random_vector2_offset(2.0), detail), - fractal_noise(p + random_vector2_offset(3.0), detail)); + fractal_noise(p + random_vector2_offset(2.0), detail, roughness), + fractal_noise(p + random_vector2_offset(3.0), detail, roughness)); return value; } -float noise_texture(vector3 co, float detail, float distortion, output color Color) +float noise_texture( + vector3 co, float detail, float roughness, float distortion, output color Color) { vector3 p = co; if (distortion != 0.0) { @@ -93,14 +95,15 @@ float noise_texture(vector3 co, float detail, float distortion, output color Col safe_snoise(p + random_vector3_offset(2.0)) * distortion); } - float value = fractal_noise(p, detail); + float value = fractal_noise(p, detail, roughness); Color = color(value, - fractal_noise(p + random_vector3_offset(3.0), detail), - fractal_noise(p + random_vector3_offset(4.0), detail)); + fractal_noise(p + random_vector3_offset(3.0), detail, roughness), + fractal_noise(p + random_vector3_offset(4.0), detail, roughness)); return value; } -float noise_texture(vector4 co, float detail, float distortion, output color Color) +float noise_texture( + vector4 co, float detail, float roughness, float distortion, output color Color) { vector4 p = co; if (distortion != 0.0) { @@ -110,10 +113,10 @@ float noise_texture(vector4 co, float detail, float distortion, output color Col safe_snoise(p + random_vector4_offset(3.0)) * distortion); } - float value = fractal_noise(p, detail); + float value = fractal_noise(p, detail, roughness); Color = color(value, - fractal_noise(p + random_vector4_offset(4.0), detail), - fractal_noise(p + random_vector4_offset(5.0), detail)); + fractal_noise(p + random_vector4_offset(4.0), detail, roughness), + fractal_noise(p + random_vector4_offset(5.0), detail, roughness)); return value; } @@ -124,6 +127,7 @@ shader node_noise_texture(int use_mapping = 0, float W = 0.0, float Scale = 5.0, float Detail = 2.0, + float Roughness = 0.5, float Distortion = 0.0, output float Fac = 0.0, output color Color = 0.0) @@ -136,13 +140,13 @@ shader node_noise_texture(int use_mapping = 0, float w = W * Scale; if (dimensions == "1D") - Fac = noise_texture(w, Detail, Distortion, Color); + Fac = noise_texture(w, Detail, Roughness, Distortion, Color); else if (dimensions == "2D") - Fac = noise_texture(vector2(p[0], p[1]), Detail, Distortion, Color); + Fac = noise_texture(vector2(p[0], p[1]), Detail, Roughness, Distortion, Color); else if (dimensions == "3D") - Fac = noise_texture(p, Detail, Distortion, Color); + Fac = noise_texture(p, Detail, Roughness, Distortion, Color); else if (dimensions == "4D") - Fac = noise_texture(vector4(p[0], p[1], p[2], w), Detail, Distortion, Color); + Fac = noise_texture(vector4(p[0], p[1], p[2], w), Detail, Roughness, Distortion, Color); else error("Unknown dimension!"); } diff --git a/intern/cycles/kernel/shaders/node_wave_texture.osl b/intern/cycles/kernel/shaders/node_wave_texture.osl index f17397be243..874bfb8d3af 100644 --- a/intern/cycles/kernel/shaders/node_wave_texture.osl +++ b/intern/cycles/kernel/shaders/node_wave_texture.osl @@ -24,9 +24,10 @@ float wave(point p_input, string bands_direction, string rings_direction, string profile, - float detail, float distortion, + float detail, float dscale, + float droughness, float phase) { /* Prevent precision issues on unit coordinates. */ @@ -67,7 +68,7 @@ float wave(point p_input, n += phase; if (distortion != 0.0) { - n = n + (distortion * (fractal_noise(p * dscale, detail) * 2.0 - 1.0)); + n = n + (distortion * (fractal_noise(p * dscale, detail, droughness) * 2.0 - 1.0)); } if (profile == "sine") { @@ -93,6 +94,7 @@ shader node_wave_texture(int use_mapping = 0, float Distortion = 0.0, float Detail = 2.0, float DetailScale = 1.0, + float DetailRoughness = 0.5, float PhaseOffset = 0.0, point Vector = P, output float Fac = 0.0, @@ -108,9 +110,10 @@ shader node_wave_texture(int use_mapping = 0, bands_direction, rings_direction, profile, - Detail, Distortion, + Detail, DetailScale, + DetailRoughness, PhaseOffset); Color = Fac; } |