]> granicus.if.org Git - docbook-dsssl/commitdiff
Added capability in FO output for displaying URLs for all
authorMichael Smith <xmldoc@users.sourceforge.net>
Mon, 10 Sep 2007 11:12:44 +0000 (11:12 +0000)
committerMichael Smith <xmldoc@users.sourceforge.net>
Mon, 10 Sep 2007 11:12:44 +0000 (11:12 +0000)
hyperlinks (elements marked up with xlink:href attributes) in the
same way as URLs for ulinks are already handled (which is to say,
either inline or as numbered footnotes).

Background on this change:
DocBook 5 allows "ubiquitous" linking, which means you can make
any element a hyperlink just by adding an xlink:href attribute to
it, with the value set to an external URL. That's in contrast to
DocBook 4, which only allows you to use specific elements (e.g.,
the link and ulink elements) to mark up hyperlinks.

The existing FO stylesheets have a mechanism for handling display
of URLs for hyperlinks that are marked up with ulink, but they did
not handle display of URLs for elements that were marked up with
xlink:href attributes. This change adds handling for those other
elements, enabling the URLs they link to be displayed either
inline or as numbered footnotes (depending on what values the user
has the ulink.show and ulink.footnotes params set to).

Note that this change only adds URL display support for elements
that call the simple.xlink template -- which currently is most
(but not all) inline elements.

This change also moves the URL display handling out of the ulink
template and into a new "hyperlink.url.display" named template;
the ulink template and the simple.xlink named template now both
call the hyperlink.url.display template.

Warning: In the stylesheet code that determines what footnote
number to assign to each footnote or external hyperlink, there is
an XPath expression for determining whether a particular
xlink:href instance is an external hyperlink; that expression is
necessarily a bit complicated and further testing may reveal that
it doesn't handle all cases as expected -- so some refinements to
it may need to be done later.

Closes #1785519. Thanks to Ken Morse for reporting and
troubleshooting the problem.

xsl/fo/footnote.xsl
xsl/fo/inline.xsl
xsl/fo/xref.xsl

index 3340b322db5e0aa3a3590a199bd58f6b2c8b81c6..ff4beb09eb442752b40c626f01212e36f3cc01f1 100644 (file)
@@ -1,6 +1,7 @@
 <?xml version='1.0'?>
 <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
                 xmlns:fo="http://www.w3.org/1999/XSL/Format"
+                xmlns:xlink="http://www.w3.org/1999/xlink"
                 xmlns:exsl="http://exslt.org/common"
                 exclude-result-prefixes="exsl"
                 version='1.0'>
     </xsl:when>
     <xsl:otherwise>
       <xsl:variable name="fnum">
+        <!-- * Determine the footnote number to display for this footnote, -->
+        <!-- * by counting all foonotes, ulinks, and any elements that have -->
+        <!-- * an xlink:href attribute that meets the following criteria: -->
+        <!-- * -->
+        <!-- * - the content of the element is not a URI that is the same -->
+        <!-- *   URI as the value of the href attribute -->
+        <!-- * - the href attribute is not an internal ID reference (does -->
+        <!-- *   not start with a hash sign) -->
+        <!-- * - the href is not part of an olink reference (the element -->
+        <!-- * - does not have an xlink:role attribute that indicates it is -->
+        <!-- *   an olink, and the hrf does not contain a hash sign) -->
+        <!-- * - the element either has no xlink:type attribute or has -->
+        <!-- *   an xlink:type attribute whose value is 'simple' -->
+        <!-- *  -->
+        <!-- * Note that hyperlinks are counted only if both the value of -->
+        <!-- * ulink.footnotes is non-zero and the value of ulink.show is -->
+        <!-- * non-zero -->
         <!-- FIXME: list in @from is probably not complete -->
         <xsl:number level="any" 
                     from="chapter|appendix|preface|article|refentry|bibliography" 
-                    count="footnote[not(@label)][not(ancestor::table) and not(ancestor::informaltable)]|ulink[$ulink.footnotes != 0][node()][@url != .][not(ancestor::footnote)][$ulink.show != 0]" 
+                    count="footnote[not(@label)][not(ancestor::table) and not(ancestor::informaltable)]
+                    |ulink[$ulink.footnotes != 0][node()][@url != .][not(ancestor::footnote)][$ulink.show != 0]
+                    |*[node()][@xlink:href][not(@xlink:href = .)][not(starts-with(@xlink:href,'#'))]
+                      [not(contains(@xlink:href,'#') and @xlink:role = $xolink.role)]
+                      [not(@xlink:type) or @xlink:type='simple']
+                      [not(ancestor::footnote)][$ulink.footnotes != 0][$ulink.show != 0]
+                    "
                     format="1"/>
       </xsl:variable>
       <xsl:choose>
index d398decda992aa8e574a1aba66fa15429010f6ca..b019f9a1553e2911a11dc8f020960903c579462c 100644 (file)
           <fo:basic-link external-destination="url({$xhref})">
             <xsl:copy-of select="$content"/>
           </fo:basic-link>
+          <!-- * Call the template for determining whether the URL for this -->
+          <!-- * hyperlink is displayed, and how to display it (either inline or -->
+          <!-- * as a numbered footnote). -->
+          <xsl:call-template name="hyperlink.url.display">
+            <xsl:with-param name="url" select="$xhref"/>
+          </xsl:call-template>
         </xsl:otherwise>
       </xsl:choose>
     </xsl:when>
index 2b0d813df033977cbfcfff612db359c039637ea3..d7f6994d4025cc4d05e6e2783d4a2d7d35e0535d 100644 (file)
       </xsl:otherwise>
     </xsl:choose>
   </fo:basic-link>
+  <!-- * Call the template for determining whether the URL for this -->
+  <!-- * hyperlink is displayed, and how to display it (either inline or -->
+  <!-- * as a numbered footnote). -->
+  <xsl:call-template name="hyperlink.url.display">
+    <xsl:with-param name="url" select="$url"/>
+    <xsl:with-param name="ulink.url" select="$ulink.url"/>
+  </xsl:call-template>
+</xsl:template>
+
+<xsl:template name="hyperlink.url.display">
+  <!-- * This template is called for all external hyperlinks (ulinks and -->
+  <!-- * for all simple xlinks); it determines whether the URL for the -->
+  <!-- * hyperlink is displayed, and how to display it (either inline or -->
+  <!-- * as a numbered footnote). -->
+  <xsl:param name="url" select="$url"/>
+  <xsl:param name="ulink.url">
+    <!-- * ulink.url is just the value of the URL wrapped in 'url(...)' -->
+    <xsl:call-template name="fo-external-image">
+      <xsl:with-param name="filename" select="$url"/>
+    </xsl:call-template>
+  </xsl:param>
 
   <xsl:if test="count(child::node()) != 0
                 and string(.) != $url
                 and $ulink.show != 0">
-    <!-- yes, show the URI -->
+    <!-- * Display the URL for this hyperlink only if it is non-empty, -->
+    <!-- * and the value of its content is not a URL that is the same as -->
+    <!-- * URL it links to, and if ulink.show is non-zero. -->
     <xsl:choose>
       <xsl:when test="$ulink.footnotes != 0 and not(ancestor::footnote)">
+        <!-- * ulink.show and ulink.footnote are both non-zero; that -->
+        <!-- * means we display the URL as a footnote (instead of inline) -->
         <fo:footnote>
           <xsl:call-template name="ulink.footnote.number"/>
           <fo:footnote-body xsl:use-attribute-sets="footnote.properties">
         </fo:footnote>
       </xsl:when>
       <xsl:otherwise>
+        <!-- * ulink.show is non-zero, but ulink.footnote is not; that -->
+        <!-- * means we display the URL inline -->
         <fo:inline hyphenate="false">
+          <!-- * put square brackets around the URL -->
           <xsl:text> [</xsl:text>
           <fo:basic-link external-destination="{$ulink.url}">
             <xsl:call-template name="hyphenate-url">
       </xsl:otherwise>
     </xsl:choose>
     <xsl:variable name="fnum">
+      <!-- * Determine the footnote number to display for this hyperlink, -->
+      <!-- * by counting all foonotes, ulinks, and any elements that have -->
+      <!-- * an xlink:href attribute that meets the following criteria: -->
+      <!-- * -->
+      <!-- * - the content of the element is not a URI that is the same -->
+      <!-- *   URI as the value of the href attribute -->
+      <!-- * - the href attribute is not an internal ID reference (does -->
+      <!-- *   not start with a hash sign) -->
+      <!-- * - the href is not part of an olink reference (the element -->
+      <!-- * - does not have an xlink:role attribute that indicates it is -->
+      <!-- *   an olink, and the href does not contain a hash sign) -->
+      <!-- * - the element either has no xlink:type attribute or has -->
+      <!-- *   an xlink:type attribute whose value is 'simple' -->
       <!-- FIXME: list in @from is probably not complete -->
       <xsl:number level="any" 
-                  from="chapter|appendix|preface|article|refentry|bibliography[not(parent::article)]" 
-                  count="footnote[not(@label)][not(ancestor::tgroup)]|ulink[node()][@url != .][not(ancestor::footnote)]" 
+                  from="chapter|appendix|preface|article|refentry|bibliography[not(parent::article)]"
+                  count="footnote[not(@label)][not(ancestor::tgroup)]
+                  |ulink[node()][@url != .][not(ancestor::footnote)]
+                  |*[node()][@xlink:href][not(@xlink:href = .)][not(starts-with(@xlink:href,'#'))]
+                    [not(contains(@xlink:href,'#') and @xlink:role = $xolink.role)]
+                    [not(@xlink:type) or @xlink:type='simple']
+                    [not(ancestor::footnote)]"
                   format="1"/>
     </xsl:variable>
     <xsl:choose>