我有以下XML文件:
<PASS>
<FIRMWARE Unit="1" Group="FIRM">
<test name="ACPI" ID="ACPI" />
</FIRMWARE>
<NETWORK Unit="2" Group="NTWK">
<test name="Controller Test" ID="Ctlr" />
</NETWORK>
<NETWORK Unit="1" Group="NTWK">
<test name="Controller Test" ID="Ctlr" />
</NETWORK>
<ATA Unit="1" Group="ATA-">
<test name="Serial Controllers" ID="SATA" />
</ATA>
<PARALLEL_PORT Unit="1" Group="LPT-">
<test name="Verify Controller" ID="Ctrl" />
<test name="Check Status Port" ID="Stat" />
<test name="Interrupt Test" ID="Int-" />
</PARALLEL_PORT>
<SERIAL_PORT Unit="4" Group="COM-">
<test name="Interrupt" ID="Intr" />
<test name="Line Control" ID="Line" />
<test name="Test Loopback" ID="LpBk" />
<test name="Test Internal FIFO" ID="FIFO" />
<test name="Test Internal Loopback" ID="ILBk" />
</SERIAL_PORT>
<SERIAL_PORT Unit="3" Group="COM-">
<test name="Interrupt" ID="Intr" />
<test name="Line Control" ID="Line" />
<test name="Test Loopback" ID="LpBk" />
<test name="Test Internal FIFO" ID="FIFO" />
<test name="Test Internal Loopback" ID="ILBk" />
</SERIAL_PORT>
</PASS>
使用现有的XSL文件,我将所有测试结果都放在一列中。这对于打印等不太实用。如何创建包含2列或更多列的表?
<xsl:template match="PASS">
<div class="component">
<h4>PASSED</h4>
<xsl:call-template name="outputtable">
<xsl:with-param name="result" select="'PASSED'" />
</xsl:call-template>
</div>
</xsl:template>
<xsl:template name="outputtable">
<div class="attributes">
<xsl:variable name="resultlist" select="*" />
<xsl:variable name="index" select="count(child::*)" />
<xsl:for-each select="$resultlist">
<xsl:variable name="Unit" select="@Unit" />
<xsl:variable name="Group" select="@Group" />
<p class="attrtitle">
<xsl:value-of select="name()" />
Unit:
<xsl:value-of select="$Unit" />
</p>
<xsl:variable name="testtype" select="*" />
<xsl:for-each select="$testtype">
<p class="attribute">
<xsl:value-of select="@name" />
</p>
</xsl:for-each>
<p />
</xsl:for-each>
</div>
我已经搜索过解决方案并找到以下链接: Use xslt to convert xml list into html table with multiple columns和 http://blogs.msdn.com/b/kaevans/archive/2003/04/03/4754.aspx
我所拥有的情况相当不同我有结构对象而不是简单的“Item”或“ComputerName”,另一个缺点是那些测试不是同一类型(等等)。此XML报告由非OSS软件自动构建,因此我无法在创建时更改它。
我会很高兴得到任何想法!
答案 0 :(得分:0)
此转化:
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:param name="pnumCols" select="3"/>
<xsl:template match="PASS">
<div class="component">
<h4>PASSED</h4>
<div class="attributes">
<table border="1">
<xsl:apply-templates select=
"*[position() mod $pnumCols = 1]"/>
</table>
</div>
</div>
</xsl:template>
<xsl:template match="PASS/*">
<tr>
<xsl:apply-templates mode="process" select=
".|following-sibling::*[not(position() > $pnumCols -1)]"/>
</tr>
</xsl:template>
<xsl:template match="PASS/*" mode="process">
<xsl:variable name="Unit" select="@Unit" />
<xsl:variable name="Group" select="@Group" />
<td>
<p class="attrtitle">
<xsl:value-of select="name()" /> Unit:
<xsl:value-of select="$Unit" />
</p>
<xsl:variable name="testtype" select="*" />
<xsl:for-each select="$testtype">
<p class="attribute">
<xsl:value-of select="@name" />
</p>
</xsl:for-each>
<p />
</td>
</xsl:template>
</xsl:stylesheet>
应用于提供的XML文档时:
<PASS>
<FIRMWARE Unit="1" Group="FIRM">
<test name="ACPI" ID="ACPI" />
</FIRMWARE>
<NETWORK Unit="2" Group="NTWK">
<test name="Controller Test" ID="Ctlr" />
</NETWORK>
<NETWORK Unit="1" Group="NTWK">
<test name="Controller Test" ID="Ctlr" />
</NETWORK>
<ATA Unit="1" Group="ATA-">
<test name="Serial Controllers" ID="SATA" />
</ATA>
<PARALLEL_PORT Unit="1" Group="LPT-">
<test name="Verify Controller" ID="Ctrl" />
<test name="Check Status Port" ID="Stat" />
<test name="Interrupt Test" ID="Int-" />
</PARALLEL_PORT>
<SERIAL_PORT Unit="4" Group="COM-">
<test name="Interrupt" ID="Intr" />
<test name="Line Control" ID="Line" />
<test name="Test Loopback" ID="LpBk" />
<test name="Test Internal FIFO" ID="FIFO" />
<test name="Test Internal Loopback" ID="ILBk" />
</SERIAL_PORT>
<SERIAL_PORT Unit="3" Group="COM-">
<test name="Interrupt" ID="Intr" />
<test name="Line Control" ID="Line" />
<test name="Test Loopback" ID="LpBk" />
<test name="Test Internal FIFO" ID="FIFO" />
<test name="Test Internal Loopback" ID="ILBk" />
</SERIAL_PORT>
</PASS>
以$pnumCols
- 列格式生成结果,在此特定情况下,pnumCols
为3:
<div class="component">
<h4>PASSED</h4>
<div class="attributes">
<table border="1">
<tr>
<td>
<p class="attrtitle">FIRMWARE Unit:
1</p>
<p class="attribute">ACPI</p>
<p/>
</td>
<td>
<p class="attrtitle">NETWORK Unit:
2</p>
<p class="attribute">Controller Test</p>
<p/>
</td>
<td>
<p class="attrtitle">NETWORK Unit:
1</p>
<p class="attribute">Controller Test</p>
<p/>
</td>
</tr>
<tr>
<td>
<p class="attrtitle">ATA Unit:
1</p>
<p class="attribute">Serial Controllers</p>
<p/>
</td>
<td>
<p class="attrtitle">PARALLEL_PORT Unit:
1</p>
<p class="attribute">Verify Controller</p>
<p class="attribute">Check Status Port</p>
<p class="attribute">Interrupt Test</p>
<p/>
</td>
<td>
<p class="attrtitle">SERIAL_PORT Unit:
4</p>
<p class="attribute">Interrupt</p>
<p class="attribute">Line Control</p>
<p class="attribute">Test Loopback</p>
<p class="attribute">Test Internal FIFO</p>
<p class="attribute">Test Internal Loopback</p>
<p/>
</td>
</tr>
<tr>
<td>
<p class="attrtitle">SERIAL_PORT Unit:
3</p>
<p class="attribute">Interrupt</p>
<p class="attribute">Line Control</p>
<p class="attribute">Test Loopback</p>
<p class="attribute">Test Internal FIFO</p>
<p class="attribute">Test Internal Loopback</p>
<p/>
</td>
</tr>
</table>
</div>
</div>
解释:我们使用两个模板 - 一个用于连续排列一组$pnumCols
个连续结果,另一个用于mode="process"
,以实际生成内容在那一行内。