【问题标题】:Add/remove xml field from svg file with bash使用 bash 从 svg 文件中添加/删除 xml 字段
【发布时间】:2015-05-28 00:04:05
【问题描述】:

我有一组 svg 图像,我想用 bash 脚本进行修改。特别是,我想通过保留其他路径从图像中删除特定路径。这是一个工作示例:

<path
  id="rect5505"
  d="M 118.34375,20 C ... z"
  style="fill:#4d8ecb;stroke:none;fill-opacity:1" />
<path
  style="fill:#000000;fill-opacity:0.23529412;stroke:none;display:inline"
  d="m ... z"
  id="path17954"
  sodipodi:nodetypes="ssccccccccccccssccccccs" />

在这种情况下,有两个path 元素,但我只想删除具有fill:#000000;fill-opacity:0.23529412 的元素。我知道我可以使用sed 来识别包含这些字段的行,但是如何删除整个path 字段?

我想强调这个问题不是Add/remove xml tags using a bash script 的重复,因为在那种情况下只有一个字段类型。通过使用类似的东西

sed -i '/<path/,/<\/>/d' image.svg

我会删除文件中的每一个路径,不是吗?

【问题讨论】:

  • 使用像 xmllint 这样的 xml 解析器
  • @DaveJarvis,Java 问题与这里有什么关系? (特别是因为这是可能的 - 甚至很容易 - 使用命令行可访问的工具稳健地完成,如 Wintermute 的回答)。

标签: xml bash svg sed


【解决方案1】:

使用 sed 编辑 XML 并不是一个非常好的主意。我的建议是使用xmlstarlet:

xmlstarlet ed -d '//path[contains(@style, "fill:#000000") and contains(@style, "fill-opacity:0.23529412")]' filename.xml

在哪里

xmlstarlet ed -d xpath filename.xml

filename.xml 中删除与给定 XPath 表达式匹配的元素,并且

//path[contains(@style, "fill:#000000") and contains(@style, "fill-opacity:0.23529412")]

是一个 XPath 表达式,它匹配所有具有style 属性的path 节点,该属性包含fill:#000000fill-opacity:0.23529412

附录: 因为contains() 进行简单的字符串比较,所以上面使用的XPath 表达式在某些极端情况下可能会产生误报。例如,如果 style 属性包含字符串 foo-fill:#000000 ,则 contains(@style, "fill:#000000") 将为真。解决这个特定问题的一种简单但有点笨拙的方法是使用

xmlstarlet ed -d '//path[contains(concat(";", @style, ";"), ";fill:#000000;") and contains(concat(";", @style, ";"), ";fill-opacity:0.23529412;")]' filename.xml

...尽管这仍然会留下空格的问题。我想一个完美的解决方案必须解析 CSS 和 XML,这需要更多的工作(可能还有 Perl 左右)。

附录 2: 看来我们有 namespace SNAFU。要解决这个问题,请使用

xmlstarlet ed -N svg='http://www.w3.org/2000/svg' -d '//svg:path[contains(@style, "fill:#000000") and contains(@style, "fill-opacity:0.23529412")]' accessibility.svg

即:

xmlstarlet ed -N svg='http://www.w3.org/2000/svg' -d xpath filename

xpath 修改为使用svg:path 而不是path。这是必要的,因为有一个属性

xmlns="http://www.w3.org/2000/svg"

在输入文件的svg 标记中,XPath 要求处理。

【讨论】:

  • 感谢@Wintermute 的建议。我正在尝试在此图像上使用它(众多图像之一):raw.githubusercontent.com/alecive/FlatWoken/master/FlatWoken/…。我想删除的路径在那里,但脚本给了我一个错误:None of the XPaths matched; to match a node in the default namespace use '_' as the prefix (see section 5.1 in the manual). For instance, use /_:node instead of /node
猜你喜欢
  • 2021-09-04
  • 1970-01-01
  • 2021-01-24
  • 2012-04-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多