/*
* Copyright © 2025 Red Hat , Inc
*
* SPDX - License - Identifier : LGPL - 2 . 1 - or - later
*
* This library is free software ; you can redistribute it and / or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation ; either
* version 2 . 1 of the License , or ( at your option ) any later version .
*
* This library is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the GNU
* Lesser General Public License for more details .
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library . If not , see < http : //www.gnu.org/licenses/>.
*
* Authors : Matthias Clasen < mclasen @ redhat . com >
*/
#include "config.h"
#include "gtksvgtextdecorationprivate.h"
#include "gtksvgvalueprivate.h"
#include "gtksvgelementinternal.h"
static const struct {
const char *name;
TextDecoration value;
} text_decorations[] = {
{ .name = "underline" , .value = TEXT_DECORATION_UNDERLINE },
{ .name = "overline" , .value = TEXT_DECORATION_OVERLINE },
{ .name = "line-through" , .value = TEXT_DECORATION_LINE_THROUGH },
};
typedef struct
{
SvgValue base;
TextDecoration value;
} SvgTextDecoration;
static gboolean
svg_text_decoration_equal (const SvgValue *value0,
const SvgValue *value1)
{
const SvgTextDecoration *d0 = (const SvgTextDecoration *)value0;
const SvgTextDecoration *d1 = (const SvgTextDecoration *)value1;
return d0->value == d1->value;
}
static SvgValue *
svg_text_decoration_interpolate (const SvgValue *value0,
const SvgValue *value1,
SvgComputeContext *context,
double t)
{
if (t < 0 .5 )
return svg_value_ref ((SvgValue *) value0);
else
return svg_value_ref ((SvgValue *) value1);
}
static SvgValue *
svg_text_decoration_accumulate (const SvgValue *value0,
const SvgValue *value1,
SvgComputeContext *context,
int n)
{
return svg_value_ref ((SvgValue *)value0);
}
static void
svg_text_decoration_print (const SvgValue *value,
GString *string)
{
const SvgTextDecoration *d = (const SvgTextDecoration *)value;
gboolean has_value = FALSE ;
for (size_t i = 0 ; i < G_N_ELEMENTS (text_decorations); i++)
if (d->value & text_decorations[i].value)
{
if (has_value)
g_string_append_c (string, ' ' );
g_string_append (string, text_decorations[i].name);
has_value = TRUE ;
}
}
static SvgValue * svg_text_decoration_resolve (const SvgValue *value,
SvgProperty attr,
unsigned int idx,
SvgElement *shape,
SvgComputeContext *context);
static const SvgValueClass SVG_TEXT_DECORATION_CLASS = {
"SvgTextDecoration" ,
svg_value_default_free,
svg_text_decoration_equal,
svg_text_decoration_interpolate,
svg_text_decoration_accumulate,
svg_text_decoration_print,
svg_value_default_distance,
svg_text_decoration_resolve,
};
SvgValue *
svg_text_decoration_new (TextDecoration decoration)
{
static SvgTextDecoration none = { { &SVG_TEXT_DECORATION_CLASS, 0 }, .value = TEXT_DECORATION_NONE };
SvgTextDecoration *result;
if (decoration == TEXT_DECORATION_NONE)
return (SvgValue *) &none;
result = (SvgTextDecoration *) svg_value_alloc (&SVG_TEXT_DECORATION_CLASS, sizeof (SvgTextDecoration));
result->value = decoration;
return (SvgValue *) result;
}
SvgValue *
svg_text_decoration_parse (GtkCssParser *parser)
{
TextDecoration val = TEXT_DECORATION_NONE;
while (!gtk_css_parser_has_token (parser, GTK_CSS_TOKEN_EOF))
{
unsigned int i;
gtk_css_parser_skip_whitespace (parser);
for (i = 0 ; i < G_N_ELEMENTS (text_decorations); i++)
{
if (gtk_css_parser_try_ident (parser, text_decorations[i].name))
{
val |= text_decorations[i].value;
break ;
}
}
if (i == G_N_ELEMENTS (text_decorations))
return NULL;
}
return svg_text_decoration_new (val);
}
static SvgValue *
svg_text_decoration_resolve (const SvgValue *value,
SvgProperty attr,
unsigned int idx,
SvgElement *shape,
SvgComputeContext *context)
{
TextDecoration ret;
if (!context->parent)
return svg_value_ref ((SvgValue *)value);
ret = svg_text_decoration_get (context->parent->current[attr]);
if (ret == TEXT_DECORATION_NONE)
return svg_value_ref ((SvgValue *)value);
ret |= svg_text_decoration_get (value);
return svg_text_decoration_new (ret);
}
TextDecoration
svg_text_decoration_get (const SvgValue *value)
{
const SvgTextDecoration *d = (const SvgTextDecoration *)value;
return d->value;
}
Messung V0.5 in Prozent C=98 H=95 G=96
¤ Dauer der Verarbeitung: 0.11 Sekunden
(vorverarbeitet am 2026-07-02)
¤
*© Formatika GbR, Deutschland