diff --git a/gsk/gpu/shaders/color.glsl b/gsk/gpu/shaders/color.glsl index 91538b2419..577e970978 100644 --- a/gsk/gpu/shaders/color.glsl +++ b/gsk/gpu/shaders/color.glsl @@ -24,24 +24,6 @@ color_unpremultiply (vec4 color) return color.a > 0.0 ? color / vec4 (color.aaa, 1.0) : color; } -float -srgb_eotf (float v) -{ - if (v >= 0.04045) - return pow (((v + 0.055) / (1.0 + 0.055)), 2.4); - else - return v / 12.92; -} - -float -srgb_oetf (float v) -{ - if (v > 0.0031308) - return 1.055 * pow (v, 1.0 / 2.4) - 0.055; - else - return 12.92 * v; -} - vec4 alt_color_alpha (vec4 color, float alpha) @@ -62,82 +44,115 @@ output_color_alpha (vec4 color, return vec4 (color.rgb, color.a * alpha); } -vec4 -alt_color_from_output (vec4 color) +float +srgb_eotf (float v) { - if (OUTPUT_COLOR_SPACE == ALT_COLOR_SPACE) - { - if (OUTPUT_PREMULTIPLIED && !ALT_PREMULTIPLIED) - return color_unpremultiply (color); - else if (!OUTPUT_PREMULTIPLIED && ALT_PREMULTIPLIED) - return color_premultiply (color); - else - return color; - } + if (v >= 0.04045) + return pow (((v + 0.055) / (1.0 + 0.055)), 2.4); + else + return v / 12.92; +} - if (OUTPUT_PREMULTIPLIED) +float +srgb_oetf (float v) +{ + if (v > 0.0031308) + return 1.055 * pow (v, 1.0 / 2.4) - 0.055; + else + return 12.92 * v; +} + +vec3 +apply_eotf (vec3 color, + uint cs) +{ + switch (cs) + { + case GDK_COLOR_STATE_ID_SRGB: + return vec3 (srgb_eotf (color.r), + srgb_eotf (color.g), + srgb_eotf (color.b)); + + default: + return color; + } +} + +vec3 +apply_oetf (vec3 color, + uint cs) +{ + switch (cs) + { + case GDK_COLOR_STATE_ID_SRGB: + return vec3 (srgb_oetf (color.r), + srgb_oetf (color.g), + srgb_oetf (color.b)); + + default: + return color; + } +} + +vec3 +convert_linear (vec3 color, + uint from, + uint to) +{ + return color; +} + +uint +linear_color_space (uint cs) +{ + return GDK_COLOR_STATE_ID_SRGB_LINEAR; +} + +vec4 +convert_color (vec4 color, + uint from, + bool from_premul, + uint to, + bool to_premul) +{ + if (from_premul && (!to_premul || from != to)) color = color_unpremultiply (color); - if (OUTPUT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB && - ALT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB_LINEAR) + if (from != to) { - color = vec4 (srgb_eotf (color.r), - srgb_eotf (color.g), - srgb_eotf (color.b), - color.a); - } - else if (OUTPUT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB_LINEAR && - ALT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB) - { - color = vec4 (srgb_oetf (color.r), - srgb_oetf (color.g), - srgb_oetf (color.b), - color.a); + uint from_linear = linear_color_space (from); + uint to_linear = linear_color_space (to); + + if (from_linear != from) + color.rgb = apply_eotf (color.rgb, from); + + if (from_linear != to_linear) + color.rgb = convert_linear (color.rgb, from_linear, to_linear); + + if (to_linear != to) + color.rgb = apply_oetf (color.rgb, to); } - if (ALT_PREMULTIPLIED) + if (to_premul && (!from_premul || from != to)) color = color_premultiply (color); return color; } +vec4 +alt_color_from_output (vec4 color) +{ + return convert_color (color, + OUTPUT_COLOR_SPACE, OUTPUT_PREMULTIPLIED, + ALT_COLOR_SPACE, ALT_PREMULTIPLIED); +} + vec4 output_color_from_alt (vec4 color) { - if (OUTPUT_COLOR_SPACE == ALT_COLOR_SPACE) - { - if (ALT_PREMULTIPLIED && !OUTPUT_PREMULTIPLIED) - return color_unpremultiply (color); - else if (!ALT_PREMULTIPLIED && OUTPUT_PREMULTIPLIED) - return color_premultiply (color); - else - return color; - } - - if (ALT_PREMULTIPLIED) - color = color_unpremultiply (color); - - if (ALT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB && - OUTPUT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB_LINEAR) - { - color = vec4 (srgb_eotf (color.r), - srgb_eotf (color.g), - srgb_eotf (color.b), - color.a); - } - else if (ALT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB_LINEAR && - OUTPUT_COLOR_SPACE == GDK_COLOR_STATE_ID_SRGB) - { - color = vec4 (srgb_oetf (color.r), - srgb_oetf (color.g), - srgb_oetf (color.b), - color.a); - } - - if (OUTPUT_PREMULTIPLIED) - color = color_premultiply (color); - - return color; + return convert_color (color, + ALT_COLOR_SPACE, ALT_PREMULTIPLIED, + OUTPUT_COLOR_SPACE, OUTPUT_PREMULTIPLIED); } float