Merge branch 'matthiasc/for-main' into 'main'

Fix a bug in color conversion

See merge request GNOME/gtk!7328
This commit is contained in:
Matthias Clasen 2024-06-02 15:24:09 +00:00
commit 856f1808de
4 changed files with 107 additions and 42 deletions

View File

@ -157,6 +157,61 @@ gtk_css_color_to_string (const GtkCssColor *color)
return g_string_free (gtk_css_color_print (color, FALSE, g_string_new ("")), FALSE);
}
const char *
gtk_css_color_space_get_coord_name (GtkCssColorSpace color_space,
guint coord)
{
if (coord == 3)
return "alpha";
switch (color_space)
{
case GTK_CSS_COLOR_SPACE_SRGB:
case GTK_CSS_COLOR_SPACE_SRGB_LINEAR:
switch (coord)
{
case 0: return "r";
case 1: return "g";
case 2: return "b";
default: g_assert_not_reached ();
}
case GTK_CSS_COLOR_SPACE_HSL:
switch (coord)
{
case 0: return "h";
case 1: return "s";
case 2: return "l";
default: g_assert_not_reached ();
}
case GTK_CSS_COLOR_SPACE_HWB:
switch (coord)
{
case 0: return "h";
case 1: return "w";
case 2: return "b";
default: g_assert_not_reached ();
}
case GTK_CSS_COLOR_SPACE_OKLAB:
switch (coord)
{
case 0: return "l";
case 1: return "a";
case 2: return "b";
default: g_assert_not_reached ();
}
case GTK_CSS_COLOR_SPACE_OKLCH:
switch (coord)
{
case 0: return "l";
case 1: return "c";
case 2: return "h";
default: g_assert_not_reached ();
}
default:
g_assert_not_reached ();
}
}
/* }}} */
/* {{{ Color conversion */
@ -321,7 +376,8 @@ convert_linear_to_linear (GtkCssColor *output,
GtkCssColorSpace dest_linear;
float v[4];
if (dest == GTK_CSS_COLOR_SPACE_OKLCH)
if (dest == GTK_CSS_COLOR_SPACE_OKLCH ||
dest == GTK_CSS_COLOR_SPACE_OKLAB)
dest_linear = GTK_CSS_COLOR_SPACE_OKLAB;
else
dest_linear = GTK_CSS_COLOR_SPACE_SRGB_LINEAR;

View File

@ -109,4 +109,7 @@ void gtk_css_color_interpolate (const GtkCssColor *from,
GtkCssHueInterpolation interp,
GtkCssColor *output);
const char * gtk_css_color_space_get_coord_name (GtkCssColorSpace color_space,
guint coord);
G_END_DECLS

View File

@ -74,6 +74,8 @@ struct _GtkCssValue
};
};
/* {{{ GtkCssValue vfuncs */
static void
gtk_css_value_color_free (GtkCssValue *color)
{
@ -247,17 +249,6 @@ gtk_css_value_color_transition (GtkCssValue *start,
return gtk_css_color_value_new_mix (start, end, progress);
}
static inline void
append_color_component (GString *string,
const GtkCssColor *color,
guint idx)
{
if (gtk_css_color_component_missing (color, idx))
g_string_append (string, "none");
else
g_string_append_printf (string, "%g", gtk_css_color_get_component (color, idx));
}
static void
gtk_css_value_color_print (const GtkCssValue *value,
GString *string)
@ -328,6 +319,9 @@ static const GtkCssValueClass GTK_CSS_VALUE_COLOR = {
gtk_css_value_color_print
};
/* }}} */
/* {{{ Resolving colors */
static void
apply_alpha (const GdkRGBA *in,
GdkRGBA *out,
@ -354,7 +348,7 @@ apply_shade (const GdkRGBA *in,
static inline double
transition (double start,
double end,
double progress)
double progress)
{
return start + (end - start) * progress;
}
@ -497,6 +491,9 @@ gtk_css_color_value_resolve (GtkCssValue *color,
return gtk_css_color_value_do_resolve (color, provider, current, NULL);
}
/* }}} */
/* {{{ Constructors */
static GtkCssValue transparent_black_singleton = { &GTK_CSS_VALUE_COLOR, 1, TRUE, FALSE, FALSE, COLOR_TYPE_LITERAL,
.rgba = {0, 0, 0, 0} };
static GtkCssValue white_singleton = { &GTK_CSS_VALUE_COLOR, 1, TRUE, FALSE, FALSE, COLOR_TYPE_LITERAL,
@ -664,6 +661,32 @@ gtk_css_color_value_new_current_color (void)
return gtk_css_value_ref (&current_color);
}
/* }}} */
/* {{{ Parsing */
gboolean
gtk_css_color_value_can_parse (GtkCssParser *parser)
{
/* This is way too generous, but meh... */
return gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_IDENT)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_AT_KEYWORD)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_HASH_ID)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_HASH_UNRESTRICTED)
|| gtk_css_parser_has_function (parser, "lighter")
|| gtk_css_parser_has_function (parser, "darker")
|| gtk_css_parser_has_function (parser, "shade")
|| gtk_css_parser_has_function (parser, "alpha")
|| gtk_css_parser_has_function (parser, "mix")
|| gtk_css_parser_has_function (parser, "hsl")
|| gtk_css_parser_has_function (parser, "hsla")
|| gtk_css_parser_has_function (parser, "rgb")
|| gtk_css_parser_has_function (parser, "rgba")
|| gtk_css_parser_has_function (parser, "hwb")
|| gtk_css_parser_has_function (parser, "oklab")
|| gtk_css_parser_has_function (parser, "oklch")
|| gtk_css_parser_has_function (parser, "color");
}
typedef struct
{
GtkCssValue *color;
@ -727,29 +750,6 @@ parse_color_number (GtkCssParser *parser,
}
}
gboolean
gtk_css_color_value_can_parse (GtkCssParser *parser)
{
/* This is way too generous, but meh... */
return gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_IDENT)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_AT_KEYWORD)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_HASH_ID)
|| gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_HASH_UNRESTRICTED)
|| gtk_css_parser_has_function (parser, "lighter")
|| gtk_css_parser_has_function (parser, "darker")
|| gtk_css_parser_has_function (parser, "shade")
|| gtk_css_parser_has_function (parser, "alpha")
|| gtk_css_parser_has_function (parser, "mix")
|| gtk_css_parser_has_function (parser, "hsl")
|| gtk_css_parser_has_function (parser, "hsla")
|| gtk_css_parser_has_function (parser, "rgb")
|| gtk_css_parser_has_function (parser, "rgba")
|| gtk_css_parser_has_function (parser, "hwb")
|| gtk_css_parser_has_function (parser, "oklab")
|| gtk_css_parser_has_function (parser, "oklch")
|| gtk_css_parser_has_function (parser, "color");
}
typedef struct
{
GdkRGBA *rgba;
@ -1553,6 +1553,9 @@ gtk_css_color_value_parse (GtkCssParser *parser)
return NULL;
}
/* }}} */
/* {{{ Utilities */
const GdkRGBA *
gtk_css_color_value_get_rgba (const GtkCssValue *color)
{
@ -1570,3 +1573,6 @@ gtk_css_color_value_get_color (const GtkCssValue *color)
return &color->color;
}
/* }}} */
/* vim:set foldmethod=marker expandtab: */

View File

@ -1015,11 +1015,11 @@ gtk_css_number_value_multiply (GtkCssValue *value,
break;
}
return gtk_css_math_value_new (TYPE_PRODUCT, 0,
(GtkCssValue *[]) {
gtk_css_value_ref (value),
gtk_css_number_value_new (factor, GTK_CSS_NUMBER)
}, 2);
return gtk_css_math_value_new (TYPE_PRODUCT, 0,
(GtkCssValue *[]) {
gtk_css_value_ref (value),
gtk_css_number_value_new (factor, GTK_CSS_NUMBER)
}, 2);
}
GtkCssValue *
@ -1314,7 +1314,7 @@ gtk_css_arg2_value_new (guint type,
return gtk_css_dimension_value_new (v, unit);
}
/* This funciton is called at parsing time, so units are not
/* This function is called at parsing time, so units are not
* canonical, and length values can't necessarily be unified.
*/
GtkCssValue *