使用 XSL 将 XML 列表转换为 HTML 表 [英] Convert XML List to HTML Table Using XSL
问题描述
您好,过去几天我一直在为此苦苦挣扎,但找不到好的答案或解决方案.我有一个包含如下对象列表的 XML 文件:
Hello I was struggling with this for the past days and I could not find a good answer nor solution. I have an XML file with a list of objects like this:
<?xml version="1.0" encoding="UTF-8"?>
<LineItems>
<TableName>Lines</TableName>
<TableTerm>Lines</TableTerm>
<LineItems>
<Class>A Class</Class>
</LineItems>
<LineItems>
<Number>1234</Number>
</LineItems>
<LineItems>
<Description>G</Description>
</LineItems>
<LineItems>
<Class>B Class</Class>
</LineItems>
<LineItems>
<Number>5678</Number>
</LineItems>
<LineItems>
<Description>F</Description>
</LineItems>
<ColumnMetadata>
<Name>Class</Name>
<Term>Class</Term>
</ColumnMetadata>
<ColumnMetadata>
<Name>Number</Name>
<Term>No</Term>
</ColumnMetadata>
<ColumnMetadata>
<Name>Description</Name>
<Term>Description</Term>
</ColumnMetadata>
</LineItems>
我正在应用以下转换:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
<html>
<body>
<xsl:variable name="columns" select="count(LineItems/ColumnMetadata)" />
<xsl:variable name="items" select="count(LineItems/LineItems)" />
<xsl:variable name="rows" select="$items div $columns" />
<table border="1">
<thead >
<tr bgcolor="#9acd32">
<xsl:for-each select="LineItems/ColumnMetadata">
<th style="padding: .3em 0;">
<xsl:value-of select="Term" />
</th>
</xsl:for-each>
</tr>
</thead>
<tbody style="text-align: center;">
<xsl:for-each select="(//LineItems)[position()<=$rows]">
<xsl:variable name="i" select="position() - 1"/>
<tr>
<xsl:for-each select="(//*)[position()<=$columns]">
<xsl:variable name="j" select="position()+($columns*$i)"/>
<td style="padding: .3em 0;">
<xsl:value-of select="LineItems/LineItems[$j]" />
</td>
</xsl:for-each>
</tr>
</xsl:for-each>
</tbody>
</table>
</body>
</html>
</xsl:template>
</xsl:stylesheet>
最后这个案例的期望输出是:
Finally the desire output for this case would be:
<table>
<thead>
<tr>
<th>Class</th>
<th>No</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>A Class</td>
<td>1234</td>
<td>G</td>
</tr>
<tr>
<td>B Class</td>
<td>5678</td>
<td>F</td>
</tr>
</tbody>
</table>
这个案例是一个MxN表的案例,我知道节点有多少列.所以,总结一下:
This case is a case of MxN table, I cna know how many columns from nodes. So, to sumarise:
- 必须转换为表格的实际列表都在根目录
中. - 我不知道我将获得多少项(行),但我可以计算它们除以
节点($items)的数量除以的数量
节点($columns) - 像
、
和
这样的节点是表中的列,但它们可以有其他名称,它们是动态的,可以是 5、6...许多列.
- The actual list that have to be transformed as a table is all inside root
<LineItems>
. - I don't know how many items (rows) I am going to get, but I can calculate them dividing amount of
<LineItems>
nodes ($items) by amount of<ColumnMetadata>
nodes ($columns) - Nodes like
<Class>
,<Number>
and<Description>
, are columns in table, but they can have other names, they are dynamic and can be 5, 6... Many columns.
如果我在在线工具中使用 XSL 转换以上 XML,我只会得到表格的标题行(并检查 HTML,我可以看到 2 行用于 2 个项目,但为空).如果我使用 Visual Studio 转换工具,我不仅会得到标题行,还会得到表的前 2 列(在本例中为类值),但不会得到其余的值.我真的不明白这是怎么回事,为什么我使用不同的工具得到不同的结果.
If I transform above XML with XSL in online tools I only get the header row of the table (and inspecting HTML, I can see 2 rows for 2 items, but empty). If I use Visual Studio transformation tool, I not only get header row, I also get first 2 columns of table (in this example Class values) but not the values in the rest of them. I really don't understand what is going on and why do I get different results using different tools.
提前致谢
推荐答案
lineitmes 遵循常规模式.
lineitmes folllow a regular pattern.
那么我相信它可能很简单:
Then I believe it could be simply:
XSLT 1.0
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="html" encoding="UTF-8"/>
<xsl:strip-space elements="*"/>
<xsl:template match="/LineItems">
<xsl:variable name="columns" select="count(ColumnMetadata)"/>
<table border="1">
<thead >
<tr>
<xsl:for-each select="ColumnMetadata">
<th>
<xsl:value-of select="Term"/>
</th>
</xsl:for-each>
</tr>
</thead>
<tbody>
<xsl:for-each select="LineItems[position() mod $columns = 1]">
<tr>
<xsl:for-each select=". | following-sibling::LineItems[position() < $columns]">
<td>
<xsl:value-of select="*"/>
</td>
</xsl:for-each>
</tr>
</xsl:for-each>
</tbody>
</table>
</xsl:template>
</xsl:stylesheet>
这篇关于使用 XSL 将 XML 列表转换为 HTML 表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!