喜欢 this other question我很难用 XSLT1 表达简单的东西...
在 xsl:stylesheet
中,我有这个“identity like”转换以将属性 align="center"
添加到 TD
标记中与其他属性更多(必须留在那里)... 添加 align
的触发器是在标签 TD
中存在标签 CENTER
. (稍后标签 CENTER
将被删除)。
<xsl:template match="@*|node()" name="identity">
<xsl:copy>
<xsl:if test="name()='td' and .//center">
<xsl:attribute name="align">center</xsl:attribute>
</xsl:if>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
此代码不工作(xsl:if
被忽略)。
需要td//center
,不仅需要td/center
,也不需要td/p/center
。必须是通用的,对于任何 td//center
。输入示例:
<td colspan="2">
<p><center>POF</center></p>
</td>
最佳答案
来自问题评论:
The problem now:
<td align="x"><p><center>
is not changed, only<td><p><center>
那是因为您要添加一个 align
属性使用
<xsl:attribute name="align">center</xsl:attribute>
但也复制现有的
<xsl:apply-templates select="@*|node()"/>
当您尝试将两个具有相同名称的属性添加到同一元素时,第二个添加的属性(在本例中是从输入元素复制的属性)将获胜。
我肯定会将逻辑拆分到单独的模板中:
<!-- copy everything as-is except for more specific templates below -->
<xsl:template match="@*|node()">
<xsl:copy>
<xsl:apply-templates select="@*|node()"/>
</xsl:copy>
</xsl:template>
<!-- add align="center" to any td with a <center> descendant -->
<xsl:template match="td[.//center]">
<td align="center">
<!-- ignore any existing align attribute on the input td -->
<xsl:apply-templates select="@*[local-name() != 'align'] | node()" />
</td>
</xsl:template>
<!-- remove any <center> that's inside a td, but keep processing its children -->
<xsl:template match="td//center">
<xsl:apply-templates />
</xsl:template>
这会改变
<td colspan="2" align="left">
<p><center>POF</center></p>
</td>
进入
<td align="center" colspan="2">
<p>POF</p>
</td>
请注意它是 td[.//center]
- 一个 td
具有 center
的元素元素后代 - 不同于 td[//center]
- 一个 td
在包含任何 center
的文档中出现的元素其中任何位置的元素(不一定在 td
内)。
关于algorithm - 如何在 XSLT 1 中使用身份转换将属性添加到以子元素为条件的父节点?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18078679/