我有一个问题,我需要从xml生成html,我可以有多个嵌套在彼此的标签。我如何通过递归传递它们?
以下是xml中的示例:
<rows>
<row>
<cell>1</cell>
<cell>2</cell>
<cell>1</cell>
<cell>2</cell>
<row>
<cell>3</cell>
<cell>4</cell>
<row>
<cell>5</cell>
<cell>6</cell>
<cell>6</cell>
</row>
</row>
</row>
</rows>
我的xslt是:
<table>
<th>1</th><th>2</th>3<th>4</th><th>5</th>
<xsl:for-each select="rows/row">
<tr>
<xsl:for-each select="cell">
<td>
<xsl:value-of select="."/>
</td>
</xsl:for-each>
</tr>
<xsl:for-each select="row">
<tr>
<xsl:for-each select="cell">
<td>
<xsl:value-of select="."/>
</td>
</xsl:for-each>
</tr>
</xsl:for-each>
</xsl:for-each>
</table>
所以我现在的问题是如何在每行显示所有属性?
编辑:从xslt生成的html
<html><body>
<table>
<th>1</th>
<th>2</th>
<th>3</th>
<th>4</th>
<th>5</th>
<tr>
<td>1</td>
<td>2</td>
<td>1</td>
<td>2</td>
</tr>
<tr>
<td>3</td>
<td>4</td>
</tr>
</table>
</body></html>
第二次编辑:
XSLT:
<xsl:template match="cell">
<td style="overflow:hidden;border:1px solid black;">
<div style="width:100px;height:20px;margin-bottom: 10px;margin-top: 10px;">
<xsl:variable name="id1" select="row/@id"/>
<xsl:if test="starts-with(id1, 'Dir')">
<xsl:value-of select="cell/@image"/>
</xsl:if>
<xsl:value-of select="."/>
</div>
</td>
</xsl:template>
的xml:
<row id="Dir_44630">
<cell>Text</cell>
<cell>1</cell>
<cell>1.00</cell>
<cell>3</cell>
<cell 4</cell>
<cell>5</cell>
<cell>6</cell>
<cell>7</cell>
</row>
答案 0 :(得分:1)
首先,在您的情况下,您可以首先使用模板来匹配根行元素
<xsl:template match="/rows">
在此,您必须编写代码来构建表头,然后开始寻找子行元素
<xsl:template match="/rows">
<table>
<!-- Header -->
<xsl:apply-templates select="row"/>
</table>
</xsl:template>
然后,您将拥有一个匹配行元素的模板,因此您可以输出 tr 元素,然后查找单个单元格
<xsl:template match="row">
<tr>
<xsl:apply-templates select="cell"/>
</tr>
<xsl:apply-templates select="row"/>
</xsl:template>
请注意递归调用以继续查找嵌套在当前行元素中的行元素。
同样,您将拥有一个模板来匹配单元格元素,这些元素只会输出 td 元素和单元格值。
我唯一不确定的是关于应该输出哪些行的规则。看起来您不想输出嵌套两个或更多级别的行元素。在这种情况下,您可以添加模板以忽略至少有两行或多行是祖先的行
<xsl:template match="row[ancestor::row[2]]"/>
这是完整的XSLT
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="html" indent="yes"/>
<xsl:template match="/rows">
<table>
<tr>
<th>1</th>
<th>2</th>
<th>3</th>
<th>4</th>
<th>5</th>
</tr>
<xsl:apply-templates select="row"/>
</table>
</xsl:template>
<xsl:template match="row">
<tr>
<xsl:apply-templates select="cell"/>
</tr>
<xsl:apply-templates select="row"/>
</xsl:template>
<xsl:template match="row[ancestor::row[2]]"/>
<xsl:template match="cell">
<td>
<xsl:value-of select="."/>
</td>
</xsl:template>
</xsl:stylesheet>
当应用于您的示例XML时,输出以下内容
<table>
<tr>
<th>1</th>
<th>2</th>
<th>3</th>
<th>4</th>
<th>5</th>
</tr>
<tr>
<td>1</td>
<td>2</td>
<td>1</td>
<td>2</td>
</tr>
<tr>
<td>3</td>
<td>4</td>
</tr>
</table>
编辑:如果要从与单元格元素匹配的模板中访问行元素上的属性,则需要指定它是父元素,像这样
<xsl:variable name="id1" select="../@id"/>
执行select="row/@id"
实际上会查找当前单元格元素的子行。