[librsvg: 3/4] Handle the isolation property in the drawing machinery




commit 7eb6d567f415adcd3f1a16310e88ff8090555031
Author: Federico Mena Quintero <federico gnome org>
Date:   Thu Nov 11 14:40:38 2021 -0600

    Handle the isolation property in the drawing machinery
    
    This is an easy one; Isolation::Isolate basically means to
    unconditionally create a temporary surface for compositing, which we
    already know how to do.
    
    Part-of: <https://gitlab.gnome.org/GNOME/librsvg/-/merge_requests/630>

 src/drawing_ctx.rs                                 | 23 +++++++++++++---------
 .../reftests/svg2-reftests/isolation-ref.svg       |  4 ++++
 .../fixtures/reftests/svg2-reftests/isolation.svg  |  7 +++++++
 tests/src/reference.rs                             |  7 +++++++
 4 files changed, 32 insertions(+), 9 deletions(-)
---
diff --git a/src/drawing_ctx.rs b/src/drawing_ctx.rs
index af45c3ec1..8988ffe03 100644
--- a/src/drawing_ctx.rs
+++ b/src/drawing_ctx.rs
@@ -33,8 +33,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, Filter, Isolation, MaskType, MixBlendMode, Opacity,
+    Overflow, PaintTarget, ShapeRendering, StrokeLinecap, StrokeLinejoin, TextRendering,
 };
 use crate::rect::{IRect, Rect};
 use crate::surface_utils::{
@@ -718,14 +718,19 @@ impl DrawingCtx {
                     &self.empty_bbox(),
                 )?;
 
-                let is_opaque = approx_eq!(f64, opacity, 1.0);
-                let needs_temporary_surface = !(is_opaque
-                    && stacking_ctx.filter == Filter::None
-                    && stacking_ctx.mask.is_none()
-                    && stacking_ctx.mix_blend_mode == MixBlendMode::Normal
-                    && stacking_ctx.clip_in_object_space.is_none());
+                let should_isolate = match stacking_ctx.isolation {
+                    Isolation::Auto => {
+                        let is_opaque = approx_eq!(f64, opacity, 1.0);
+                        !(is_opaque
+                            && stacking_ctx.filter == Filter::None
+                            && stacking_ctx.mask.is_none()
+                            && stacking_ctx.mix_blend_mode == MixBlendMode::Normal
+                            && stacking_ctx.clip_in_object_space.is_none())
+                    }
+                    Isolation::Isolate => true,
+                };
 
-                let res = if needs_temporary_surface {
+                let res = if should_isolate {
                     // Compute our assortment of affines
 
                     let affines = CompositingAffines::new(
diff --git a/tests/fixtures/reftests/svg2-reftests/isolation-ref.svg 
b/tests/fixtures/reftests/svg2-reftests/isolation-ref.svg
new file mode 100644
index 000000000..4d62f1326
--- /dev/null
+++ b/tests/fixtures/reftests/svg2-reftests/isolation-ref.svg
@@ -0,0 +1,4 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg xmlns="http://www.w3.org/2000/svg"; width="200" height="200">
+  <rect width="100%" height="100%" fill="lime"/>
+</svg>
diff --git a/tests/fixtures/reftests/svg2-reftests/isolation.svg 
b/tests/fixtures/reftests/svg2-reftests/isolation.svg
new file mode 100644
index 000000000..367ba85de
--- /dev/null
+++ b/tests/fixtures/reftests/svg2-reftests/isolation.svg
@@ -0,0 +1,7 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg xmlns="http://www.w3.org/2000/svg"; width="200" height="200">
+  <rect width="100%" height="100%" fill="lime"/>
+  <g style="isolation: isolate;">
+    <rect width="50%" height="50%" fill="lime" style="mix-blend-mode: difference;"/>
+  </g>
+</svg>
diff --git a/tests/src/reference.rs b/tests/src/reference.rs
index 9eaa49f70..03ce6b30f 100644
--- a/tests/src/reference.rs
+++ b/tests/src/reference.rs
@@ -18,6 +18,7 @@ use librsvg::{
 use std::path::PathBuf;
 
 use crate::reference_utils::{Compare, Evaluate, Reference};
+use crate::test_svg_reference;
 use crate::utils::{load_svg, render_document, setup_font_map, setup_language, SurfaceSize};
 
 // The original reference images from the SVG1.1 test suite are at 72 DPI.
@@ -393,3 +394,9 @@ test_compare_render_output!(
   </svg>
     "##,
 );
+
+test_svg_reference!(
+    isolation,
+    "tests/fixtures/reftests/svg2-reftests/isolation.svg",
+    "tests/fixtures/reftests/svg2-reftests/isolation-ref.svg"
+);


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]