summaryrefslogtreecommitdiff
path: root/svgio
diff options
context:
space:
mode:
authorXisco Fauli <xiscofauli@libreoffice.org>2024-05-06 17:15:59 +0200
committerAndras Timar <andras.timar@collabora.com>2024-06-03 14:31:32 +0200
commitab33c8f661c3ecafd97c7eef74a333dbb4d2e0a6 (patch)
tree25e193d8cc07ff1e78f6ade8c9af19e35f81d6ac /svgio
parenta05ee9324fa4bd54f25b85f268e29c5d478e6980 (diff)
tdf#155651: Add support for "context-fill"
Change-Id: I6f96cc7c059ece5f9401fc0ae552cf279e53109c Reviewed-on: https://gerrit.libreoffice.org/c/core/+/167230 Reviewed-by: Xisco Fauli <xiscofauli@libreoffice.org> Tested-by: Jenkins (cherry picked from commit 3b0f96a0773f19f7d5bdb5725ff9667eb4809215) Reviewed-on: https://gerrit.libreoffice.org/c/core/+/167218 Reviewed-by: Caolán McNamara <caolan.mcnamara@collabora.com>
Diffstat (limited to 'svgio')
-rw-r--r--svgio/inc/svgstyleattributes.hxx7
-rw-r--r--svgio/qa/cppunit/SvgImportTest.cxx8
-rw-r--r--svgio/qa/cppunit/data/contextFill.svg8
-rw-r--r--svgio/source/svgreader/svgstyleattributes.cxx36
4 files changed, 57 insertions, 2 deletions
diff --git a/svgio/inc/svgstyleattributes.hxx b/svgio/inc/svgstyleattributes.hxx
index 61a3816e82cb..30cbab965644 100644
--- a/svgio/inc/svgstyleattributes.hxx
+++ b/svgio/inc/svgstyleattributes.hxx
@@ -247,6 +247,9 @@ namespace svgio::svgreader
// #121221# Defines if evtl. an empty array *is* set
bool mbStrokeDasharraySet : 1;
+ // tdf#155651 Defines if 'context-fill' is used in fill
+ bool mbContextFill : 1;
+
// tdf#155651 Defines if 'context-stroke' is used in stroke
bool mbContextStroke : 1;
@@ -254,6 +257,7 @@ namespace svgio::svgreader
OUString maNodeFillURL;
OUString maNodeStrokeURL;
+ const basegfx::BColor* maContextFill;
const basegfx::BColor* maContextStroke;
/// internal helpers
@@ -332,6 +336,9 @@ namespace svgio::svgreader
/// stroke content
const basegfx::BColor* getStroke() const;
+ /// context fill content
+ const basegfx::BColor* getContextFill() const;
+
/// context stroke content
const basegfx::BColor* getContextStroke() const;
diff --git a/svgio/qa/cppunit/SvgImportTest.cxx b/svgio/qa/cppunit/SvgImportTest.cxx
index 48b8d89bfeee..5214319f59ff 100644
--- a/svgio/qa/cppunit/SvgImportTest.cxx
+++ b/svgio/qa/cppunit/SvgImportTest.cxx
@@ -685,6 +685,14 @@ CPPUNIT_TEST_FIXTURE(Test, testMarkerOrient)
assertXPath(pDocument, "/primitive2D/transform/transform[2]"_ostr, "xy33"_ostr, "1");
}
+CPPUNIT_TEST_FIXTURE(Test, testContextFill)
+{
+ xmlDocUniquePtr pDocument = dumpAndParseSvg(u"/svgio/qa/cppunit/data/contextFill.svg");
+
+ assertXPath(pDocument, "/primitive2D/transform/polypolygonstroke/line"_ostr, "color"_ostr, "#ff0000");
+ assertXPath(pDocument, "/primitive2D/transform/transform/polypolygoncolor"_ostr, "color"_ostr, "#ff0000");
+}
+
CPPUNIT_TEST_FIXTURE(Test, testContextStroke)
{
xmlDocUniquePtr pDocument = dumpAndParseSvg(u"/svgio/qa/cppunit/data/contextStroke.svg");
diff --git a/svgio/qa/cppunit/data/contextFill.svg b/svgio/qa/cppunit/data/contextFill.svg
new file mode 100644
index 000000000000..399d3c16b09e
--- /dev/null
+++ b/svgio/qa/cppunit/data/contextFill.svg
@@ -0,0 +1,8 @@
+<svg width="100" height="100" xmlns="http://www.w3.org/2000/svg">
+<defs>
+ <marker id="triangle" viewBox="0 0 10 10" refX="5" refY="5" markerWidth="6" markerHeight="6" orient="auto">
+ <path d="M 0 0 L 10 5 L 0 10 z" fill="context-fill" />
+ </marker>
+</defs>
+<line x1="10" y1="10" x2="90" y2="90" fill="red" stroke="red" marker-end="url(#triangle)" />
+</svg>
diff --git a/svgio/source/svgreader/svgstyleattributes.cxx b/svgio/source/svgreader/svgstyleattributes.cxx
index eee09889c226..42e19c51fcd5 100644
--- a/svgio/source/svgreader/svgstyleattributes.cxx
+++ b/svgio/source/svgreader/svgstyleattributes.cxx
@@ -817,6 +817,11 @@ namespace svgio::svgreader
rMarkerTransform.identity();
rClipRange.reset();
+ // Set the current fill to the marker before calling getMarkerPrimitives,
+ // which calls decomposeSvgNode to decompose the children of the marker.
+ // If any of the children uses 'fill="context-fill"', then it will use it
+ const_cast<SvgStyleAttributes*>(rMarker.getSvgStyleAttributes())->maContextFill = getFill();
+
// Set the current stroke to the marker before calling getMarkerPrimitives,
// which calls decomposeSvgNode to decompose the children of the marker.
// If any of the children uses 'stroke="context-stroke"', then it will use it
@@ -1292,9 +1297,11 @@ namespace svgio::svgreader
maBaselineShift(BaselineShift::Baseline),
maBaselineShiftNumber(0),
maDominantBaseline(DominantBaseline::Auto),
- maResolvingParent(33, 0),
+ maResolvingParent(34, 0),
mbStrokeDasharraySet(false),
+ mbContextFill(false),
mbContextStroke(false),
+ maContextFill(nullptr),
maContextStroke(nullptr)
{
}
@@ -1315,7 +1322,11 @@ namespace svgio::svgreader
OUString aURL;
SvgNumber aOpacity;
- if(readSvgPaint(aContent, aSvgPaint, aURL, aOpacity))
+ if(o3tl::equalsIgnoreAsciiCase(o3tl::trim(aContent), u"context-fill"))
+ {
+ mbContextFill = true;
+ }
+ else if(readSvgPaint(aContent, aSvgPaint, aURL, aOpacity))
{
setFill(aSvgPaint);
if(aOpacity.isSet())
@@ -2007,6 +2018,23 @@ namespace svgio::svgreader
}
}
+ const basegfx::BColor* SvgStyleAttributes::getContextFill() const
+ {
+ if (SVGToken::Marker == mrOwner.getType())
+ return maContextFill;
+
+ const SvgStyleAttributes* pSvgStyleAttributes = getParentStyle();
+ if (pSvgStyleAttributes && maResolvingParent[33] < nStyleDepthLimit)
+ {
+ ++maResolvingParent[33];
+ auto ret = pSvgStyleAttributes->getContextFill();
+ --maResolvingParent[33];
+ return ret;
+ }
+
+ return nullptr;
+ }
+
const basegfx::BColor* SvgStyleAttributes::getContextStroke() const
{
if (SVGToken::Marker == mrOwner.getType())
@@ -2092,6 +2120,10 @@ namespace svgio::svgreader
}
}
}
+ else if (mbContextFill)
+ {
+ return getContextFill();
+ }
else if (maNodeFillURL.isEmpty())
{
const SvgStyleAttributes* pSvgStyleAttributes = getParentStyle();