XSLT: вставка узлов в корень файла SVG - PullRequest
0 голосов
/ 09 февраля 2019

Моя цель - добавить два узла <style> и <whatever> в мой SVG-файл, используя XSLT ниже, но я столкнулся с двумя проблемами.Во-первых, при добавлении <style> он включает три атрибута xmlns, которые мне не нужны:

<style xmlns=""
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:svg="http://www.w3.org/2000/svg">.val{--valence: #4599a3}</style>

Затем он не добавляет мой второй узел <whatever>.

. Как это сделать?Я это исправлю?

<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet xmlns:xsl='http://www.w3.org/1999/XSL/Transform' xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' xmlns:svg="http://www.w3.org/2000/svg" version='1.0'>

    <!-- this template is applied by default to all nodes and attributes -->
    <xsl:template match="@*|node()">
        <!-- just copy all my attributes and child nodes, except if there's a better template for some of them -->
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>

   <xsl:template match="svg:title">
      <xsl:copy-of select="."/>
      <style>.val{--valence: #4599a3}</style>
   </xsl:template>

    <xsl:template match="svg:title">
        <xsl:copy-of select="."/>
        <whatever>foo</whatever>
    </xsl:template>

    <xsl:template match="svg:defs/svg:circle">
        <xsl:copy>
            <xsl:copy-of select="@*"/>
            <xsl:attribute name="style">fill: var(--valence, #47565b)</xsl:attribute>
        </xsl:copy>
    </xsl:template>

</xsl:stylesheet>

Ответы [ 2 ]

0 голосов
/ 09 февраля 2019

Если вы хотите добавить элементы в пространство имен SVG, вам нужно использовать его, поэтому, если предполагается, что вся таблица стилей создает элементы SVG, и вы уже объявили ее в корневом элементе, как вы это сделали с

<xsl:stylesheet xmlns:xsl='http://www.w3.org/1999/XSL/Transform' xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance' xmlns:svg="http://www.w3.org/2000/svg" version='1.0'>

вы можете создать элемент SVG style, используя svg:style:

   <xsl:template match="svg:title">
      <xsl:copy-of select="."/>
      <svg:style>.val{--valence: #4599a3}</svg:style>
   </xsl:template>

В качестве альтернативы вы можете поместить объявление пространства имен по умолчанию xmlns="http://www.w3.org/2000/svg" в корневой элемент таблицы стилей, например

<xsl:stylesheet 
  xmlns:xsl='http://www.w3.org/1999/XSL/Transform'
  xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'
  xmlns:svg="http://www.w3.org/2000/svg"
  xmlns="http://www.w3.org/2000/svg"
  version='1.0'>

  ..
   <xsl:template match="svg:title">
      <xsl:copy-of select="."/>
      <style>.val{--valence: #4599a3}</style>
   </xsl:template>

xsl:element не требуется.

Что касается других объявлений пространства имен, которые вы объявляете в корневом элементе для выражений XPath или шаблонов сопоставления XSLT, но не хотите использовать дляэлементы результата, вы можете использовать атрибут exclude-result-prefixes на xsl:stylesheet / xsl:transform например exclude-result-prefixes="xsi svg"

<xsl:stylesheet 
      xmlns:xsl='http://www.w3.org/1999/XSL/Transform'
      xmlns:xsi='http://www.w3.org/2001/XMLSchema-instance'
      xmlns:svg="http://www.w3.org/2000/svg"
      xmlns="http://www.w3.org/2000/svg"
      exclude-result-prefixes="xsi svg"
      version='1.0'>

    <!-- this template is applied by default to all nodes and attributes -->
    <xsl:template match="@*|node()">
        <!-- just copy all my attributes and child nodes, except if there's a better template for some of them -->
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>

   <xsl:template match="svg:title">
      <xsl:copy-of select="."/>
      <style>.val{--valence: #4599a3}</style>
   </xsl:template>

</xsl:stylesheet>

https://xsltfiddle.liberty -development.net / gWvjQeY

0 голосов
/ 09 февраля 2019
  1. Пространства имен наследуются.Чтобы избавиться от них, вам нужно установить другое пространство имен или пустое пространство имен (создавая xmlns="", что означает отсутствие пространства имен / пустое пространство имен).Чтобы удалить

    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:svg="http://www.w3.org/2000/svg"
    

    Один из способов решения этой проблемы - явное определение элемента с помощью xsl:element:

    <xsl:element name="whatever" namespace="">foo</xsl:element>
    

    . Теперь у вас остается только xmlns="" наэлемент.Чтобы также удалить это, установите пространство имен в пространство имен по умолчанию - здесь, вероятно, http://www.w3.org/2000/svg

    <xsl:element name="whatever" namespace="http://www.w3.org/2000/svg">foo</xsl:element>
    

    Теперь элемент выглядит как <whatever>foo</whatever>, но помните, что он на самом деле имеет унаследованное пространство имен по умолчанию.

  2. Тогда мой второй узел не добавляется <whatever>.

    Это происходит потому, что у вас есть два шаблона с одинаковым правилом сопоставления match="svg:title".Сделайте соответствующие правила уникальными, и это будет работать.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...