From 993d463a2c38ebc9805c7467e4a602a2ffca1b85 Mon Sep 17 00:00:00 2001 From: Dogway <13509598+Dogway@users.noreply.github.com> Date: Tue, 31 Mar 2020 10:36:51 +0100 Subject: [PATCH 1/2] Update white_point.slang Ported updated white_point.glsl to slang format. --- misc/white_point.slang | 177 ++++++++++++++++++++++++++++------------- 1 file changed, 120 insertions(+), 57 deletions(-) diff --git a/misc/white_point.slang b/misc/white_point.slang index c5e0ec1..c81d60f 100644 --- a/misc/white_point.slang +++ b/misc/white_point.slang @@ -1,32 +1,37 @@ #version 450 -// white point adjustment -// by hunterk -// based on blog post by Tanner Helland -// http://www.tannerhelland.com/4435/convert-temperature-rgb-algorithm-code/ +// White Point Mapping +// ported by Dogway +// +// From the first comment post (sRGB primaries and linear light compensated) +// http://www.zombieprototypes.com/?p=210#comment-4695029660 +// Based on the Neil Bartlett's blog update +// http://www.zombieprototypes.com/?p=210 +// Inspired itself by Tanner Helland's work +// http://www.tannerhelland.com/4435/convert-temperature-rgb-algorithm-code/ layout(push_constant) uniform Push { - vec4 SourceSize; - vec4 OriginalSize; - vec4 OutputSize; - uint FrameCount; + vec4 SourceSize; + vec4 OriginalSize; + vec4 OutputSize; + uint FrameCount; float temperature; float luma_preserve; - float wp_red; - float wp_green; - float wp_blue; + float red; + float green; + float blue; } params; -#pragma parameter temperature "White Point" 6500.0 0.0 12000.0 100.0 +#pragma parameter temperature "White Point" 9311.0 1031.0 12047.0 72.0 #pragma parameter luma_preserve "Preserve Luminance" 1.0 0.0 1.0 1.0 -#pragma parameter wp_red "Red Shift" 0.0 -1.0 1.0 0.01 -#pragma parameter wp_green "Green Shift" 0.0 -1.0 1.0 0.01 -#pragma parameter wp_blue "Blue Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter red "Red Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter green "Green Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter blue "Blue Shift" 0.0 -1.0 1.0 0.01 layout(std140, set = 0, binding = 0) uniform UBO { - mat4 MVP; + mat4 MVP; } global; #pragma stage vertex @@ -45,51 +50,109 @@ layout(location = 0) in vec2 vTexCoord; layout(location = 0) out vec4 FragColor; layout(set = 0, binding = 2) uniform sampler2D Source; -// white point adjustment -// based on blog post by Tanner Helland -// http://www.tannerhelland.com/4435/convert-temperature-rgb-algorithm-code/ + + vec3 wp_adjust(vec3 color){ - const float target_white_point = 9300.0; - const mat3 RGBtoYIQ = mat3( - 0.2989, 0.5870, 0.1140, - 0.5959, -0.2744, -0.3216, - 0.2115, -0.5229, 0.3114); - const mat3 YIQtoRGB = mat3( - 1.0, 0.956, 0.6210, - 1.0, -0.2720, -0.6474, - 1.0, -1.1060, 1.7046); + float temp = params.temperature / 100.; + float k = params.temperature / 10000.; + float lk = log(k); - float temp = params.temperature / 100.0; - - // all calculations assume a scale of 255. We'll normalize this at the end - vec3 wp = vec3(255.); - - // calculate RED - wp.r = (temp <= 66.) ? 255. : 329.698727446 * pow((temp - 60.), -0.1332047592); - - // calculate GREEN - wp.g = (temp <= 66.) ? 99.4708025861 * log(temp) - 161.1195681661 : 288.1221695283 * pow((temp - 60.), -0.0755148492); - - // calculate BLUE - wp.b = (temp >= 66.) ? 255. : (temp <= 19.) ? 0. : 138.5177312231 * log(temp - 10.) - 305.0447927307; - - // clamp and normalize - wp.rgb = clamp(wp.rgb, vec3(0.), vec3(255.)) / vec3(255.); - - // this is dumb, but various cores don't always show white as white. Use this to make white white... - wp.rgb += vec3(params.wp_red, params.wp_green, params.wp_blue); - - // apply transformation - vec3 adjusted = (color * wp); - vec3 base_luma = color * RGBtoYIQ; - vec3 adjusted_luma = adjusted * RGBtoYIQ; - adjusted = (params.luma_preserve > 0.5) ? adjusted_luma + (vec3(base_luma.r,0.,0.) - vec3(adjusted_luma.r,0.,0.)) : adjusted_luma; - - return adjusted * YIQtoRGB; + vec3 wp = vec3(1.); + + // calculate RED + wp.r = (temp <= 65.) ? 1. : 0.32068362618584273 + (0.19668730877673762 * pow(k - 0.21298613432655075, - 1.5139012907556737)) + (- 0.013883432789258415 * lk); + + // calculate GREEN + float mg = 1.226916242502167 + (- 1.3109482654223614 * pow(k - 0.44267061967913873, 3.) * exp(- 5.089297600846147 * (k - 0.44267061967913873))) + (0.6453936305542096 * lk); + float pg = 0.4860175851734596 + (0.1802139719519286 * pow(k - 0.14573069517701578, - 1.397716496795082)) + (- 0.00803698899233844 * lk); + wp.g = (temp <= 65.5) ? ((temp <= 8.) ? 0. : mg) : pg; + + // calculate BLUE + wp.b = (temp <= 19.) ? 0. : (temp >= 66.) ? 1. : 1.677499032830161 + (- 0.02313594016938082 * pow(k - 1.1367244820333684, 3.) * exp(- 4.221279555918655 * (k - 1.1367244820333684))) + (1.6550275798913296 * lk); + + // clamp + wp.rgb = clamp(wp.rgb, vec3(0.), vec3(1.)); + + // R/G/B independent manual White Point adjustment + wp.rgb += vec3(params.red, params.green, params.blue); + + // Linear color input + return color * wp; } +vec3 sRGB_to_XYZ(vec3 RGB){ + + const mat3x3 m = mat3x3( + 0.4124564, 0.3575761, 0.1804375, + 0.2126729, 0.7151522, 0.0721750, + 0.0193339, 0.1191920, 0.9503041); + return RGB * m; +} + + +vec3 XYZtoYxy(vec3 XYZ){ + + float XYZrgb = XYZ.r+XYZ.g+XYZ.b; + float Yxyr = XYZ.g; + float Yxyg = (XYZrgb <= 0.0) ? 0.3805 : XYZ.r / XYZrgb; + float Yxyb = (XYZrgb <= 0.0) ? 0.3769 : XYZ.g / XYZrgb; + return vec3(Yxyr,Yxyg,Yxyb); +} + +vec3 XYZ_to_sRGB(vec3 XYZ){ + + const mat3x3 m = mat3x3( + 3.2404542, -1.5371385, -0.4985314, + -0.9692660, 1.8760108, 0.0415560, + 0.0556434, -0.2040259, 1.0572252); + return XYZ * m; +} + + +vec3 YxytoXYZ(vec3 Yxy){ + + float Xs = Yxy.r * (Yxy.g/Yxy.b); + float Xsz = (Yxy.r <= 0.0) ? 0 : 1; + vec3 XYZ = vec3(Xsz,Xsz,Xsz) * vec3(Xs, Yxy.r, (Xs/Yxy.g)-Xs-Yxy.r); + return XYZ; +} + + +vec3 linear_to_sRGB(vec3 color, float gamma){ + + color = clamp(color, 0.0, 1.0); + color.r = (color.r <= 0.00313066844250063) ? + color.r * 12.92 : 1.055 * pow(color.r, 1.0 / gamma) - 0.055; + color.g = (color.g <= 0.00313066844250063) ? + color.g * 12.92 : 1.055 * pow(color.g, 1.0 / gamma) - 0.055; + color.b = (color.b <= 0.00313066844250063) ? + color.b * 12.92 : 1.055 * pow(color.b, 1.0 / gamma) - 0.055; + + return color.rgb; +} + + +vec3 sRGB_to_linear(vec3 color, float gamma){ + + color = clamp(color, 0.0, 1.0); + color.r = (color.r <= 0.04045) ? + color.r / 12.92 : pow((color.r + 0.055) / (1.055), gamma); + color.g = (color.g <= 0.04045) ? + color.g / 12.92 : pow((color.g + 0.055) / (1.055), gamma); + color.b = (color.b <= 0.04045) ? + color.b / 12.92 : pow((color.b + 0.055) / (1.055), gamma); + + return color.rgb; +} + + void main() { - FragColor = vec4(wp_adjust(texture(Source, vTexCoord).rgb), 1.0); -} \ No newline at end of file + vec3 original = sRGB_to_linear(texture(Source, vTexCoord).rgb, 2.40); + vec3 adjusted = wp_adjust(original); + vec3 base_luma = XYZtoYxy(sRGB_to_XYZ(original)); + vec3 adjusted_luma = XYZtoYxy(sRGB_to_XYZ(adjusted)); + adjusted = (params.luma_preserve == 1.0) ? adjusted_luma + (vec3(base_luma.r,0.,0.) - vec3(adjusted_luma.r,0.,0.)) : adjusted_luma; + FragColor = vec4(linear_to_sRGB(XYZ_to_sRGB(YxytoXYZ(adjusted)), 2.40), 1.0); +} From 49c860f6ac35900add23e834e8d5037444b59bc6 Mon Sep 17 00:00:00 2001 From: Dogway <13509598+Dogway@users.noreply.github.com> Date: Tue, 31 Mar 2020 18:55:49 +0100 Subject: [PATCH 2/2] Update white_point.slang --- misc/white_point.slang | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/misc/white_point.slang b/misc/white_point.slang index c81d60f..ba1bad0 100644 --- a/misc/white_point.slang +++ b/misc/white_point.slang @@ -18,16 +18,16 @@ layout(push_constant) uniform Push uint FrameCount; float temperature; float luma_preserve; - float red; - float green; - float blue; + float wp_red; + float wp_green; + float wp_blue; } params; #pragma parameter temperature "White Point" 9311.0 1031.0 12047.0 72.0 #pragma parameter luma_preserve "Preserve Luminance" 1.0 0.0 1.0 1.0 -#pragma parameter red "Red Shift" 0.0 -1.0 1.0 0.01 -#pragma parameter green "Green Shift" 0.0 -1.0 1.0 0.01 -#pragma parameter blue "Blue Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter wp_red "Red Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter wp_green "Green Shift" 0.0 -1.0 1.0 0.01 +#pragma parameter wp_blue "Blue Shift" 0.0 -1.0 1.0 0.01 layout(std140, set = 0, binding = 0) uniform UBO { @@ -75,7 +75,7 @@ vec3 wp_adjust(vec3 color){ wp.rgb = clamp(wp.rgb, vec3(0.), vec3(1.)); // R/G/B independent manual White Point adjustment - wp.rgb += vec3(params.red, params.green, params.blue); + wp.rgb += vec3(params.wp_red, params.wp_green, params.wp_blue); // Linear color input return color * wp;