[librsvg: 19/22] node: split resolve_resources method



commit 1579902a9ebf04d69f652cfea849750e6ff9e784
Author: Paolo Borelli <pborelli gnome org>
Date:   Tue Jan 8 12:43:11 2019 +0100

    node: split resolve_resources method
    
    Split a separate method in the trait that is used to load resources,
    this allow to clean up the set_atts signature in most of the cases.
    Later we can think of moving the actual load of the resources to
    its own tree trasversal instead of doing it during parsing.

 rsvg_internals/src/clip_path.rs                  |  3 +-
 rsvg_internals/src/filters/blend.rs              | 10 +----
 rsvg_internals/src/filters/color_matrix.rs       | 10 +----
 rsvg_internals/src/filters/component_transfer.rs | 12 ++----
 rsvg_internals/src/filters/composite.rs          | 10 +----
 rsvg_internals/src/filters/convolve_matrix.rs    | 10 +----
 rsvg_internals/src/filters/displacement_map.rs   | 10 +----
 rsvg_internals/src/filters/flood.rs              | 10 +----
 rsvg_internals/src/filters/gaussian_blur.rs      | 10 +----
 rsvg_internals/src/filters/image.rs              | 13 +++----
 rsvg_internals/src/filters/light/light_source.rs |  3 +-
 rsvg_internals/src/filters/light/lighting.rs     | 10 +----
 rsvg_internals/src/filters/merge.rs              | 12 ++----
 rsvg_internals/src/filters/mod.rs                | 12 ++----
 rsvg_internals/src/filters/morphology.rs         | 10 +----
 rsvg_internals/src/filters/node.rs               |  3 +-
 rsvg_internals/src/filters/offset.rs             | 10 +----
 rsvg_internals/src/filters/tile.rs               | 10 +----
 rsvg_internals/src/filters/turbulence.rs         | 10 +----
 rsvg_internals/src/gradient.rs                   |  3 +-
 rsvg_internals/src/image.rs                      | 48 +++++++++++++-----------
 rsvg_internals/src/link.rs                       |  3 +-
 rsvg_internals/src/marker.rs                     |  3 +-
 rsvg_internals/src/mask.rs                       |  3 +-
 rsvg_internals/src/node.rs                       | 26 +++++++++----
 rsvg_internals/src/pattern.rs                    |  3 +-
 rsvg_internals/src/shapes.rs                     | 13 +++----
 rsvg_internals/src/stop.rs                       |  3 +-
 rsvg_internals/src/structure.rs                  | 13 +++----
 rsvg_internals/src/style.rs                      |  3 +-
 rsvg_internals/src/text.rs                       |  9 ++---
 rsvg_internals/src/xml.rs                        |  6 ++-
 32 files changed, 115 insertions(+), 199 deletions(-)
---
diff --git a/rsvg_internals/src/clip_path.rs b/rsvg_internals/src/clip_path.rs
index 77afc9f2..78000cc2 100644
--- a/rsvg_internals/src/clip_path.rs
+++ b/rsvg_internals/src/clip_path.rs
@@ -6,7 +6,6 @@ use attributes::Attribute;
 use coord_units::CoordUnits;
 use drawing_ctx::DrawingCtx;
 use error::RenderingError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::ParseValue;
 use property_bag::PropertyBag;
@@ -79,7 +78,7 @@ impl NodeClipPath {
 }
 
 impl NodeTrait for NodeClipPath {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::ClipPathUnits => self.units.set(attr.parse(value, ())?),
diff --git a/rsvg_internals/src/filters/blend.rs b/rsvg_internals/src/filters/blend.rs
index 0016b311..0a713447 100644
--- a/rsvg_internals/src/filters/blend.rs
+++ b/rsvg_internals/src/filters/blend.rs
@@ -5,7 +5,6 @@ use cairo;
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::ParseError;
 use property_bag::PropertyBag;
@@ -45,13 +44,8 @@ impl Blend {
 }
 
 impl NodeTrait for Blend {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/color_matrix.rs b/rsvg_internals/src/filters/color_matrix.rs
index 112d892c..9bba598a 100644
--- a/rsvg_internals/src/filters/color_matrix.rs
+++ b/rsvg_internals/src/filters/color_matrix.rs
@@ -6,7 +6,6 @@ use nalgebra::{Matrix3, Matrix4x5, Matrix5, Vector5};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, ListLength, NumberListError, ParseError};
 use property_bag::PropertyBag;
@@ -48,13 +47,8 @@ impl ColorMatrix {
 }
 
 impl NodeTrait for ColorMatrix {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         // First, determine the operation type.
         let mut operation_type = OperationType::Matrix;
diff --git a/rsvg_internals/src/filters/component_transfer.rs 
b/rsvg_internals/src/filters/component_transfer.rs
index 40cfa0b5..b76b9af4 100644
--- a/rsvg_internals/src/filters/component_transfer.rs
+++ b/rsvg_internals/src/filters/component_transfer.rs
@@ -6,7 +6,6 @@ use cairo::{self, ImageSurface};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, NodeType, RsvgNode};
 use parsers::{self, ListLength, NumberListError, ParseError};
 use property_bag::PropertyBag;
@@ -203,19 +202,14 @@ impl FuncX {
 
 impl NodeTrait for ComponentTransfer {
     #[inline]
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)
     }
 }
 
 impl NodeTrait for FuncX {
     #[inline]
-    fn set_atts(&self, _node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Type => self.function_type.set(FunctionType::parse(attr, value)?),
diff --git a/rsvg_internals/src/filters/composite.rs b/rsvg_internals/src/filters/composite.rs
index 8dde21da..6a0f2c87 100644
--- a/rsvg_internals/src/filters/composite.rs
+++ b/rsvg_internals/src/filters/composite.rs
@@ -6,7 +6,6 @@ use cssparser::{CowRcStr, Parser, Token};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::{NodeError, ValueErrorKind};
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, Parse, ParseValue};
 use property_bag::PropertyBag;
@@ -62,13 +61,8 @@ impl Composite {
 }
 
 impl NodeTrait for Composite {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/convolve_matrix.rs b/rsvg_internals/src/filters/convolve_matrix.rs
index 9490eaf7..b4047dc9 100644
--- a/rsvg_internals/src/filters/convolve_matrix.rs
+++ b/rsvg_internals/src/filters/convolve_matrix.rs
@@ -6,7 +6,6 @@ use nalgebra::{DMatrix, Dynamic, MatrixVec};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, ListLength, NumberListError, ParseError};
 use property_bag::PropertyBag;
@@ -57,13 +56,8 @@ impl ConvolveMatrix {
 }
 
 impl NodeTrait for ConvolveMatrix {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/displacement_map.rs b/rsvg_internals/src/filters/displacement_map.rs
index a01b59db..385f63c5 100644
--- a/rsvg_internals/src/filters/displacement_map.rs
+++ b/rsvg_internals/src/filters/displacement_map.rs
@@ -5,7 +5,6 @@ use cairo::{self, ImageSurface, MatrixTrait};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, ParseError};
 use property_bag::PropertyBag;
@@ -47,13 +46,8 @@ impl DisplacementMap {
 }
 
 impl NodeTrait for DisplacementMap {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/flood.rs b/rsvg_internals/src/filters/flood.rs
index d32e53aa..1355b4ff 100644
--- a/rsvg_internals/src/filters/flood.rs
+++ b/rsvg_internals/src/filters/flood.rs
@@ -2,7 +2,6 @@ use cairo::{self, ImageSurface};
 use cssparser;
 
 use drawing_ctx::DrawingCtx;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use property_bag::PropertyBag;
 use surface_utils::shared_surface::{SharedImageSurface, SurfaceType};
@@ -27,13 +26,8 @@ impl Flood {
 
 impl NodeTrait for Flood {
     #[inline]
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)
     }
 }
 
diff --git a/rsvg_internals/src/filters/gaussian_blur.rs b/rsvg_internals/src/filters/gaussian_blur.rs
index c895b416..6b330aec 100644
--- a/rsvg_internals/src/filters/gaussian_blur.rs
+++ b/rsvg_internals/src/filters/gaussian_blur.rs
@@ -8,7 +8,6 @@ use nalgebra::{DMatrix, Dynamic, MatrixVec};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers;
 use property_bag::PropertyBag;
@@ -44,13 +43,8 @@ impl GaussianBlur {
 }
 
 impl NodeTrait for GaussianBlur {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/image.rs b/rsvg_internals/src/filters/image.rs
index b6cb9ae6..ee4f79a7 100644
--- a/rsvg_internals/src/filters/image.rs
+++ b/rsvg_internals/src/filters/image.rs
@@ -180,13 +180,8 @@ impl Image {
 }
 
 impl NodeTrait for Image {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
@@ -199,6 +194,10 @@ impl NodeTrait for Image {
             }
         }
 
+        Ok(())
+    }
+
+    fn resolve_resources(&self, load_options: &LoadOptions) -> NodeResult {
         *self.load_options.borrow_mut() = Some(load_options.clone());
 
         Ok(())
diff --git a/rsvg_internals/src/filters/light/light_source.rs 
b/rsvg_internals/src/filters/light/light_source.rs
index 0a118933..96724bb7 100644
--- a/rsvg_internals/src/filters/light/light_source.rs
+++ b/rsvg_internals/src/filters/light/light_source.rs
@@ -7,7 +7,6 @@ use nalgebra::Vector3;
 use attributes::Attribute;
 use error::NodeError;
 use filters::context::FilterContext;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers;
 use property_bag::PropertyBag;
@@ -201,7 +200,7 @@ impl TransformedLightSource {
 }
 
 impl NodeTrait for LightSource {
-    fn set_atts(&self, _node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match self {
                 LightSource::Distant {
diff --git a/rsvg_internals/src/filters/light/lighting.rs b/rsvg_internals/src/filters/light/lighting.rs
index 9fed94be..d3580d2c 100644
--- a/rsvg_internals/src/filters/light/lighting.rs
+++ b/rsvg_internals/src/filters/light/lighting.rs
@@ -29,7 +29,6 @@ use filters::{
     FilterError,
     PrimitiveWithInput,
 };
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, NodeType, RsvgNode};
 use parsers;
 use property_bag::PropertyBag;
@@ -98,13 +97,8 @@ impl Lighting {
 }
 
 impl NodeTrait for Lighting {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/merge.rs b/rsvg_internals/src/filters/merge.rs
index 8954e510..0765933b 100644
--- a/rsvg_internals/src/filters/merge.rs
+++ b/rsvg_internals/src/filters/merge.rs
@@ -4,7 +4,6 @@ use cairo::{self, ImageSurface};
 
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, NodeType, RsvgNode};
 use property_bag::PropertyBag;
 use rect::IRect;
@@ -46,19 +45,14 @@ impl MergeNode {
 
 impl NodeTrait for Merge {
     #[inline]
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)
     }
 }
 
 impl NodeTrait for MergeNode {
     #[inline]
-    fn set_atts(&self, _node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::In => {
diff --git a/rsvg_internals/src/filters/mod.rs b/rsvg_internals/src/filters/mod.rs
index c4e9ca94..f8633107 100644
--- a/rsvg_internals/src/filters/mod.rs
+++ b/rsvg_internals/src/filters/mod.rs
@@ -9,7 +9,6 @@ use attributes::Attribute;
 use coord_units::CoordUnits;
 use drawing_ctx::DrawingCtx;
 use error::{RenderingError, ValueErrorKind};
-use handle::LoadOptions;
 use length::{Length, LengthDir, LengthUnit};
 use node::{NodeResult, NodeTrait, NodeType, RsvgNode};
 use parsers::{ParseError, ParseValue};
@@ -111,7 +110,7 @@ impl Primitive {
 }
 
 impl NodeTrait for Primitive {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // With ObjectBoundingBox, only fractions and percents are allowed.
         let primitiveunits = node
             .get_parent()
@@ -193,13 +192,8 @@ impl PrimitiveWithInput {
 }
 
 impl NodeTrait for PrimitiveWithInput {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/morphology.rs b/rsvg_internals/src/filters/morphology.rs
index bc511a70..a168c916 100644
--- a/rsvg_internals/src/filters/morphology.rs
+++ b/rsvg_internals/src/filters/morphology.rs
@@ -6,7 +6,6 @@ use cairo::{self, ImageSurface, MatrixTrait};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, ParseError};
 use property_bag::PropertyBag;
@@ -49,13 +48,8 @@ impl Morphology {
 }
 
 impl NodeTrait for Morphology {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/node.rs b/rsvg_internals/src/filters/node.rs
index 88d7f600..e68c3d51 100644
--- a/rsvg_internals/src/filters/node.rs
+++ b/rsvg_internals/src/filters/node.rs
@@ -4,7 +4,6 @@ use std::cell::Cell;
 use attributes::Attribute;
 use coord_units::CoordUnits;
 use error::ValueErrorKind;
-use handle::LoadOptions;
 use length::{Length, LengthDir, LengthUnit};
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{Parse, ParseError, ParseValue};
@@ -36,7 +35,7 @@ impl NodeFilter {
 }
 
 impl NodeTrait for NodeFilter {
-    fn set_atts(&self, _node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // Parse filterUnits first as it affects x, y, width, height checks.
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/offset.rs b/rsvg_internals/src/filters/offset.rs
index 194b5164..133999ec 100644
--- a/rsvg_internals/src/filters/offset.rs
+++ b/rsvg_internals/src/filters/offset.rs
@@ -5,7 +5,6 @@ use cairo::{self, ImageSurface, MatrixTrait};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers;
 use property_bag::PropertyBag;
@@ -36,13 +35,8 @@ impl Offset {
 }
 
 impl NodeTrait for Offset {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/filters/tile.rs b/rsvg_internals/src/filters/tile.rs
index a4512cf0..76d8fa30 100644
--- a/rsvg_internals/src/filters/tile.rs
+++ b/rsvg_internals/src/filters/tile.rs
@@ -1,7 +1,6 @@
 use cairo::{self, ImageSurface, Matrix, MatrixTrait, PatternTrait};
 
 use drawing_ctx::DrawingCtx;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use property_bag::PropertyBag;
 use surface_utils::shared_surface::SharedImageSurface;
@@ -25,13 +24,8 @@ impl Tile {
 }
 
 impl NodeTrait for Tile {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)
     }
 }
 
diff --git a/rsvg_internals/src/filters/turbulence.rs b/rsvg_internals/src/filters/turbulence.rs
index 000637fe..622a2f51 100644
--- a/rsvg_internals/src/filters/turbulence.rs
+++ b/rsvg_internals/src/filters/turbulence.rs
@@ -5,7 +5,6 @@ use cairo::{self, ImageSurface, MatrixTrait};
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::NodeError;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{self, ParseError};
 use property_bag::PropertyBag;
@@ -61,13 +60,8 @@ impl Turbulence {
 
 impl NodeTrait for Turbulence {
     #[inline]
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
-        self.base.set_atts(node, load_options, pbag)?;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
+        self.base.set_atts(node, pbag)?;
 
         for (attr, value) in pbag.iter() {
             match attr {
diff --git a/rsvg_internals/src/gradient.rs b/rsvg_internals/src/gradient.rs
index 5ece9427..b79179f4 100644
--- a/rsvg_internals/src/gradient.rs
+++ b/rsvg_internals/src/gradient.rs
@@ -9,7 +9,6 @@ use coord_units::CoordUnits;
 use defs::Fragment;
 use drawing_ctx::{AcquiredNode, DrawingCtx, NodeStack};
 use error::*;
-use handle::LoadOptions;
 use length::*;
 use node::*;
 use paint_server::PaintSource;
@@ -658,7 +657,7 @@ impl NodeGradient {
 }
 
 impl NodeTrait for NodeGradient {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         let mut g = self.gradient.borrow_mut();
 
         let mut x1 = None;
diff --git a/rsvg_internals/src/image.rs b/rsvg_internals/src/image.rs
index 8f52e8aa..aa920667 100644
--- a/rsvg_internals/src/image.rs
+++ b/rsvg_internals/src/image.rs
@@ -21,6 +21,7 @@ pub struct NodeImage {
     y: Cell<Length>,
     w: Cell<Length>,
     h: Cell<Length>,
+    href: RefCell<Option<Href>>,
     surface: RefCell<Option<cairo::ImageSurface>>,
 }
 
@@ -32,18 +33,14 @@ impl NodeImage {
             y: Cell::new(Length::default()),
             w: Cell::new(Length::default()),
             h: Cell::new(Length::default()),
+            href: RefCell::new(None),
             surface: RefCell::new(None),
         }
     }
 }
 
 impl NodeTrait for NodeImage {
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // SVG element has overflow:hidden
         // https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
         node.set_overflow_hidden();
@@ -68,21 +65,10 @@ impl NodeTrait for NodeImage {
                 // "path" is used by some older Adobe Illustrator versions
                 Attribute::XlinkHref | Attribute::Path => {
                     // FIXME: use better errors here; these should be loading errors
-
-                    let href = Href::without_fragment(value)
-                        .map_err(|_| NodeError::value_error(attr, "fragment not allowed here"))?;
-
-                    let url = match href {
-                        Href::PlainUri(u) => u,
-                        _ => unreachable!(),
-                    };
-
-                    *self.surface.borrow_mut() = Some(
-                        // FIXME: translate the error better here
-                        handle::load_image_to_surface(load_options, &url).map_err(|e| {
-                            NodeError::value_error(attr, &format!("could not load image: {}", e))
-                        })?,
-                    );
+                    *self.href.borrow_mut() =
+                        Some(Href::without_fragment(value).map_err(|_| {
+                            NodeError::value_error(attr, "fragment not allowed here")
+                        })?);
                 }
 
                 _ => (),
@@ -92,6 +78,26 @@ impl NodeTrait for NodeImage {
         Ok(())
     }
 
+    fn resolve_resources(&self, load_options: &LoadOptions) -> NodeResult {
+        match *self.href.borrow() {
+            None => (),
+            Some(Href::PlainUri(ref url)) => {
+                *self.surface.borrow_mut() = Some(
+                    // FIXME: translate the error better here
+                    handle::load_image_to_surface(load_options, &url).map_err(|e| {
+                        NodeError::value_error(
+                            Attribute::XlinkHref,
+                            &format!("could not load image: {}", e),
+                        )
+                    })?,
+                );
+            }
+            _ => unreachable!(),
+        };
+
+        Ok(())
+    }
+
     fn draw(
         &self,
         node: &RsvgNode,
diff --git a/rsvg_internals/src/link.rs b/rsvg_internals/src/link.rs
index d25bf6fc..991fe66e 100644
--- a/rsvg_internals/src/link.rs
+++ b/rsvg_internals/src/link.rs
@@ -10,7 +10,6 @@ use std::cell::RefCell;
 use attributes::Attribute;
 use drawing_ctx::DrawingCtx;
 use error::RenderingError;
-use handle::LoadOptions;
 use node::*;
 use property_bag::PropertyBag;
 
@@ -27,7 +26,7 @@ impl NodeLink {
 }
 
 impl NodeTrait for NodeLink {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::XlinkHref => *self.link.borrow_mut() = Some(value.to_owned()),
diff --git a/rsvg_internals/src/marker.rs b/rsvg_internals/src/marker.rs
index 4cd702f9..e7c054dd 100644
--- a/rsvg_internals/src/marker.rs
+++ b/rsvg_internals/src/marker.rs
@@ -12,7 +12,6 @@ use defs::Fragment;
 use drawing_ctx::DrawingCtx;
 use error::*;
 use float_eq_cairo::ApproxEqCairo;
-use handle::LoadOptions;
 use iri::IRI;
 use length::{Length, LengthDir};
 use node::*;
@@ -207,7 +206,7 @@ impl NodeMarker {
 }
 
 impl NodeTrait for NodeMarker {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // marker element has overflow:hidden
         // https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
         node.set_overflow_hidden();
diff --git a/rsvg_internals/src/mask.rs b/rsvg_internals/src/mask.rs
index 75e52423..726e49e3 100644
--- a/rsvg_internals/src/mask.rs
+++ b/rsvg_internals/src/mask.rs
@@ -5,7 +5,6 @@ use attributes::Attribute;
 use coord_units::CoordUnits;
 use drawing_ctx::DrawingCtx;
 use error::RenderingError;
-use handle::LoadOptions;
 use length::{Length, LengthDir};
 use node::{NodeResult, NodeTrait, RsvgNode};
 use parsers::{Parse, ParseValue};
@@ -193,7 +192,7 @@ fn compute_luminance_to_alpha(
 }
 
 impl NodeTrait for NodeMask {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::X => self.x.set(attr.parse(value, LengthDir::Horizontal)?),
diff --git a/rsvg_internals/src/node.rs b/rsvg_internals/src/node.rs
index 58a2855b..b7866594 100644
--- a/rsvg_internals/src/node.rs
+++ b/rsvg_internals/src/node.rs
@@ -97,17 +97,18 @@ pub trait NodeTrait: Downcast {
     /// Sets per-node attributes from the `pbag`
     ///
     /// Each node is supposed to iterate the `pbag`, and parse any attributes it needs.
-    fn set_atts(
-        &self,
-        node: &RsvgNode,
-        load_options: &LoadOptions,
-        pbag: &PropertyBag<'_>,
-    ) -> NodeResult;
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult;
 
     /// Sets any special-cased properties that the node may have, that are different
     /// from defaults in the node's `State`.
     fn set_overridden_properties(&self, _state: &mut State) {}
 
+    /// Load resources specified in the attributes.
+    fn resolve_resources(&self, _load_options: &LoadOptions) -> NodeResult {
+        // Most of the nodes do not need to load resources
+        Ok(())
+    }
+
     fn draw(
         &self,
         _node: &RsvgNode,
@@ -348,7 +349,7 @@ impl Node {
         self.data.cond.get()
     }
 
-    pub fn set_atts(&self, node: &RsvgNode, load_options: &LoadOptions, pbag: &PropertyBag<'_>) {
+    pub fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Transform => match Matrix::parse_str(value, ()) {
@@ -371,7 +372,7 @@ impl Node {
             }
         }
 
-        match self.data.node_impl.set_atts(node, load_options, pbag) {
+        match self.data.node_impl.set_atts(node, pbag) {
             Ok(_) => (),
             Err(e) => {
                 self.set_error(e);
@@ -444,6 +445,15 @@ impl Node {
         }
     }
 
+    pub fn resolve_resources(&self, load_options: &LoadOptions) {
+        match self.data.node_impl.resolve_resources(load_options) {
+            Ok(_) => (),
+            Err(e) => {
+                self.set_error(e);
+            }
+        }
+    }
+
     /// Implements a very limited CSS selection engine
     fn set_css_styles(&self, css_styles: &CssStyles) {
         // Try to properly support all of the following, including inheritance:
diff --git a/rsvg_internals/src/pattern.rs b/rsvg_internals/src/pattern.rs
index 17802f9f..892fac06 100644
--- a/rsvg_internals/src/pattern.rs
+++ b/rsvg_internals/src/pattern.rs
@@ -13,7 +13,6 @@ use defs::Fragment;
 use drawing_ctx::{DrawingCtx, NodeStack};
 use error::{AttributeResultExt, RenderingError};
 use float_eq_cairo::ApproxEqCairo;
-use handle::LoadOptions;
 use length::*;
 use node::*;
 use paint_server::PaintSource;
@@ -173,7 +172,7 @@ impl NodePattern {
 }
 
 impl NodeTrait for NodePattern {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // pattern element has overflow:hidden
         // https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
         node.set_overflow_hidden();
diff --git a/rsvg_internals/src/shapes.rs b/rsvg_internals/src/shapes.rs
index 4579cd91..759565f6 100644
--- a/rsvg_internals/src/shapes.rs
+++ b/rsvg_internals/src/shapes.rs
@@ -7,7 +7,6 @@ use attributes::Attribute;
 use cssparser::{Parser, Token};
 use drawing_ctx::DrawingCtx;
 use error::*;
-use handle::LoadOptions;
 use length::*;
 use marker;
 use node::*;
@@ -125,7 +124,7 @@ impl NodePath {
 }
 
 impl NodeTrait for NodePath {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             if attr == Attribute::D {
                 let mut builder = PathBuilder::new();
@@ -234,7 +233,7 @@ impl NodePoly {
 }
 
 impl NodeTrait for NodePoly {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             // support for svg < 1.0 which used verts
             if attr == Attribute::Points || attr == Attribute::Verts {
@@ -295,7 +294,7 @@ impl NodeLine {
 }
 
 impl NodeTrait for NodeLine {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::X1 => self.x1.set(attr.parse(value, LengthDir::Horizontal)?),
@@ -361,7 +360,7 @@ impl NodeRect {
 }
 
 impl NodeTrait for NodeRect {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::X => self.x.set(attr.parse(value, LengthDir::Horizontal)?),
@@ -561,7 +560,7 @@ impl NodeCircle {
 }
 
 impl NodeTrait for NodeCircle {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Cx => self.cx.set(attr.parse(value, LengthDir::Horizontal)?),
@@ -617,7 +616,7 @@ impl NodeEllipse {
 }
 
 impl NodeTrait for NodeEllipse {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Cx => self.cx.set(attr.parse(value, LengthDir::Horizontal)?),
diff --git a/rsvg_internals/src/stop.rs b/rsvg_internals/src/stop.rs
index 13994dee..8b549ba7 100644
--- a/rsvg_internals/src/stop.rs
+++ b/rsvg_internals/src/stop.rs
@@ -2,7 +2,6 @@ use std::cell::Cell;
 
 use attributes::Attribute;
 use error::*;
-use handle::LoadOptions;
 use length::*;
 use node::*;
 use parsers::ParseValue;
@@ -35,7 +34,7 @@ fn validate_offset(length: Length) -> Result<Length, ValueErrorKind> {
 }
 
 impl NodeTrait for NodeStop {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::Offset => {
diff --git a/rsvg_internals/src/structure.rs b/rsvg_internals/src/structure.rs
index fd4dc584..57c772f8 100644
--- a/rsvg_internals/src/structure.rs
+++ b/rsvg_internals/src/structure.rs
@@ -9,7 +9,6 @@ use dpi::Dpi;
 use drawing_ctx::DrawingCtx;
 use error::{AttributeResultExt, RenderingError};
 use float_eq_cairo::ApproxEqCairo;
-use handle::LoadOptions;
 use length::*;
 use node::*;
 use parsers::{Parse, ParseValue};
@@ -27,7 +26,7 @@ impl NodeGroup {
 }
 
 impl NodeTrait for NodeGroup {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, _: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, _: &PropertyBag<'_>) -> NodeResult {
         Ok(())
     }
 
@@ -55,7 +54,7 @@ impl NodeDefs {
 }
 
 impl NodeTrait for NodeDefs {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, _: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, _: &PropertyBag<'_>) -> NodeResult {
         Ok(())
     }
 }
@@ -69,7 +68,7 @@ impl NodeSwitch {
 }
 
 impl NodeTrait for NodeSwitch {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, _: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, _: &PropertyBag<'_>) -> NodeResult {
         Ok(())
     }
 
@@ -147,7 +146,7 @@ impl NodeSvg {
 }
 
 impl NodeTrait for NodeSvg {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // SVG element has overflow:hidden
         // https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
         node.set_overflow_hidden();
@@ -260,7 +259,7 @@ impl NodeUse {
 }
 
 impl NodeTrait for NodeUse {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::XlinkHref => {
@@ -415,7 +414,7 @@ impl NodeSymbol {
 }
 
 impl NodeTrait for NodeSymbol {
-    fn set_atts(&self, node: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, node: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         // symbol element has overflow:hidden
         // https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
         node.set_overflow_hidden();
diff --git a/rsvg_internals/src/style.rs b/rsvg_internals/src/style.rs
index acb2033e..e201e9d6 100644
--- a/rsvg_internals/src/style.rs
+++ b/rsvg_internals/src/style.rs
@@ -1,5 +1,4 @@
 use attributes::Attribute;
-use handle::LoadOptions;
 use node::{NodeResult, NodeTrait, NodeType, RsvgNode};
 use property_bag::PropertyBag;
 use text::NodeChars;
@@ -56,7 +55,7 @@ impl NodeStyle {
 }
 
 impl NodeTrait for NodeStyle {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             if attr == Attribute::Type {
                 *self.type_.borrow_mut() = Some(value.to_string());
diff --git a/rsvg_internals/src/text.rs b/rsvg_internals/src/text.rs
index 23b7916b..436cda91 100644
--- a/rsvg_internals/src/text.rs
+++ b/rsvg_internals/src/text.rs
@@ -11,7 +11,6 @@ use drawing_ctx::DrawingCtx;
 use error::{AttributeResultExt, RenderingError};
 use float_eq_cairo::ApproxEqCairo;
 use font_props::FontWeightSpec;
-use handle::LoadOptions;
 use length::*;
 use node::{CascadedValues, NodeResult, NodeTrait, NodeType, RsvgNode};
 use parsers::ParseValue;
@@ -542,7 +541,7 @@ impl NodeChars {
 }
 
 impl NodeTrait for NodeChars {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, _: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, _: &PropertyBag<'_>) -> NodeResult {
         Ok(())
     }
 }
@@ -585,7 +584,7 @@ impl NodeText {
 }
 
 impl NodeTrait for NodeText {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::X => self.x.set(attr.parse(value, LengthDir::Horizontal)?),
@@ -710,7 +709,7 @@ fn extract_chars_children_to_chunks_recursively(
 }
 
 impl NodeTrait for NodeTRef {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::XlinkHref => {
@@ -766,7 +765,7 @@ impl NodeTSpan {
 }
 
 impl NodeTrait for NodeTSpan {
-    fn set_atts(&self, _: &RsvgNode, _: &LoadOptions, pbag: &PropertyBag<'_>) -> NodeResult {
+    fn set_atts(&self, _: &RsvgNode, pbag: &PropertyBag<'_>) -> NodeResult {
         for (attr, value) in pbag.iter() {
             match attr {
                 Attribute::X => self
diff --git a/rsvg_internals/src/xml.rs b/rsvg_internals/src/xml.rs
index b063360a..5b36b3ce 100644
--- a/rsvg_internals/src/xml.rs
+++ b/rsvg_internals/src/xml.rs
@@ -335,7 +335,7 @@ impl XmlState {
             parent.add_child(&new_node);
         }
 
-        new_node.set_atts(&new_node, &handle::get_load_options(self.handle), pbag);
+        new_node.set_atts(&new_node, pbag);
 
         // The "svg" node is special; it will parse its style attributes
         // until the end, in standard_element_end().
@@ -345,6 +345,10 @@ impl XmlState {
 
         new_node.set_overridden_properties();
 
+        // For now we load resources directly when parsing, but probably we should
+        // move this to a trasversal of the tree once we finished parsing
+        new_node.resolve_resources(&handle::get_load_options(self.handle));
+
         new_node
     }
 



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