summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFederico Mena Quintero <federico@gnome.org>2023-03-22 12:44:06 -0600
committerMarge Bot <marge-bot@gnome.org>2023-03-23 01:41:14 +0000
commit50eee1991e092671d7702a6ef7ebd569502cd447 (patch)
tree626f94849aa6f1bb2e1e2f50fc564101148bb624
parentce3b71599a5fa077f85fc19204ebacb5d5e32bb6 (diff)
downloadlibrsvg-50eee1991e092671d7702a6ef7ebd569502cd447.tar.gz
StackingCtx: decide whether there are filters at all right here, not in DrawingCtx
We used to have struct StackingCtx { filter: Filter } struct Filter { filter: properties::Filter, // other gunk } and there, Filter.filter can be properties::Filter::None or properties::Filter::List(FilterValueList). Resolve this early into an Option<Filter>, like this: struct StackingCtx { filter: Option<Filter> } struct Filter { filter_list: FilterValueList, // other gunk } This way, subsequent code in DrawingCtx doesn't have to tear apart the Filter.filter to see whether there's actually a filter specification there or just "none". Part-of: <https://gitlab.gnome.org/GNOME/librsvg/-/merge_requests/816>
-rw-r--r--src/drawing_ctx.rs20
-rw-r--r--src/layout.rs29
2 files changed, 27 insertions, 22 deletions
diff --git a/src/drawing_ctx.rs b/src/drawing_ctx.rs
index 8ef328a6..cdb84f16 100644
--- a/src/drawing_ctx.rs
+++ b/src/drawing_ctx.rs
@@ -34,8 +34,8 @@ use crate::paint_server::{PaintSource, UserSpacePaintSource};
use crate::path_builder::*;
use crate::pattern::UserSpacePattern;
use crate::properties::{
- ClipRule, ComputedValues, FillRule, Filter, MaskType, MixBlendMode, Opacity, Overflow,
- PaintTarget, ShapeRendering, StrokeLinecap, StrokeLinejoin, TextRendering,
+ ClipRule, ComputedValues, FillRule, MaskType, MixBlendMode, Opacity, Overflow, PaintTarget,
+ ShapeRendering, StrokeLinecap, StrokeLinejoin, TextRendering,
};
use crate::rect::{rect_to_transform, IRect, Rect};
use crate::session::Session;
@@ -765,12 +765,12 @@ impl DrawingCtx {
// Create temporary surface and its cr
- let cr = match stacking_ctx.filter.filter {
- Filter::None => cairo::Context::new(
+ let cr = match stacking_ctx.filter {
+ None => cairo::Context::new(
&self
.create_similar_surface_for_toplevel_viewport(&self.cr.target())?,
)?,
- Filter::List(_) => {
+ Some(_) => {
cairo::Context::new(self.create_surface_for_toplevel_viewport()?)?
}
};
@@ -790,7 +790,7 @@ impl DrawingCtx {
BoundingBox::new().with_transform(affines.for_temporary_surface)
};
- if let Filter::List(ref filter_list) = stacking_ctx.filter.filter {
+ if let Some(ref filter) = stacking_ctx.filter {
let surface_to_filter = SharedImageSurface::copy_from_surface(
&cairo::ImageSurface::try_from(temporary_draw_ctx.cr.target())
.unwrap(),
@@ -808,7 +808,7 @@ impl DrawingCtx {
.resolve(
acquired_nodes,
values.stroke_opacity().0,
- stacking_ctx.filter.current_color,
+ filter.current_color,
None,
None,
self.session(),
@@ -823,7 +823,7 @@ impl DrawingCtx {
.resolve(
acquired_nodes,
values.fill_opacity().0,
- stacking_ctx.filter.current_color,
+ filter.current_color,
None,
None,
self.session(),
@@ -843,13 +843,13 @@ impl DrawingCtx {
let filtered_surface = temporary_draw_ctx
.run_filters(
surface_to_filter,
- filter_list,
+ &filter.filter_list,
acquired_nodes,
&stacking_ctx.element_name,
&user_space_params,
stroke_paint_source,
fill_paint_source,
- stacking_ctx.filter.current_color,
+ filter.current_color,
bbox,
)?
.into_image_surface()?;
diff --git a/src/layout.rs b/src/layout.rs
index a65bc1cf..460095b3 100644
--- a/src/layout.rs
+++ b/src/layout.rs
@@ -14,6 +14,7 @@ use crate::coord_units::CoordUnits;
use crate::dasharray::Dasharray;
use crate::document::AcquiredNodes;
use crate::element::{Element, ElementData};
+use crate::filter::FilterValueList;
use crate::length::*;
use crate::node::*;
use crate::paint_server::{PaintSource, UserSpacePaintSource};
@@ -47,7 +48,7 @@ pub struct StackingContext {
pub element_name: String,
pub transform: Transform,
pub opacity: Opacity,
- pub filter: Filter,
+ pub filter: Option<Filter>,
pub clip_in_user_space: Option<Node>,
pub clip_in_object_space: Option<Node>,
pub mask: Option<Node>,
@@ -150,10 +151,21 @@ pub struct FontProperties {
}
pub struct Filter {
- pub filter: properties::Filter,
+ pub filter_list: FilterValueList,
pub current_color: RGBA,
}
+fn get_filter(values: &ComputedValues) -> Option<Filter> {
+ match values.filter() {
+ properties::Filter::None => None,
+
+ properties::Filter::List(filter_list) => Some(Filter {
+ filter_list: filter_list,
+ current_color: values.color().0,
+ }),
+ }
+}
+
impl StackingContext {
pub fn new(
session: &Session,
@@ -167,27 +179,20 @@ impl StackingContext {
let opacity;
let filter;
- let current_color = values.color().0;
-
match element.element_data {
// "The opacity, filter and display properties do not apply to the mask element"
// https://drafts.fxtf.org/css-masking-1/#MaskElement
ElementData::Mask(_) => {
opacity = Opacity(UnitInterval::clamp(1.0));
- filter = properties::Filter::None;
+ filter = None;
}
_ => {
opacity = values.opacity();
- filter = values.filter();
+ filter = get_filter(values);
}
}
- let filter = Filter {
- filter,
- current_color,
- };
-
let clip_path = values.clip_path();
let clip_uri = clip_path.0.get();
let (clip_in_user_space, clip_in_object_space) = clip_uri
@@ -274,7 +279,7 @@ impl StackingContext {
Isolation::Auto => {
let is_opaque = approx_eq!(f64, opacity, 1.0);
!(is_opaque
- && self.filter.filter == properties::Filter::None
+ && self.filter.is_none()
&& self.mask.is_none()
&& self.mix_blend_mode == MixBlendMode::Normal
&& self.clip_in_object_space.is_none())