Alot of the docs pages have manually written table of contents linking to
headings with the page. I figured this is a good candidate for being
auto-generated.
The basic idea is that given a document with a series of headings
<h2><a name="xxx">Foo</a></h2>
..
<h3><a name="xxx">Bar</a></h3>
..
<h3><a name="xxx">Wizz</a></h3>
..
<h2><a name="xxx">Oooh</a></h2>
..
<h3><a name="xxx">Ahhh</a></h3>
Then, generate a table of contents with a nested set of lists <ul>. THe
XSL below attempts todo this for heading levels h2 -> h6, and splices the
TOC into the page where it sees an <ul id='toc'></ul> element
(typically
just after <h1>).
I'm kind of out of practice with XSL, so there's probably a nicer way
to write the 'toc' template below...
Dan.
Index: docs/page.xsl
===================================================================
RCS file: /data/cvs/libvirt/docs/page.xsl,v
retrieving revision 1.7
diff -u -r1.7 page.xsl
--- docs/page.xsl 28 Apr 2008 08:29:35 -0000 1.7
+++ docs/page.xsl 30 Apr 2008 12:55:20 -0000
@@ -59,6 +59,54 @@
</ul>
</xsl:template>
+ <xsl:template name="toc">
+ <ul>
+ <xsl:for-each select="/html/body/h2[count(a) = 1]">
+ <xsl:variable name="thishead" select="."/>
+ <li>
+ <a href="#{a/@name}"><xsl:value-of
select="a/text()"/></a>
+ <xsl:if test="count(./following-sibling::h3[preceding-sibling::h2[1] =
$thishead and count(a) = 1]) > 0">
+ <ul>
+ <xsl:for-each
select="./following-sibling::h3[preceding-sibling::h2[1] = $thishead and count(a) =
1]">
+ <xsl:variable name="thissubhead" select="."/>
+ <li>
+ <a href="#{a/@name}"><xsl:value-of
select="a/text()"/></a>
+ <xsl:if
test="count(./following-sibling::h4[preceding-sibling::h3[1] = $thissubhead and
count(a) = 1]) > 0">
+ <ul>
+ <xsl:for-each
select="./following-sibling::h4[preceding-sibling::h3[1] = $thissubhead and count(a)
= 1]">
+ <li>
+ <a href="#{a/@name}"><xsl:value-of
select="a/text()"/></a>
+ <xsl:if
test="count(./following-sibling::h5[preceding-sibling::h4[1] = $thissubhead and
count(a) = 1]) > 0">
+ <ul>
+ <xsl:for-each
select="./following-sibling::h5[preceding-sibling::h4[1] = $thissubhead and count(a)
= 1]">
+ <li>
+ <a href="#{a/@name}"><xsl:value-of
select="a/text()"/></a>
+ <xsl:if
test="count(./following-sibling::h6[preceding-sibling::h5[1] = $thissubhead and
count(a) = 1]) > 0">
+ <ul>
+ <xsl:for-each
select="./following-sibling::h6[preceding-sibling::h5[1] = $thissubhead and count(a)
= 1]">
+ <li>
+ <a
href="#{a/@name}"><xsl:value-of
select="a/text()"/></a>
+ </li>
+ </xsl:for-each>
+ </ul>
+ </xsl:if>
+ </li>
+ </xsl:for-each>
+ </ul>
+ </xsl:if>
+ </li>
+ </xsl:for-each>
+ </ul>
+ </xsl:if>
+ </li>
+ </xsl:for-each>
+ </ul>
+ </xsl:if>
+ </li>
+ </xsl:for-each>
+ </ul>
+ </xsl:template>
+
<!-- This is the master page structure -->
<xsl:template match="/" mode="page">
<xsl:param name="pagename"/>
@@ -93,7 +141,16 @@
</xsl:apply-templates>
</div>
<div id="content">
- <xsl:copy-of select="html/body/*"/>
+ <xsl:for-each select="html/body/*">
+ <xsl:choose>
+ <xsl:when test="name() = 'ul' and @id =
'toc'">
+ <xsl:call-template name="toc"/>
+ </xsl:when>
+ <xsl:otherwise>
+ <xsl:copy-of select="."/>
+ </xsl:otherwise>
+ </xsl:choose>
+ </xsl:for-each>
</div>
</div>
<div id="footer">
--
|: Red Hat, Engineering, Boston -o-
http://people.redhat.com/berrange/ :|
|:
http://libvirt.org -o-
http://virt-manager.org -o-
http://ovirt.org :|
|:
http://autobuild.org -o-
http://search.cpan.org/~danberr/ :|
|: GnuPG: 7D3B9505 -o- F3C9 553F A1DA 4AC2 5648 23C1 B3DF F742 7D3B 9505 :|