是否可以更改此 XSL 代码以填充 HTML table?
Can this XSL code be changed to fill in a HTML table instead?
我对昨天提供给我的一个问题有了这个很好的答案:
由于打印页面上的 space 限制,我想将数据布局为 table。这是一个在 Microsoft Expression Web 中修改的示例:
所以,我想使用我当前使用的 XSL 代码:
<xsl:variable name="AssignHistory" select="document('AssignHistory.xml')"/>
<xsl:variable name="week" select="Date/@NextWeek"/>
<xsl:apply-templates select="$AssignHistory/AssignmentHistory/*[name()=$week]/StudentItems"/>
模板函数:
<xsl:template match="StudentItems">
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<xsl:value-of select="Description"/>
: 
<xsl:value-of select="Name"/>
<br/>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</xsl:template>
<xsl:template match="Item">
<xsl:value-of select="Description"/>
: 
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
<br/>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
所以,最后的 table 将有 1、2 或 3 列。
如果列表中有 7 项学生项目,则它有 1 列内容。
如果有 14 个项目,则第 7 到 14 项显示在第二列中。
如果有 21 项,则第 15 到 21 项显示在第三列中。
唯一的其他区别是:
- 第一列的行将以 "description" 值作为前缀。
- 会有一个标题行说明 "school"(硬编码文本)。除非只有 1 列,否则不需要这一行。
是否可以以任何方式调整这些模板以创建此修改后的输出?
这里是一些修改后的 XML 数据以供使用:
<StudentItems>
<Item>
<Name Counsel="9">1</Name>
<Type>Bible Reading (Main)</Type>
<Description>Bible Reading</Description>
</Item>
<Item Description="Initial Call">
<Name Counsel="37">2</Name>
<Type>#1 Student (Main)</Type>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>3</Name>
<Type>Assistant</Type>
<Description>Initial Call</Description>
</Item>
<Item>
<Name Counsel="48">4</Name>
<Type>#2 Student (Main)</Type>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>5</Name>
<Type>Assistant</Type>
<Description>Return Visit</Description>
</Item>
<Item>
<Name Counsel="27">6</Name>
<Type>#3 Student (Main)</Type>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>7</Name>
<Type>Assistant</Type>
<Description>Bible Study</Description>
</Item>
</StudentItems>
非常感谢您的帮助。我很感激。
我进步很大。不知道是不是最好的方法:
<table cellpadding="2">
<xsl:apply-templates select="$AssignHistory/AssignmentHistory/*[name()=$week]/StudentItems"/>
</table>
和
<xsl:template match="StudentItems">
<xsl:if test="Item[position() = 1]">
<xsl:if test="count(Item) = 14">
<tr>
<td>
<b>Main</b>
</td>
<td>
<b>Auxiliary Class 1</b>
</td>
</tr>
</xsl:if>
<xsl:if test="count(Item) = 21">
<tr>
<td>
<b>Main</b>
</td>
<td>
<b>Auxiliary Class 1</b>
</td>
<td>
<b>Auxiliary Class 2</b>
</td>
</tr>
</xsl:if>
</xsl:if>
<tr>
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</tr>
</xsl:template>
<xsl:template match="Item" mode="leader">
<td>
<b><xsl:value-of select="Description"/>: </b>
<xsl:value-of select="Name"/>
<br/>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</td>
</xsl:template>
<xsl:template match="Item">
<b><xsl:value-of select="Description"/>: </b>
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
<xsl:if test="position() != 3">
<br/>
</xsl:if>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
这似乎很有效。但我只想在第一列上使用 "description" 标签,但我不知道如何将其从其他列中删除:
我继续尝试并应用建议的内容(内联 tables)并且代码更简单:
<xsl:template match="StudentItems">
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<table cellpadding="2" style="float:left;">
<tr>
<td>
<xsl:choose>
<xsl:when test="position() = 1">Main </xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1 </xsl:when>
<xsl:otherwise>Auxiliary Class 2 </xsl:otherwise>
</xsl:choose>
</td>
</tr>
<tr>
<td>
<b>
<xsl:value-of select="Description"/>: 
</b>
<xsl:value-of select="Name"/>
</td>
</tr>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</table>
</xsl:template>
<xsl:template match="Item">
<tr>
<td>
<b>
<xsl:value-of select="Description"/>: 
</b>
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
</td>
</tr>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
这看起来更简单。谢谢。但我还有两个问题:
如果 StudentItems 列表中只有 7 个项目(或更少),我不需要标题行。
我不想为第二个或第三个 table 添加 "descriptions"。
这可以做到吗?
我相信我会做这样的事情:
<xsl:template match="StudentItems">
<table border="1" style="display:inline;">
<tr>
<td> </td>
</tr>
<xsl:for-each select="Item[contains('1,2,4,6', position())]">
<tr>
<th><xsl:value-of select="Description"/></th>
</tr>
</xsl:for-each>
</table>
<xsl:apply-templates select="Item[position()mod 7 = 1]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<table border="1" style="display:inline;">
<tr>
<th colspan="2">
<xsl:choose>
<xsl:when test="position() = 1">Main </xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1 </xsl:when>
<xsl:otherwise>Auxiliary Class 2 </xsl:otherwise>
</xsl:choose>
</th>
</tr>
<tr>
<td colspan="2"><xsl:value-of select="Name"/></td>
</tr>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</table>
</xsl:template>
<xsl:template match="Item">
<tr>
<td><xsl:value-of select="Name"/></td>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
</tr>
</xsl:template>
<xsl:template match="Item" mode="follower">
<td><xsl:value-of select="Name"/></td>
</xsl:template>
应用于以下测试输入:
<StudentItems>
<Item>
<Name>Name 1</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 2</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 3</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 4</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 5</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 6</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 7</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 8</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 9</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 10</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 11</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 12</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 13</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 14</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 15</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 16</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 17</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 18</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 19</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 20</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 21</Name>
<Description>Bible Study</Description>
</Item>
</StudentItems>
结果(呈现)是:
您将此作为 的扩展提出 - 我的第一个答案是对我在那里给出的答案的改编。然而,问题的性质已经发生了显着变化,我认为用新的眼光来看待它可能会更好。
这个解决方案可能不像另一个 "clever" - 但对我来说它似乎更直接。
<xsl:template match="StudentItems">
<table border="1" width="80%">
<thead>
<tr>
<th/>
<xsl:for-each select="Item[contains('|1|8|15|', concat('|', position(), '|'))]">
<th colspan="2">
<xsl:choose>
<xsl:when test="position() = 1">Main</xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1</xsl:when>
<xsl:when test="position() = 3">Auxiliary Class 2</xsl:when>
</xsl:choose>
</th>
</xsl:for-each>
</tr>
</thead>
<tbody>
<tr>
<th><xsl:value-of select="Item[1]/Description"/></th>
<xsl:for-each select="Item[contains('|1|8|15|', concat('|', position(), '|'))]">
<td colspan="2"><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[2]/Description"/></th>
<xsl:for-each select="Item[contains('|2|3|9|10|16|17|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[4]/Description"/></th>
<xsl:for-each select="Item[contains('|4|5|11|12|18|19|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[6]/Description"/></th>
<xsl:for-each select="Item[contains('|6|7|13|14|20|21|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
</tbody>
</table>
</xsl:template>
这里的结果是单table,呈现为:
我对昨天提供给我的一个问题有了这个很好的答案:
由于打印页面上的 space 限制,我想将数据布局为 table。这是一个在 Microsoft Expression Web 中修改的示例:
所以,我想使用我当前使用的 XSL 代码:
<xsl:variable name="AssignHistory" select="document('AssignHistory.xml')"/>
<xsl:variable name="week" select="Date/@NextWeek"/>
<xsl:apply-templates select="$AssignHistory/AssignmentHistory/*[name()=$week]/StudentItems"/>
模板函数:
<xsl:template match="StudentItems">
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<xsl:value-of select="Description"/>
: 
<xsl:value-of select="Name"/>
<br/>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</xsl:template>
<xsl:template match="Item">
<xsl:value-of select="Description"/>
: 
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
<br/>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
所以,最后的 table 将有 1、2 或 3 列。
如果列表中有 7 项学生项目,则它有 1 列内容。 如果有 14 个项目,则第 7 到 14 项显示在第二列中。 如果有 21 项,则第 15 到 21 项显示在第三列中。
唯一的其他区别是:
- 第一列的行将以 "description" 值作为前缀。
- 会有一个标题行说明 "school"(硬编码文本)。除非只有 1 列,否则不需要这一行。
是否可以以任何方式调整这些模板以创建此修改后的输出?
这里是一些修改后的 XML 数据以供使用:
<StudentItems>
<Item>
<Name Counsel="9">1</Name>
<Type>Bible Reading (Main)</Type>
<Description>Bible Reading</Description>
</Item>
<Item Description="Initial Call">
<Name Counsel="37">2</Name>
<Type>#1 Student (Main)</Type>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>3</Name>
<Type>Assistant</Type>
<Description>Initial Call</Description>
</Item>
<Item>
<Name Counsel="48">4</Name>
<Type>#2 Student (Main)</Type>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>5</Name>
<Type>Assistant</Type>
<Description>Return Visit</Description>
</Item>
<Item>
<Name Counsel="27">6</Name>
<Type>#3 Student (Main)</Type>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>7</Name>
<Type>Assistant</Type>
<Description>Bible Study</Description>
</Item>
</StudentItems>
非常感谢您的帮助。我很感激。
我进步很大。不知道是不是最好的方法:
<table cellpadding="2">
<xsl:apply-templates select="$AssignHistory/AssignmentHistory/*[name()=$week]/StudentItems"/>
</table>
和
<xsl:template match="StudentItems">
<xsl:if test="Item[position() = 1]">
<xsl:if test="count(Item) = 14">
<tr>
<td>
<b>Main</b>
</td>
<td>
<b>Auxiliary Class 1</b>
</td>
</tr>
</xsl:if>
<xsl:if test="count(Item) = 21">
<tr>
<td>
<b>Main</b>
</td>
<td>
<b>Auxiliary Class 1</b>
</td>
<td>
<b>Auxiliary Class 2</b>
</td>
</tr>
</xsl:if>
</xsl:if>
<tr>
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</tr>
</xsl:template>
<xsl:template match="Item" mode="leader">
<td>
<b><xsl:value-of select="Description"/>: </b>
<xsl:value-of select="Name"/>
<br/>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</td>
</xsl:template>
<xsl:template match="Item">
<b><xsl:value-of select="Description"/>: </b>
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
<xsl:if test="position() != 3">
<br/>
</xsl:if>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
这似乎很有效。但我只想在第一列上使用 "description" 标签,但我不知道如何将其从其他列中删除:
我继续尝试并应用建议的内容(内联 tables)并且代码更简单:
<xsl:template match="StudentItems">
<xsl:apply-templates select="Item[not((position() - 1) mod 7)]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<table cellpadding="2" style="float:left;">
<tr>
<td>
<xsl:choose>
<xsl:when test="position() = 1">Main </xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1 </xsl:when>
<xsl:otherwise>Auxiliary Class 2 </xsl:otherwise>
</xsl:choose>
</td>
</tr>
<tr>
<td>
<b>
<xsl:value-of select="Description"/>: 
</b>
<xsl:value-of select="Name"/>
</td>
</tr>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</table>
</xsl:template>
<xsl:template match="Item">
<tr>
<td>
<b>
<xsl:value-of select="Description"/>: 
</b>
<xsl:value-of select="Name"/>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
</td>
</tr>
</xsl:template>
<xsl:template match="Item" mode="follower">
<xsl:text> / </xsl:text>
<xsl:value-of select="Name"/>
</xsl:template>
这看起来更简单。谢谢。但我还有两个问题:
如果 StudentItems 列表中只有 7 个项目(或更少),我不需要标题行。
我不想为第二个或第三个 table 添加 "descriptions"。
这可以做到吗?
我相信我会做这样的事情:
<xsl:template match="StudentItems">
<table border="1" style="display:inline;">
<tr>
<td> </td>
</tr>
<xsl:for-each select="Item[contains('1,2,4,6', position())]">
<tr>
<th><xsl:value-of select="Description"/></th>
</tr>
</xsl:for-each>
</table>
<xsl:apply-templates select="Item[position()mod 7 = 1]" mode="leader"/>
</xsl:template>
<xsl:template match="Item" mode="leader">
<table border="1" style="display:inline;">
<tr>
<th colspan="2">
<xsl:choose>
<xsl:when test="position() = 1">Main </xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1 </xsl:when>
<xsl:otherwise>Auxiliary Class 2 </xsl:otherwise>
</xsl:choose>
</th>
</tr>
<tr>
<td colspan="2"><xsl:value-of select="Name"/></td>
</tr>
<xsl:apply-templates select="following-sibling::Item[position() <= 6 and position() mod 2]"/>
</table>
</xsl:template>
<xsl:template match="Item">
<tr>
<td><xsl:value-of select="Name"/></td>
<xsl:apply-templates select="following-sibling::Item[1]" mode="follower"/>
</tr>
</xsl:template>
<xsl:template match="Item" mode="follower">
<td><xsl:value-of select="Name"/></td>
</xsl:template>
应用于以下测试输入:
<StudentItems>
<Item>
<Name>Name 1</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 2</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 3</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 4</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 5</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 6</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 7</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 8</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 9</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 10</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 11</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 12</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 13</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 14</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 15</Name>
<Description>Bible Reading</Description>
</Item>
<Item>
<Name>Name 16</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 17</Name>
<Description>Initial Call</Description>
</Item>
<Item>
<Name>Name 18</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 19</Name>
<Description>Return Visit</Description>
</Item>
<Item>
<Name>Name 20</Name>
<Description>Bible Study</Description>
</Item>
<Item>
<Name>Name 21</Name>
<Description>Bible Study</Description>
</Item>
</StudentItems>
结果(呈现)是:
您将此作为
这个解决方案可能不像另一个 "clever" - 但对我来说它似乎更直接。
<xsl:template match="StudentItems">
<table border="1" width="80%">
<thead>
<tr>
<th/>
<xsl:for-each select="Item[contains('|1|8|15|', concat('|', position(), '|'))]">
<th colspan="2">
<xsl:choose>
<xsl:when test="position() = 1">Main</xsl:when>
<xsl:when test="position() = 2">Auxiliary Class 1</xsl:when>
<xsl:when test="position() = 3">Auxiliary Class 2</xsl:when>
</xsl:choose>
</th>
</xsl:for-each>
</tr>
</thead>
<tbody>
<tr>
<th><xsl:value-of select="Item[1]/Description"/></th>
<xsl:for-each select="Item[contains('|1|8|15|', concat('|', position(), '|'))]">
<td colspan="2"><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[2]/Description"/></th>
<xsl:for-each select="Item[contains('|2|3|9|10|16|17|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[4]/Description"/></th>
<xsl:for-each select="Item[contains('|4|5|11|12|18|19|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
<tr>
<th><xsl:value-of select="Item[6]/Description"/></th>
<xsl:for-each select="Item[contains('|6|7|13|14|20|21|', concat('|', position(), '|'))]">
<td><xsl:value-of select="Name"/></td>
</xsl:for-each>
</tr>
</tbody>
</table>
</xsl:template>
这里的结果是单table,呈现为: