1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-10 05:17:34 +00:00

LibWeb: Implement SVG opacity properties

This implements the stop-opacity, fill-opacity, and stroke-opacity
properties (in CSS). This replaces the existing more ad-hoc
fill-opacity attribute handling.
This commit is contained in:
MacDue 2023-05-19 20:35:39 +01:00 committed by Andreas Kling
parent 120e5b6b6f
commit 00cda96e2d
13 changed files with 141 additions and 29 deletions

View file

@ -236,36 +236,58 @@ Optional<int> StyleProperties::z_index() const
return {};
}
float StyleProperties::opacity() const
static float resolve_opacity_value(CSS::StyleValue const& value)
{
auto value = property(CSS::PropertyID::Opacity);
float unclamped_opacity = 1.0f;
if (value->has_number()) {
unclamped_opacity = value->to_number();
} else if (value->is_calculated()) {
auto& calculated = value->as_calculated();
if (value.has_number()) {
unclamped_opacity = value.to_number();
} else if (value.is_calculated()) {
auto& calculated = value.as_calculated();
if (calculated.resolved_type() == CalculatedStyleValue::ResolvedType::Percentage) {
auto maybe_percentage = value->as_calculated().resolve_percentage();
auto maybe_percentage = value.as_calculated().resolve_percentage();
if (maybe_percentage.has_value())
unclamped_opacity = maybe_percentage->as_fraction();
else
dbgln("Unable to resolve calc() as opacity (percentage): {}", value->to_string());
dbgln("Unable to resolve calc() as opacity (percentage): {}", value.to_string());
} else {
auto maybe_number = const_cast<CalculatedStyleValue&>(value->as_calculated()).resolve_number();
auto maybe_number = const_cast<CalculatedStyleValue&>(value.as_calculated()).resolve_number();
if (maybe_number.has_value())
unclamped_opacity = maybe_number.value();
else
dbgln("Unable to resolve calc() as opacity (number): {}", value->to_string());
dbgln("Unable to resolve calc() as opacity (number): {}", value.to_string());
}
} else if (value->is_percentage()) {
unclamped_opacity = value->as_percentage().percentage().as_fraction();
} else if (value.is_percentage()) {
unclamped_opacity = value.as_percentage().percentage().as_fraction();
}
return clamp(unclamped_opacity, 0.0f, 1.0f);
}
float StyleProperties::opacity() const
{
auto value = property(CSS::PropertyID::Opacity);
return resolve_opacity_value(*value);
}
float StyleProperties::fill_opacity() const
{
auto value = property(CSS::PropertyID::FillOpacity);
return resolve_opacity_value(*value);
}
float StyleProperties::stroke_opacity() const
{
auto value = property(CSS::PropertyID::StrokeOpacity);
return resolve_opacity_value(*value);
}
float StyleProperties::stop_opacity() const
{
auto value = property(CSS::PropertyID::StopOpacity);
return resolve_opacity_value(*value);
}
Optional<CSS::FlexDirection> StyleProperties::flex_direction() const
{
auto value = property(CSS::PropertyID::FlexDirection);