我有以下xml。
<xml>
<table>
<cols width="1.00*" />
<cols width="2.00*" />
<cols width="4.00*" />
<row><p>Hello</p></row>
</table>
<p>
Life is good.
</p>
</xml>
阐释: 我需要从上面的xml中读取列宽并显示。但在某些情况下,用户指定的宽度应小于表格列相互重叠的宽度。 因此我想做这个公式。 col1width = col1width / totalWidth * 100; 这将以%格式提供表格宽度,以便正确分配列。 但我无法统计所有这些属性。我的xslt不起作用。请参阅下面的xslt:
XSLT:
<xsl:template match="node()" mode="table">
<fo:table table-layout="fixed">
<fo:table-header>
<fo:table-row>
<xsl:for-each select="current()/cols">
<xsl:variable name="maxWidth"
select="number(substring-before(current()/table/cols/@width, '*')) + number(substring-before(following-sibling::cols/@width, '*'))" />
</xsl:for-each>
</fo:table-row>
</fo:table>
已尝试解决方案:
我尝试过使用sum函数。但在这里,在总结之前,我必须这样做 截断'*'字符并转换为数字然后添加。是否 不行。
编写一个递归模板来获取总和。我得到了这个总和。但是我无法返回总宽度 模板。我猜xslt不支持返回计算 值。下面是递归xslt。
<xsl:template name="maximumTableWidth">
<xsl:param name="total" select="0" />
<xsl:param name="totalCols" />
<xsl:param name="index" select="1" />
<xsl:if test="$index <= $totalCols">
<xsl:variable name="maxWidth"
select="$total + translate(current()/cols[$index]/@width, '*', '')" />
<xsl:call-template name="maximumTableWidth">
<xsl:with-param name="total" select="$maxWidth" />
<xsl:with-param name="nodes" select="$totalCols" />
<xsl:with-param name="index" select="$index + 1" />
</xsl:call-template>
</xsl:if>
</xsl:template>
XSLT电话:
<xsl:template name="main">
<xsl:variable name="maximumWidth">
<xsl:call-template name="maximumTableWidth">
<xsl:with-param name="total" select="0" />
<xsl:with-param name="totalCols"
select="count(current()/cols)" />
</xsl:call-template>
</xsl:variable>
</xsl:template>
这里,变量是string类型,因此没有值。 请帮我解决这个问题。也可以为表列宽度建议任何其他方法。我使用xsl fo生成pdf输出。而我的整个xslt都是动态的。我不能有像node1 / node2 / node3这样的直接路径。
谢谢。
答案 0 :(得分:2)
您的 maximumTableWidth 模板开始时遇到了一些问题。首先,您应该将translate
函数包装在number
函数
<xsl:variable name="maxWidth"
select="$total + number(translate(current()/cols[$index]/@width, '*', ''))" />
其次,您需要确保使用正确的参数调用它。对于递归调用,您应设置一个名为 nodes 的参数,当它应为 totalCols
时<xsl:with-param name="totalCols" select="$totalCols" />
但就返回值而言,您需要使用 xsl:value-of 输出值,然后设置 maximumWidth 变量达到那个价值。您需要做的就是将模板中的 xsl:if 更改为 xsl:choose 并输出 xsl:otherwise 条件中的值:
<xsl:template name="maximumTableWidth">
<xsl:param name="total" select="0" />
<xsl:param name="totalCols" />
<xsl:param name="index" select="1" />
<xsl:choose>
<xsl:when test="$index <= $totalCols">
<xsl:variable name="maxWidth"
select="$total + number(translate(current()/cols[$index]/@width, '*', ''))" />
<xsl:call-template name="maximumTableWidth">
<xsl:with-param name="total" select="$maxWidth" />
<xsl:with-param name="totalCols" select="$totalCols" />
<xsl:with-param name="index" select="$index + 1" />
</xsl:call-template>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$total" />
</xsl:otherwise>
</xsl:choose>
</xsl:template>
还有另一种递归写入此模板的方法。不是传入索引并递增它,而是传递 cols 元素本身,并使用following-sibling
迭代它们。请尝试使用此模板
<xsl:template name="maximumTableWidth">
<xsl:param name="col" />
<xsl:param name="total" select="0" />
<xsl:choose>
<xsl:when test="$col">
<xsl:variable name="maxWidth"
select="$total + number(translate($col/@width, '*', ''))" />
<xsl:call-template name="maximumTableWidth">
<xsl:with-param name="total" select="$maxWidth" />
<xsl:with-param name="col" select="$col/following-sibling::cols[1]" />
</xsl:call-template>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="$total" />
</xsl:otherwise>
</xsl:choose>
</xsl:template>
你会这样称呼:
<xsl:variable name="maximumWidth">
<xsl:call-template name="maximumTableWidth">
<xsl:with-param name="col" select="cols[1]" />
</xsl:call-template>
</xsl:variable>
<xsl:value-of select="$maximumWidth" />
编辑:如果您能够使用XSLT 2.0,那么您可以完全取消命名模板,只需将 maximumWidth 模板设置为此
<xsl:variable name="maximumWidth" select="sum(cols/(number(translate(@width, '*', ''))))" />