From 4b10b6d627d666e7a3d2febac3f149ddd494f1d4 Mon Sep 17 00:00:00 2001 From: Jeff Schiller Date: Mon, 26 Mar 2012 23:33:27 -0700 Subject: [PATCH] Fix nested defs problem and add unit test --- scour.py | 22 ++++++++++++++++++++++ testscour.py | 6 ++++++ unittests/nested-defs.svg | 14 ++++++++++++++ 3 files changed, 42 insertions(+) create mode 100644 unittests/nested-defs.svg diff --git a/scour.py b/scour.py index a3a8a74..9b40e99 100755 --- a/scour.py +++ b/scour.py @@ -565,6 +565,25 @@ numBytesSavedInTransforms = 0 numPointsRemovedFromPolygon = 0 numCommentBytes = 0 +def flattenDefs(doc): + """ + Puts all defined elements into a newly created defs in the document. This function + handles recursive defs elements. + """ + defs = doc.documentElement.getElementsByTagName('defs') + + if defs.length > 1: + topDef = doc.createElementNS(NS['SVG'], 'defs') + + for defElem in defs: + # Remove all children of this defs and put it into the topDef. + while defElem.hasChildNodes(): + topDef.appendChild(defElem.firstChild) + defElem.parentNode.removeChild(defElem) + + if topDef.hasChildNodes(): + doc.documentElement.insertBefore(topDef, doc.documentElement.firstChild) + def removeUnusedDefs(doc, defElem, elemsToRemove=None): if elemsToRemove is None: elemsToRemove = [] @@ -2887,6 +2906,9 @@ def scourString(in_string, options=None): if options.remove_metadata: removeMetadataElements(doc) + # flattend defs elements into just one defs element + flattenDefs(doc) + # remove unreferenced gradients/patterns outside of defs # and most unreferenced elements inside of defs while removeUnreferencedElements(doc) > 0: diff --git a/testscour.py b/testscour.py index bce1d13..0167875 100755 --- a/testscour.py +++ b/testscour.py @@ -172,6 +172,12 @@ class KeepTitleInDefs(unittest.TestCase): self.assertEquals(len(doc.getElementsByTagNameNS(SVGNS, 'title')), 1, 'Title removed from in defs' ) +class RemoveNestedDefs(unittest.TestCase): + def runTest(self): + doc = scour.scourXmlFile('unittests/nested-defs.svg') + allDefs = doc.getElementsByTagNameNS(SVGNS, 'defs') + self.assertEquals(len(allDefs), 1, 'More than one defs left in doc') + class KeepUnreferencedIDsWhenEnabled(unittest.TestCase): def runTest(self): doc = scour.scourXmlFile('unittests/ids-to-strip.svg') diff --git a/unittests/nested-defs.svg b/unittests/nested-defs.svg new file mode 100644 index 0000000..7091985 --- /dev/null +++ b/unittests/nested-defs.svg @@ -0,0 +1,14 @@ + + + + + + + + + + + + + +