]> git.evergreen-ils.org Git - working/Evergreen.git/blob - stylesheets/styleguide/docbook-xsl-1.75.2/common/common.xsl
stylesheet changes.
[working/Evergreen.git] / stylesheets / styleguide / docbook-xsl-1.75.2 / common / common.xsl
1 <?xml version='1.0'?>
2 <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
3                 xmlns:doc="http://nwalsh.com/xsl/documentation/1.0"
4                 xmlns:dyn="http://exslt.org/dynamic"
5                 xmlns:saxon="http://icl.com/saxon"
6                 exclude-result-prefixes="doc dyn saxon"
7                 version='1.0'>
8
9 <!-- ********************************************************************
10      $Id: common.xsl 8274 2009-02-27 07:02:45Z bobstayton $
11      ********************************************************************
12
13      This file is part of the XSL DocBook Stylesheet distribution.
14      See ../README or http://docbook.sf.net/release/xsl/current/ for
15      copyright and other information.
16
17      ******************************************************************** -->
18
19 <doc:reference xmlns="" xml:id="base">
20   <info>
21     <title>Common » Base Template Reference</title>
22     <releaseinfo role="meta">
23       $Id: common.xsl 8274 2009-02-27 07:02:45Z bobstayton $
24     </releaseinfo>
25   </info>
26   <!-- * yes, partintro is a valid child of a reference... -->
27   <partintro xml:id="partintro">
28     <title>Introduction</title>
29     <para>This is technical reference documentation for the “base”
30       set of common templates in the DocBook XSL Stylesheets.</para>
31     <para>This is not intended to be user documentation. It is
32       provided for developers writing customization layers for the
33       stylesheets.</para>
34   </partintro>
35 </doc:reference>
36
37 <!-- ==================================================================== -->
38 <!-- Establish strip/preserve whitespace rules -->
39
40 <xsl:preserve-space elements="*"/>
41
42 <xsl:strip-space elements="
43 abstract affiliation anchor answer appendix area areaset areaspec
44 artheader article audiodata audioobject author authorblurb authorgroup
45 beginpage bibliodiv biblioentry bibliography biblioset blockquote book
46 bookbiblio bookinfo callout calloutlist caption caution chapter
47 citerefentry cmdsynopsis co collab colophon colspec confgroup
48 copyright dedication docinfo editor entrytbl epigraph equation
49 example figure footnote footnoteref formalpara funcprototype
50 funcsynopsis glossary glossdef glossdiv glossentry glosslist graphicco
51 group highlights imagedata imageobject imageobjectco important index
52 indexdiv indexentry indexterm info informalequation informalexample
53 informalfigure informaltable inlineequation inlinemediaobject
54 itemizedlist itermset keycombo keywordset legalnotice listitem lot
55 mediaobject mediaobjectco menuchoice msg msgentry msgexplan msginfo
56 msgmain msgrel msgset msgsub msgtext note objectinfo
57 orderedlist othercredit part partintro preface printhistory procedure
58 programlistingco publisher qandadiv qandaentry qandaset question
59 refentry reference refmeta refnamediv refsection refsect1 refsect1info refsect2
60 refsect2info refsect3 refsect3info refsynopsisdiv refsynopsisdivinfo
61 revhistory revision row sbr screenco screenshot sect1 sect1info sect2
62 sect2info sect3 sect3info sect4 sect4info sect5 sect5info section
63 sectioninfo seglistitem segmentedlist seriesinfo set setindex setinfo
64 shortcut sidebar simplelist simplesect spanspec step subject
65 subjectset substeps synopfragment table tbody textobject tfoot tgroup
66 thead tip toc tocchap toclevel1 toclevel2 toclevel3 toclevel4
67 toclevel5 tocpart varargs variablelist varlistentry videodata
68 videoobject void warning subjectset
69
70 classsynopsis
71 constructorsynopsis
72 destructorsynopsis
73 fieldsynopsis
74 methodparam
75 methodsynopsis
76 ooclass
77 ooexception
78 oointerface
79 simplemsgentry
80 manvolnum
81 "/>
82 <!-- ====================================================================== -->
83
84 <doc:template name="is.component" xmlns="">
85 <refpurpose>Tests if a given node is a component-level element</refpurpose>
86
87 <refdescription id="is.component-desc">
88 <para>This template returns '1' if the specified node is a component
89 (Chapter, Appendix, etc.), and '0' otherwise.</para>
90 </refdescription>
91
92 <refparameter id="is.component-params">
93 <variablelist>
94 <varlistentry><term>node</term>
95 <listitem>
96 <para>The node which is to be tested.</para>
97 </listitem>
98 </varlistentry>
99 </variablelist>
100 </refparameter>
101
102 <refreturn id="is.component-returns">
103 <para>This template returns '1' if the specified node is a component
104 (Chapter, Appendix, etc.), and '0' otherwise.</para>
105 </refreturn>
106 </doc:template>
107
108 <xsl:template name="is.component">
109   <xsl:param name="node" select="."/>
110   <xsl:choose>
111     <xsl:when test="local-name($node) = 'appendix'
112                     or local-name($node) = 'article'
113                     or local-name($node) = 'chapter'
114                     or local-name($node) = 'preface'
115                     or local-name($node) = 'bibliography'
116                     or local-name($node) = 'glossary'
117                     or local-name($node) = 'index'">1</xsl:when>
118     <xsl:otherwise>0</xsl:otherwise>
119   </xsl:choose>
120 </xsl:template>
121
122 <!-- ====================================================================== -->
123
124 <doc:template name="is.section" xmlns="">
125 <refpurpose>Tests if a given node is a section-level element</refpurpose>
126
127 <refdescription id="is.section-desc">
128 <para>This template returns '1' if the specified node is a section
129 (Section, Sect1, Sect2, etc.), and '0' otherwise.</para>
130 </refdescription>
131
132 <refparameter id="is.section-params">
133 <variablelist>
134 <varlistentry><term>node</term>
135 <listitem>
136 <para>The node which is to be tested.</para>
137 </listitem>
138 </varlistentry>
139 </variablelist>
140 </refparameter>
141
142 <refreturn id="is.section-returns">
143 <para>This template returns '1' if the specified node is a section
144 (Section, Sect1, Sect2, etc.), and '0' otherwise.</para>
145 </refreturn>
146 </doc:template>
147
148 <xsl:template name="is.section">
149   <xsl:param name="node" select="."/>
150   <xsl:choose>
151     <xsl:when test="local-name($node) = 'section'
152                     or local-name($node) = 'sect1'
153                     or local-name($node) = 'sect2'
154                     or local-name($node) = 'sect3'
155                     or local-name($node) = 'sect4'
156                     or local-name($node) = 'sect5'
157                     or local-name($node) = 'refsect1'
158                     or local-name($node) = 'refsect2'
159                     or local-name($node) = 'refsect3'
160                     or local-name($node) = 'simplesect'">1</xsl:when>
161     <xsl:otherwise>0</xsl:otherwise>
162   </xsl:choose>
163 </xsl:template>
164
165 <!-- ====================================================================== -->
166
167 <doc:template name="section.level" xmlns="">
168 <refpurpose>Returns the hierarchical level of a section</refpurpose>
169
170 <refdescription id="section.level-desc">
171 <para>This template calculates the hierarchical level of a section.
172 The element <tag>sect1</tag> is at level 1, <tag>sect2</tag> is
173 at level 2, etc.</para>
174
175 <para>Recursive sections are calculated down to the fifth level.</para>
176 </refdescription>
177
178 <refparameter id="section.level-params">
179 <variablelist>
180 <varlistentry><term>node</term>
181 <listitem>
182 <para>The section node for which the level should be calculated.
183 Defaults to the context node.</para>
184 </listitem>
185 </varlistentry>
186 </variablelist>
187 </refparameter>
188
189 <refreturn id="section.level-returns">
190 <para>The section level, <quote>1</quote>, <quote>2</quote>, etc.
191 </para>
192 </refreturn>
193 </doc:template>
194
195 <xsl:template name="section.level">
196   <xsl:param name="node" select="."/>
197   <xsl:choose>
198     <xsl:when test="local-name($node)='sect1'">1</xsl:when>
199     <xsl:when test="local-name($node)='sect2'">2</xsl:when>
200     <xsl:when test="local-name($node)='sect3'">3</xsl:when>
201     <xsl:when test="local-name($node)='sect4'">4</xsl:when>
202     <xsl:when test="local-name($node)='sect5'">5</xsl:when>
203     <xsl:when test="local-name($node)='section'">
204       <xsl:choose>
205         <xsl:when test="$node/../../../../../../section">6</xsl:when>
206         <xsl:when test="$node/../../../../../section">5</xsl:when>
207         <xsl:when test="$node/../../../../section">4</xsl:when>
208         <xsl:when test="$node/../../../section">3</xsl:when>
209         <xsl:when test="$node/../../section">2</xsl:when>
210         <xsl:otherwise>1</xsl:otherwise>
211       </xsl:choose>
212     </xsl:when>
213     <xsl:when test="local-name($node)='refsect1' or
214                     local-name($node)='refsect2' or
215                     local-name($node)='refsect3' or
216                     local-name($node)='refsection' or
217                     local-name($node)='refsynopsisdiv'">
218       <xsl:call-template name="refentry.section.level">
219         <xsl:with-param name="node" select="$node"/>
220       </xsl:call-template>
221     </xsl:when>
222     <xsl:when test="local-name($node)='simplesect'">
223       <xsl:choose>
224         <xsl:when test="$node/../../sect1">2</xsl:when>
225         <xsl:when test="$node/../../sect2">3</xsl:when>
226         <xsl:when test="$node/../../sect3">4</xsl:when>
227         <xsl:when test="$node/../../sect4">5</xsl:when>
228         <xsl:when test="$node/../../sect5">5</xsl:when>
229         <xsl:when test="$node/../../section">
230           <xsl:choose>
231             <xsl:when test="$node/../../../../../section">5</xsl:when>
232             <xsl:when test="$node/../../../../section">4</xsl:when>
233             <xsl:when test="$node/../../../section">3</xsl:when>
234             <xsl:otherwise>2</xsl:otherwise>
235           </xsl:choose>
236         </xsl:when>
237         <xsl:otherwise>1</xsl:otherwise>
238       </xsl:choose>
239     </xsl:when>
240     <xsl:otherwise>1</xsl:otherwise>
241   </xsl:choose>
242 </xsl:template><!-- section.level -->
243
244 <doc:template name="qanda.section.level" xmlns="">
245 <refpurpose>Returns the hierarchical level of a QandASet</refpurpose>
246
247 <refdescription id="qanda.section.level-desc">
248 <para>This template calculates the hierarchical level of a QandASet.
249 </para>
250 </refdescription>
251
252 <refreturn id="qanda.section.level-returns">
253 <para>The level, <quote>1</quote>, <quote>2</quote>, etc.
254 </para>
255 </refreturn>
256 </doc:template>
257
258 <xsl:template name="qanda.section.level">
259   <xsl:variable name="section"
260                 select="(ancestor::section
261                          |ancestor::simplesect
262                          |ancestor::sect5
263                          |ancestor::sect4
264                          |ancestor::sect3
265                          |ancestor::sect2
266                          |ancestor::sect1
267                          |ancestor::refsect3
268                          |ancestor::refsect2
269                          |ancestor::refsect1)[last()]"/>
270
271   <xsl:choose>
272     <xsl:when test="count($section) = '0'">1</xsl:when>
273     <xsl:otherwise>
274       <xsl:variable name="slevel">
275         <xsl:call-template name="section.level">
276           <xsl:with-param name="node" select="$section"/>
277         </xsl:call-template>
278       </xsl:variable>
279       <xsl:value-of select="$slevel + 1"/>
280     </xsl:otherwise>
281   </xsl:choose>
282 </xsl:template>
283
284 <!-- Finds the total section depth of a section in a refentry -->
285 <xsl:template name="refentry.section.level">
286   <xsl:param name="node" select="."/>
287
288   <xsl:variable name="RElevel">
289     <xsl:call-template name="refentry.level">
290       <xsl:with-param name="node" select="$node/ancestor::refentry[1]"/>
291     </xsl:call-template>
292   </xsl:variable>
293
294   <xsl:variable name="levelinRE">
295     <xsl:choose>
296       <xsl:when test="local-name($node)='refsynopsisdiv'">1</xsl:when>
297       <xsl:when test="local-name($node)='refsect1'">1</xsl:when>
298       <xsl:when test="local-name($node)='refsect2'">2</xsl:when>
299       <xsl:when test="local-name($node)='refsect3'">3</xsl:when>
300       <xsl:when test="local-name($node)='refsection'">
301         <xsl:choose>
302           <xsl:when test="$node/../../../../../refsection">5</xsl:when>
303           <xsl:when test="$node/../../../../refsection">4</xsl:when>
304           <xsl:when test="$node/../../../refsection">3</xsl:when>
305           <xsl:when test="$node/../../refsection">2</xsl:when>
306           <xsl:otherwise>1</xsl:otherwise>
307         </xsl:choose>
308       </xsl:when>
309     </xsl:choose>
310   </xsl:variable>
311
312   <xsl:value-of select="$levelinRE + $RElevel"/>
313 </xsl:template>
314
315 <!-- Finds the section depth of a refentry -->
316 <xsl:template name="refentry.level">
317   <xsl:param name="node" select="."/>
318   <xsl:variable name="container"
319                 select="($node/ancestor::section |
320                         $node/ancestor::sect1 |
321                         $node/ancestor::sect2 |
322                         $node/ancestor::sect3 |
323                         $node/ancestor::sect4 |
324                         $node/ancestor::sect5)[last()]"/>
325
326   <xsl:choose>
327     <xsl:when test="$container">
328       <xsl:variable name="slevel">
329         <xsl:call-template name="section.level">
330           <xsl:with-param name="node" select="$container"/>
331         </xsl:call-template>
332       </xsl:variable>
333       <xsl:value-of select="$slevel + 1"/>
334     </xsl:when>
335     <xsl:otherwise>1</xsl:otherwise>
336   </xsl:choose>
337 </xsl:template>
338
339 <xsl:template name="qandadiv.section.level">
340   <xsl:variable name="section.level">
341     <xsl:call-template name="qanda.section.level"/>
342   </xsl:variable>
343   <xsl:variable name="anc.divs" select="ancestor::qandadiv"/>
344
345   <xsl:value-of select="count($anc.divs) + number($section.level)"/>
346 </xsl:template>
347
348 <xsl:template name="question.answer.label">
349   <xsl:variable name="deflabel">
350     <xsl:choose>
351       <xsl:when test="ancestor-or-self::*[@defaultlabel]">
352         <xsl:value-of select="(ancestor-or-self::*[@defaultlabel])[last()]
353                               /@defaultlabel"/>
354       </xsl:when>
355       <xsl:otherwise>
356         <xsl:value-of select="$qanda.defaultlabel"/>
357       </xsl:otherwise>
358     </xsl:choose>
359   </xsl:variable>
360
361   <xsl:variable name="label" select="@label"/>
362
363 <!--
364  (hnr      (hierarchical-number-recursive (normalize "qandadiv") node))
365
366          (parsect  (ancestor-member node (section-element-list)))
367
368          (defnum   (if (and %qanda-inherit-numeration% 
369                             %section-autolabel%)
370                        (if (node-list-empty? parsect)
371                            (section-autolabel-prefix node)
372                            (section-autolabel parsect))
373                        ""))
374
375          (hnumber  (let loop ((numlist hnr) (number defnum) 
376                               (sep (if (equal? defnum "") "" ".")))
377                      (if (null? numlist)
378                          number
379                          (loop (cdr numlist) 
380                                (string-append number
381                                               sep
382                                               (number->string (car numlist)))
383                                "."))))
384          (cnumber  (child-number (parent node)))
385          (number   (string-append hnumber 
386                                   (if (equal? hnumber "")
387                                       ""
388                                       ".")
389                                   (number->string cnumber))))
390 -->
391
392   <xsl:choose>
393     <xsl:when test="$deflabel = 'qanda'">
394       <xsl:call-template name="gentext">
395         <xsl:with-param name="key">
396           <xsl:choose>
397             <xsl:when test="local-name(.) = 'question'">question</xsl:when>
398             <xsl:when test="local-name(.) = 'answer'">answer</xsl:when>
399             <xsl:when test="local-name(.) = 'qandadiv'">qandadiv</xsl:when>
400             <xsl:otherwise>qandaset</xsl:otherwise>
401           </xsl:choose>
402         </xsl:with-param>
403       </xsl:call-template>
404     </xsl:when>
405     <xsl:when test="$deflabel = 'label'">
406       <xsl:value-of select="$label"/>
407     </xsl:when>
408     <xsl:when test="$deflabel = 'number'
409                     and local-name(.) = 'question'">
410       <xsl:apply-templates select="ancestor::qandaset[1]"
411                            mode="number"/>
412       <xsl:choose>
413         <xsl:when test="ancestor::qandadiv">
414           <xsl:apply-templates select="ancestor::qandadiv[1]"
415                                mode="number"/>
416           <xsl:apply-templates select="ancestor::qandaentry"
417                                mode="number"/>
418         </xsl:when>
419         <xsl:otherwise>
420           <xsl:apply-templates select="ancestor::qandaentry"
421                                mode="number"/>
422         </xsl:otherwise>
423       </xsl:choose>
424     </xsl:when>
425     <xsl:otherwise>
426       <!-- nothing -->
427     </xsl:otherwise>
428   </xsl:choose>
429 </xsl:template>
430
431 <xsl:template match="qandaset" mode="number">
432   <!-- FIXME: -->
433 </xsl:template>
434
435 <xsl:template match="qandadiv" mode="number">
436   <xsl:number level="multiple" from="qandaset" format="1."/>
437 </xsl:template>
438
439 <xsl:template match="qandaentry" mode="number">
440   <xsl:choose>
441     <xsl:when test="ancestor::qandadiv">
442       <xsl:number level="single" from="qandadiv" format="1."/>
443     </xsl:when>
444     <xsl:otherwise>
445       <xsl:number level="single" from="qandaset" format="1."/>
446     </xsl:otherwise>
447   </xsl:choose>
448 </xsl:template>
449
450 <!-- ====================================================================== -->
451
452 <xsl:template name="object.id">
453   <xsl:param name="object" select="."/>
454   <xsl:choose>
455     <xsl:when test="$object/@id">
456       <xsl:value-of select="$object/@id"/>
457     </xsl:when>
458     <xsl:when test="$object/@xml:id">
459       <xsl:value-of select="$object/@xml:id"/>
460     </xsl:when>
461     <xsl:otherwise>
462       <xsl:value-of select="generate-id($object)"/>
463     </xsl:otherwise>
464   </xsl:choose>
465 </xsl:template>
466
467 <xsl:template name="person.name">
468   <!-- Formats a personal name. Handles corpauthor as a special case. -->
469   <xsl:param name="node" select="."/>
470
471   <xsl:variable name="style">
472     <xsl:choose>
473       <xsl:when test="$node/@role">
474         <xsl:value-of select="$node/@role"/>
475       </xsl:when>
476       <xsl:otherwise>
477         <xsl:call-template name="gentext.template">
478           <xsl:with-param name="context" select="'styles'"/>
479           <xsl:with-param name="name" select="'person-name'"/>
480         </xsl:call-template>
481       </xsl:otherwise>
482     </xsl:choose>
483   </xsl:variable>
484
485   <xsl:choose>
486     <!-- the personname element is a specialcase -->
487     <xsl:when test="$node/personname">
488       <xsl:call-template name="person.name">
489         <xsl:with-param name="node" select="$node/personname"/>
490       </xsl:call-template>
491     </xsl:when>
492
493     <!-- handle corpauthor as a special case...-->
494     <!-- * MikeSmith 2007-06: I'm wondering if the person.name template -->
495     <!-- * actually ever gets called to handle corpauthor.. maybe -->
496     <!-- * we don't actually need to check for corpauthor here. -->
497     <xsl:when test="local-name($node)='corpauthor'">
498       <xsl:apply-templates select="$node"/>
499     </xsl:when>
500
501     <xsl:otherwise>
502       <xsl:choose>
503         <!-- Handle case when personname contains only general markup (DocBook 5.0) -->
504         <xsl:when test="$node/self::personname and not($node/firstname or $node/honorific or $node/lineage or $node/othername or $node/surname)">
505           <xsl:apply-templates select="$node/node()"/>
506         </xsl:when>
507         <xsl:when test="$style = 'family-given'">
508           <xsl:call-template name="person.name.family-given">
509             <xsl:with-param name="node" select="$node"/>
510           </xsl:call-template>
511         </xsl:when>
512         <xsl:when test="$style = 'last-first'">
513           <xsl:call-template name="person.name.last-first">
514             <xsl:with-param name="node" select="$node"/>
515           </xsl:call-template>
516         </xsl:when>
517         <xsl:otherwise>
518           <xsl:call-template name="person.name.first-last">
519             <xsl:with-param name="node" select="$node"/>
520           </xsl:call-template>
521         </xsl:otherwise>
522       </xsl:choose>
523     </xsl:otherwise>
524   </xsl:choose>
525 </xsl:template>
526
527 <xsl:template name="person.name.family-given">
528   <xsl:param name="node" select="."/>
529
530   <!-- The family-given style applies a convention for identifying given -->
531   <!-- and family names in locales where it may be ambiguous -->
532   <xsl:apply-templates select="$node//surname[1]"/>
533
534   <xsl:if test="$node//surname and $node//firstname">
535     <xsl:text> </xsl:text>
536   </xsl:if>
537
538   <xsl:apply-templates select="$node//firstname[1]"/>
539
540   <xsl:text> [FAMILY Given]</xsl:text>
541 </xsl:template>
542
543 <xsl:template name="person.name.last-first">
544   <xsl:param name="node" select="."/>
545
546   <xsl:apply-templates select="$node//surname[1]"/>
547
548   <xsl:if test="$node//surname and $node//firstname">
549     <xsl:text>, </xsl:text>
550   </xsl:if>
551
552   <xsl:apply-templates select="$node//firstname[1]"/>
553 </xsl:template>
554
555 <xsl:template name="person.name.first-last">
556   <xsl:param name="node" select="."/>
557
558   <xsl:if test="$node//honorific">
559     <xsl:apply-templates select="$node//honorific[1]"/>
560     <xsl:value-of select="$punct.honorific"/>
561   </xsl:if>
562
563   <xsl:if test="$node//firstname">
564     <xsl:if test="$node//honorific">
565       <xsl:text> </xsl:text>
566     </xsl:if>
567     <xsl:apply-templates select="$node//firstname[1]"/>
568   </xsl:if>
569
570   <xsl:if test="$node//othername and $author.othername.in.middle != 0">
571     <xsl:if test="$node//honorific or $node//firstname">
572       <xsl:text> </xsl:text>
573     </xsl:if>
574     <xsl:apply-templates select="$node//othername[1]"/>
575   </xsl:if>
576
577   <xsl:if test="$node//surname">
578     <xsl:if test="$node//honorific or $node//firstname
579                   or ($node//othername and $author.othername.in.middle != 0)">
580       <xsl:text> </xsl:text>
581     </xsl:if>
582     <xsl:apply-templates select="$node//surname[1]"/>
583   </xsl:if>
584
585   <xsl:if test="$node//lineage">
586     <xsl:text>, </xsl:text>
587     <xsl:apply-templates select="$node//lineage[1]"/>
588   </xsl:if>
589 </xsl:template>
590
591 <xsl:template name="person.name.list">
592   <!-- Return a formatted string representation of the contents of
593        the current element. The current element must contain one or
594        more AUTHORs, CORPAUTHORs, OTHERCREDITs, and/or EDITORs.
595
596        John Doe
597      or
598        John Doe and Jane Doe
599      or
600        John Doe, Jane Doe, and A. Nonymous
601   -->
602   <xsl:param name="person.list"
603              select="author|corpauthor|othercredit|editor"/>
604   <xsl:param name="person.count" select="count($person.list)"/>
605   <xsl:param name="count" select="1"/>
606
607   <xsl:choose>
608     <xsl:when test="$count &gt; $person.count"></xsl:when>
609     <xsl:otherwise>
610       <xsl:call-template name="person.name">
611         <xsl:with-param name="node" select="$person.list[position()=$count]"/>
612       </xsl:call-template>
613
614       <xsl:choose>
615         <xsl:when test="$person.count = 2 and $count = 1">
616           <xsl:call-template name="gentext.template">
617             <xsl:with-param name="context" select="'authorgroup'"/>
618             <xsl:with-param name="name" select="'sep2'"/>
619           </xsl:call-template>
620         </xsl:when>
621         <xsl:when test="$person.count &gt; 2 and $count+1 = $person.count">
622           <xsl:call-template name="gentext.template">
623             <xsl:with-param name="context" select="'authorgroup'"/>
624             <xsl:with-param name="name" select="'seplast'"/>
625           </xsl:call-template>
626         </xsl:when>
627         <xsl:when test="$count &lt; $person.count">
628           <xsl:call-template name="gentext.template">
629             <xsl:with-param name="context" select="'authorgroup'"/>
630             <xsl:with-param name="name" select="'sep'"/>
631           </xsl:call-template>
632         </xsl:when>
633       </xsl:choose>
634
635       <xsl:call-template name="person.name.list">
636         <xsl:with-param name="person.list" select="$person.list"/>
637         <xsl:with-param name="person.count" select="$person.count"/>
638         <xsl:with-param name="count" select="$count+1"/>
639       </xsl:call-template>
640     </xsl:otherwise>
641   </xsl:choose>
642 </xsl:template><!-- person.name.list -->
643
644 <!-- === synopsis ======================================================= -->
645 <!-- The following definitions match those given in the reference
646      documentation for DocBook V3.0
647 -->
648
649 <xsl:variable name="arg.choice.opt.open.str">[</xsl:variable>
650 <xsl:variable name="arg.choice.opt.close.str">]</xsl:variable>
651 <xsl:variable name="arg.choice.req.open.str">{</xsl:variable>
652 <xsl:variable name="arg.choice.req.close.str">}</xsl:variable>
653 <xsl:variable name="arg.choice.plain.open.str"><xsl:text> </xsl:text></xsl:variable>
654 <xsl:variable name="arg.choice.plain.close.str"><xsl:text> </xsl:text></xsl:variable>
655 <xsl:variable name="arg.choice.def.open.str">[</xsl:variable>
656 <xsl:variable name="arg.choice.def.close.str">]</xsl:variable>
657 <xsl:variable name="arg.rep.repeat.str">...</xsl:variable>
658 <xsl:variable name="arg.rep.norepeat.str"></xsl:variable>
659 <xsl:variable name="arg.rep.def.str"></xsl:variable>
660 <xsl:variable name="arg.or.sep"> | </xsl:variable>
661 <xsl:variable name="cmdsynopsis.hanging.indent">4pi</xsl:variable>
662
663 <!-- ====================================================================== -->
664
665 <!--
666 <xsl:template name="xref.g.subst">
667   <xsl:param name="string"></xsl:param>
668   <xsl:param name="target" select="."/>
669   <xsl:variable name="subst">%g</xsl:variable>
670
671   <xsl:choose>
672     <xsl:when test="contains($string, $subst)">
673       <xsl:value-of select="substring-before($string, $subst)"/>
674       <xsl:call-template name="gentext.element.name">
675         <xsl:with-param name="element.name" select="local-name($target)"/>
676       </xsl:call-template>
677       <xsl:call-template name="xref.g.subst">
678         <xsl:with-param name="string"
679                         select="substring-after($string, $subst)"/>
680         <xsl:with-param name="target" select="$target"/>
681       </xsl:call-template>
682     </xsl:when>
683     <xsl:otherwise>
684       <xsl:value-of select="$string"/>
685     </xsl:otherwise>
686   </xsl:choose>
687 </xsl:template>
688
689 <xsl:template name="xref.t.subst">
690   <xsl:param name="string"></xsl:param>
691   <xsl:param name="target" select="."/>
692   <xsl:variable name="subst">%t</xsl:variable>
693
694   <xsl:choose>
695     <xsl:when test="contains($string, $subst)">
696       <xsl:call-template name="xref.g.subst">
697         <xsl:with-param name="string"
698                         select="substring-before($string, $subst)"/>
699         <xsl:with-param name="target" select="$target"/>
700       </xsl:call-template>
701       <xsl:call-template name="title.xref">
702         <xsl:with-param name="target" select="$target"/>
703       </xsl:call-template>
704       <xsl:call-template name="xref.t.subst">
705         <xsl:with-param name="string"
706                         select="substring-after($string, $subst)"/>
707         <xsl:with-param name="target" select="$target"/>
708       </xsl:call-template>
709     </xsl:when>
710     <xsl:otherwise>
711       <xsl:call-template name="xref.g.subst">
712         <xsl:with-param name="string" select="$string"/>
713         <xsl:with-param name="target" select="$target"/>
714       </xsl:call-template>
715     </xsl:otherwise>
716   </xsl:choose>
717 </xsl:template>
718
719 <xsl:template name="xref.n.subst">
720   <xsl:param name="string"></xsl:param>
721   <xsl:param name="target" select="."/>
722   <xsl:variable name="subst">%n</xsl:variable>
723
724   <xsl:choose>
725     <xsl:when test="contains($string, $subst)">
726       <xsl:call-template name="xref.t.subst">
727         <xsl:with-param name="string"
728                         select="substring-before($string, $subst)"/>
729         <xsl:with-param name="target" select="$target"/>
730       </xsl:call-template>
731       <xsl:call-template name="number.xref">
732         <xsl:with-param name="target" select="$target"/>
733       </xsl:call-template>
734       <xsl:call-template name="xref.t.subst">
735         <xsl:with-param name="string"
736                         select="substring-after($string, $subst)"/>
737         <xsl:with-param name="target" select="$target"/>
738       </xsl:call-template>
739     </xsl:when>
740     <xsl:otherwise>
741       <xsl:call-template name="xref.t.subst">
742         <xsl:with-param name="string" select="$string"/>
743         <xsl:with-param name="target" select="$target"/>
744       </xsl:call-template>
745     </xsl:otherwise>
746   </xsl:choose>
747 </xsl:template>
748
749 <xsl:template name="subst.xref.text">
750   <xsl:param name="xref.text"></xsl:param>
751   <xsl:param name="target" select="."/>
752
753   <xsl:call-template name="xref.n.subst">
754     <xsl:with-param name="string" select="$xref.text"/>
755     <xsl:with-param name="target" select="$target"/>
756   </xsl:call-template>
757 </xsl:template>
758 -->
759
760 <!-- ====================================================================== -->
761
762 <xsl:template name="filename-basename">
763   <!-- We assume all filenames are really URIs and use "/" -->
764   <xsl:param name="filename"></xsl:param>
765   <xsl:param name="recurse" select="false()"/>
766
767   <xsl:choose>
768     <xsl:when test="substring-after($filename, '/') != ''">
769       <xsl:call-template name="filename-basename">
770         <xsl:with-param name="filename"
771                         select="substring-after($filename, '/')"/>
772         <xsl:with-param name="recurse" select="true()"/>
773       </xsl:call-template>
774     </xsl:when>
775     <xsl:otherwise>
776       <xsl:value-of select="$filename"/>
777     </xsl:otherwise>
778   </xsl:choose>
779 </xsl:template>
780
781 <xsl:template name="filename-extension">
782   <xsl:param name="filename"></xsl:param>
783   <xsl:param name="recurse" select="false()"/>
784
785   <!-- Make sure we only look at the base name... -->
786   <xsl:variable name="basefn">
787     <xsl:choose>
788       <xsl:when test="$recurse">
789         <xsl:value-of select="$filename"/>
790       </xsl:when>
791       <xsl:otherwise>
792         <xsl:call-template name="filename-basename">
793           <xsl:with-param name="filename" select="$filename"/>
794         </xsl:call-template>
795       </xsl:otherwise>
796     </xsl:choose>
797   </xsl:variable>
798
799   <xsl:choose>
800     <xsl:when test="substring-after($basefn, '.') != ''">
801       <xsl:call-template name="filename-extension">
802         <xsl:with-param name="filename"
803                         select="substring-after($basefn, '.')"/>
804         <xsl:with-param name="recurse" select="true()"/>
805       </xsl:call-template>
806     </xsl:when>
807     <xsl:when test="$recurse">
808       <xsl:value-of select="$basefn"/>
809     </xsl:when>
810     <xsl:otherwise></xsl:otherwise>
811   </xsl:choose>
812 </xsl:template>
813
814 <!-- ====================================================================== -->
815
816 <doc:template name="select.mediaobject" xmlns="">
817 <refpurpose>Selects and processes an appropriate media object from a list</refpurpose>
818
819 <refdescription id="select.mediaobject-desc">
820 <para>This template takes a list of media objects (usually the
821 children of a mediaobject or inlinemediaobject) and processes
822 the "right" object.</para>
823
824 <para>This template relies on a template named 
825 "select.mediaobject.index" to determine which object
826 in the list is appropriate.</para>
827
828 <para>If no acceptable object is located, nothing happens.</para>
829 </refdescription>
830
831 <refparameter id="select.mediaobject-params">
832 <variablelist>
833 <varlistentry><term>olist</term>
834 <listitem>
835 <para>The node list of potential objects to examine.</para>
836 </listitem>
837 </varlistentry>
838 </variablelist>
839 </refparameter>
840
841 <refreturn id="select.mediaobject-returns">
842 <para>Calls &lt;xsl:apply-templates&gt; on the selected object.</para>
843 </refreturn>
844 </doc:template>
845
846 <xsl:template name="select.mediaobject">
847   <xsl:param name="olist"
848              select="imageobject|imageobjectco
849                      |videoobject|audioobject|textobject"/>
850   
851   <xsl:variable name="mediaobject.index">
852     <xsl:call-template name="select.mediaobject.index">
853       <xsl:with-param name="olist" select="$olist"/>
854       <xsl:with-param name="count" select="1"/>
855     </xsl:call-template>
856   </xsl:variable>
857
858   <xsl:if test="$mediaobject.index != ''">
859     <xsl:apply-templates select="$olist[position() = $mediaobject.index]"/>
860   </xsl:if>
861 </xsl:template>
862
863 <!-- ====================================================================== -->
864
865 <doc:template name="select.mediaobject.index" xmlns="">
866 <refpurpose>Selects the position of the appropriate media object from a list</refpurpose>
867
868 <refdescription id="select.mediaobject.index-desc">
869 <para>This template takes a list of media objects (usually the
870 children of a mediaobject or inlinemediaobject) and determines
871 the "right" object. It returns the position of that object
872 to be used by the calling template.</para>
873
874 <para>If the parameter <parameter>use.role.for.mediaobject</parameter>
875 is nonzero, then it first checks for an object with
876 a role attribute of the appropriate value.  It takes the first
877 of those.  Otherwise, it takes the first acceptable object
878 through a recursive pass through the list.</para>
879
880 <para>This template relies on a template named "is.acceptable.mediaobject"
881 to determine if a given object is an acceptable graphic. The semantics
882 of media objects is that the first acceptable graphic should be used.
883 </para>
884
885 <para>If no acceptable object is located, no index is returned.</para>
886 </refdescription>
887
888 <refparameter id="select.mediaobject.index-params">
889 <variablelist>
890 <varlistentry><term>olist</term>
891 <listitem>
892 <para>The node list of potential objects to examine.</para>
893 </listitem>
894 </varlistentry>
895 <varlistentry><term>count</term>
896 <listitem>
897 <para>The position in the list currently being considered by the 
898 recursive process.</para>
899 </listitem>
900 </varlistentry>
901 </variablelist>
902 </refparameter>
903
904 <refreturn id="select.mediaobject.index-returns">
905 <para>Returns the position in the original list of the selected object.</para>
906 </refreturn>
907 </doc:template>
908
909 <xsl:template name="select.mediaobject.index">
910   <xsl:param name="olist"
911              select="imageobject|imageobjectco
912                      |videoobject|audioobject|textobject"/>
913   <xsl:param name="count">1</xsl:param>
914
915   <xsl:choose>
916     <!-- Test for objects preferred by role -->
917     <xsl:when test="$use.role.for.mediaobject != 0 
918                and $preferred.mediaobject.role != ''
919                and $olist[@role = $preferred.mediaobject.role]"> 
920       
921       <!-- Get the first hit's position index -->
922       <xsl:for-each select="$olist">
923         <xsl:if test="@role = $preferred.mediaobject.role and
924              not(preceding-sibling::*[@role = $preferred.mediaobject.role])"> 
925           <xsl:value-of select="position()"/> 
926         </xsl:if>
927       </xsl:for-each>
928     </xsl:when>
929
930     <xsl:when test="$use.role.for.mediaobject != 0 
931                and $olist[@role = $stylesheet.result.type]">
932       <!-- Get the first hit's position index -->
933       <xsl:for-each select="$olist">
934         <xsl:if test="@role = $stylesheet.result.type and 
935               not(preceding-sibling::*[@role = $stylesheet.result.type])"> 
936           <xsl:value-of select="position()"/> 
937         </xsl:if>
938       </xsl:for-each>
939     </xsl:when>
940     <!-- Accept 'html' for $stylesheet.result.type = 'xhtml' -->
941     <xsl:when test="$use.role.for.mediaobject != 0 
942                and $stylesheet.result.type = 'xhtml'
943                and $olist[@role = 'html']">
944       <!-- Get the first hit's position index -->
945       <xsl:for-each select="$olist">
946         <xsl:if test="@role = 'html' and 
947               not(preceding-sibling::*[@role = 'html'])"> 
948           <xsl:value-of select="position()"/> 
949         </xsl:if>
950       </xsl:for-each>
951     </xsl:when>
952
953     <!-- If no selection by role, and there is only one object, use it -->
954     <xsl:when test="count($olist) = 1 and $count = 1">
955       <xsl:value-of select="$count"/> 
956     </xsl:when>
957
958     <xsl:otherwise>
959       <!-- Otherwise select first acceptable object -->
960       <xsl:if test="$count &lt;= count($olist)">
961         <xsl:variable name="object" select="$olist[position()=$count]"/>
962     
963         <xsl:variable name="useobject">
964           <xsl:choose>
965             <!-- The phrase is used only when contains TeX Math and output is FO -->
966             <xsl:when test="local-name($object)='textobject' and $object/phrase
967                             and $object/@role='tex' and $stylesheet.result.type = 'fo'
968                             and $tex.math.in.alt != ''">
969               <xsl:text>1</xsl:text> 
970             </xsl:when>
971             <!-- The phrase is never used -->
972             <xsl:when test="local-name($object)='textobject' and $object/phrase">
973               <xsl:text>0</xsl:text>
974             </xsl:when>
975             <xsl:when test="local-name($object)='textobject'
976                             and $object/ancestor::equation ">
977             <!-- The first textobject is not a reasonable fallback
978                  for equation image -->
979               <xsl:text>0</xsl:text>
980             </xsl:when>
981             <!-- The first textobject is a reasonable fallback -->
982             <xsl:when test="local-name($object)='textobject'
983                             and $object[not(@role) or @role!='tex']">
984               <xsl:text>1</xsl:text>
985             </xsl:when>
986             <!-- don't use graphic when output is FO, TeX Math is used 
987                  and there is math in alt element -->
988             <xsl:when test="$object/ancestor::equation and 
989                             $object/ancestor::equation/alt[@role='tex']
990                             and $stylesheet.result.type = 'fo'
991                             and $tex.math.in.alt != ''">
992               <xsl:text>0</xsl:text>
993             </xsl:when>
994             <!-- If there's only one object, use it -->
995             <xsl:when test="$count = 1 and count($olist) = 1">
996                <xsl:text>1</xsl:text>
997             </xsl:when>
998             <!-- Otherwise, see if this one is a useable graphic -->
999             <xsl:otherwise>
1000               <xsl:choose>
1001                 <!-- peek inside imageobjectco to simplify the test -->
1002                 <xsl:when test="local-name($object) = 'imageobjectco'">
1003                   <xsl:call-template name="is.acceptable.mediaobject">
1004                     <xsl:with-param name="object" select="$object/imageobject"/>
1005                   </xsl:call-template>
1006                 </xsl:when>
1007                 <xsl:otherwise>
1008                   <xsl:call-template name="is.acceptable.mediaobject">
1009                     <xsl:with-param name="object" select="$object"/>
1010                   </xsl:call-template>
1011                 </xsl:otherwise>
1012               </xsl:choose>
1013             </xsl:otherwise>
1014           </xsl:choose>
1015         </xsl:variable>
1016     
1017         <xsl:choose>
1018           <xsl:when test="$useobject='1'">
1019             <xsl:value-of select="$count"/>
1020           </xsl:when>
1021           <xsl:otherwise>
1022             <xsl:call-template name="select.mediaobject.index">
1023               <xsl:with-param name="olist" select="$olist"/>
1024               <xsl:with-param name="count" select="$count + 1"/>
1025             </xsl:call-template>
1026           </xsl:otherwise>
1027         </xsl:choose>
1028       </xsl:if>
1029     </xsl:otherwise>
1030   </xsl:choose>
1031 </xsl:template>
1032
1033 <doc:template name="is.acceptable.mediaobject" xmlns="">
1034 <refpurpose>Returns '1' if the specified media object is recognized</refpurpose>
1035
1036 <refdescription id="is.acceptable.mediaobject-desc">
1037 <para>This template examines a media object and returns '1' if the
1038 object is recognized as a graphic.</para>
1039 </refdescription>
1040
1041 <refparameter id="is.acceptable.mediaobject-params">
1042 <variablelist>
1043 <varlistentry><term>object</term>
1044 <listitem>
1045 <para>The media object to consider.</para>
1046 </listitem>
1047 </varlistentry>
1048 </variablelist>
1049 </refparameter>
1050
1051 <refreturn id="is.acceptable.mediaobject-returns">
1052 <para>0 or 1</para>
1053 </refreturn>
1054 </doc:template>
1055
1056 <xsl:template name="is.acceptable.mediaobject">
1057   <xsl:param name="object"></xsl:param>
1058
1059   <xsl:variable name="filename">
1060     <xsl:call-template name="mediaobject.filename">
1061       <xsl:with-param name="object" select="$object"/>
1062     </xsl:call-template>
1063   </xsl:variable>
1064
1065   <xsl:variable name="ext">
1066     <xsl:call-template name="filename-extension">
1067       <xsl:with-param name="filename" select="$filename"/>
1068     </xsl:call-template>
1069   </xsl:variable>
1070
1071   <!-- there will only be one -->
1072   <xsl:variable name="data" select="$object/videodata
1073                                     |$object/imagedata
1074                                     |$object/audiodata"/>
1075
1076   <xsl:variable name="format" select="$data/@format"/>
1077
1078   <xsl:variable name="graphic.format">
1079     <xsl:if test="$format">
1080       <xsl:call-template name="is.graphic.format">
1081         <xsl:with-param name="format" select="$format"/>
1082       </xsl:call-template>
1083     </xsl:if>
1084   </xsl:variable>
1085
1086   <xsl:variable name="graphic.ext">
1087     <xsl:if test="$ext">
1088       <xsl:call-template name="is.graphic.extension">
1089         <xsl:with-param name="ext" select="$ext"/>
1090       </xsl:call-template>
1091     </xsl:if>
1092   </xsl:variable>
1093
1094   <xsl:choose>
1095     <xsl:when test="$use.svg = 0 and $format = 'SVG'">0</xsl:when>
1096     <xsl:when xmlns:svg="http://www.w3.org/2000/svg"
1097               test="$use.svg != 0 and $object/svg:*">1</xsl:when>
1098     <xsl:when test="$graphic.format = '1'">1</xsl:when>
1099     <xsl:when test="$graphic.ext = '1'">1</xsl:when>
1100     <xsl:otherwise>0</xsl:otherwise>
1101   </xsl:choose>
1102 </xsl:template>
1103
1104 <xsl:template name="mediaobject.filename">
1105   <xsl:param name="object"></xsl:param>
1106
1107   <xsl:variable name="data" select="$object/videodata
1108                                     |$object/imagedata
1109                                     |$object/audiodata
1110                                     |$object"/>
1111
1112   <xsl:variable name="filename">
1113     <xsl:choose>
1114       <xsl:when test="$data[@fileref]">
1115         <xsl:apply-templates select="$data/@fileref"/>
1116       </xsl:when>
1117       <xsl:when test="$data[@entityref]">
1118         <xsl:value-of select="unparsed-entity-uri($data/@entityref)"/>
1119       </xsl:when>
1120       <xsl:otherwise></xsl:otherwise>
1121     </xsl:choose>
1122   </xsl:variable>
1123
1124   <xsl:variable name="real.ext">
1125     <xsl:call-template name="filename-extension">
1126       <xsl:with-param name="filename" select="$filename"/>
1127     </xsl:call-template>
1128   </xsl:variable>
1129
1130   <xsl:variable name="ext">
1131     <xsl:choose>
1132       <xsl:when test="$real.ext != ''">
1133         <xsl:value-of select="$real.ext"/>
1134       </xsl:when>
1135       <xsl:otherwise>
1136         <xsl:value-of select="$graphic.default.extension"/>
1137       </xsl:otherwise>
1138     </xsl:choose>
1139   </xsl:variable>
1140
1141   <xsl:variable name="graphic.ext">
1142     <xsl:call-template name="is.graphic.extension">
1143       <xsl:with-param name="ext" select="$ext"/>
1144     </xsl:call-template>
1145   </xsl:variable>
1146
1147   <xsl:choose>
1148     <xsl:when test="$real.ext = ''">
1149       <xsl:choose>
1150         <xsl:when test="$ext != ''">
1151           <xsl:value-of select="$filename"/>
1152           <xsl:text>.</xsl:text>
1153           <xsl:value-of select="$ext"/>
1154         </xsl:when>
1155         <xsl:otherwise>
1156           <xsl:value-of select="$filename"/>
1157         </xsl:otherwise>
1158       </xsl:choose>
1159     </xsl:when>
1160     <xsl:when test="not($graphic.ext)">
1161       <xsl:choose>
1162         <xsl:when test="$graphic.default.extension != ''">
1163           <xsl:value-of select="$filename"/>
1164           <xsl:text>.</xsl:text>
1165           <xsl:value-of select="$graphic.default.extension"/>
1166         </xsl:when>
1167         <xsl:otherwise>
1168           <xsl:value-of select="$filename"/>
1169         </xsl:otherwise>
1170       </xsl:choose>
1171     </xsl:when>
1172     <xsl:otherwise>
1173       <xsl:value-of select="$filename"/>
1174     </xsl:otherwise>
1175   </xsl:choose>
1176 </xsl:template>
1177
1178 <!-- ====================================================================== -->
1179
1180 <doc:template name="check.id.unique" xmlns="">
1181 <refpurpose>Warn users about references to non-unique IDs</refpurpose>
1182 <refdescription id="check.id.unique-desc">
1183 <para>If passed an ID in <varname>linkend</varname>,
1184 <function>check.id.unique</function> prints
1185 a warning message to the user if either the ID does not exist or
1186 the ID is not unique.</para>
1187 </refdescription>
1188 </doc:template>
1189
1190 <xsl:template name="check.id.unique">
1191   <xsl:param name="linkend"></xsl:param>
1192   <xsl:if test="$linkend != ''">
1193     <xsl:variable name="targets" select="key('id',$linkend)"/>
1194     <xsl:variable name="target" select="$targets[1]"/>
1195
1196     <xsl:if test="count($targets)=0">
1197       <xsl:message>
1198         <xsl:text>Error: no ID for constraint linkend: </xsl:text>
1199         <xsl:value-of select="$linkend"/>
1200         <xsl:text>.</xsl:text>
1201       </xsl:message>
1202       <!--
1203       <xsl:message>
1204         <xsl:text>If the ID exists in your document, did your </xsl:text>
1205         <xsl:text>XSLT Processor load the DTD?</xsl:text>
1206       </xsl:message>
1207       -->
1208     </xsl:if>
1209
1210     <xsl:if test="count($targets)>1">
1211       <xsl:message>
1212         <xsl:text>Warning: multiple "IDs" for constraint linkend: </xsl:text>
1213         <xsl:value-of select="$linkend"/>
1214         <xsl:text>.</xsl:text>
1215       </xsl:message>
1216     </xsl:if>
1217   </xsl:if>
1218 </xsl:template>
1219
1220 <doc:template name="check.idref.targets" xmlns="">
1221 <refpurpose>Warn users about incorrectly typed references</refpurpose>
1222 <refdescription id="check.idref.targets-desc">
1223 <para>If passed an ID in <varname>linkend</varname>,
1224 <function>check.idref.targets</function> makes sure that the element
1225 pointed to by the link is one of the elements listed in
1226 <varname>element-list</varname> and warns the user otherwise.</para>
1227 </refdescription>
1228 </doc:template>
1229
1230 <xsl:template name="check.idref.targets">
1231   <xsl:param name="linkend"></xsl:param>
1232   <xsl:param name="element-list"></xsl:param>
1233   <xsl:if test="$linkend != ''">
1234     <xsl:variable name="targets" select="key('id',$linkend)"/>
1235     <xsl:variable name="target" select="$targets[1]"/>
1236
1237     <xsl:if test="count($target) &gt; 0">
1238       <xsl:if test="not(contains(concat(' ', $element-list, ' '), local-name($target)))">
1239         <xsl:message>
1240           <xsl:text>Error: linkend (</xsl:text>
1241           <xsl:value-of select="$linkend"/>
1242           <xsl:text>) points to "</xsl:text>
1243           <xsl:value-of select="local-name($target)"/>
1244           <xsl:text>" not (one of): </xsl:text>
1245           <xsl:value-of select="$element-list"/>
1246         </xsl:message>
1247       </xsl:if>
1248     </xsl:if>
1249   </xsl:if>
1250 </xsl:template>
1251
1252 <!-- ====================================================================== -->
1253 <!-- Procedure Step Numeration -->
1254
1255 <xsl:param name="procedure.step.numeration.formats" select="'1aiAI'"/>
1256
1257 <xsl:template name="procedure.step.numeration">
1258   <xsl:param name="context" select="."/>
1259   <xsl:variable name="format.length"
1260                 select="string-length($procedure.step.numeration.formats)"/>
1261   <xsl:choose>
1262     <xsl:when test="local-name($context) = 'substeps'">
1263       <xsl:variable name="ssdepth"
1264                     select="count($context/ancestor::substeps)"/>
1265       <xsl:variable name="sstype" select="($ssdepth mod $format.length)+2"/>
1266       <xsl:choose>
1267         <xsl:when test="$sstype &gt; $format.length">
1268           <xsl:value-of select="substring($procedure.step.numeration.formats,1,1)"/>
1269         </xsl:when>
1270         <xsl:otherwise>
1271           <xsl:value-of select="substring($procedure.step.numeration.formats,$sstype,1)"/>
1272         </xsl:otherwise>
1273       </xsl:choose>
1274     </xsl:when>
1275     <xsl:when test="local-name($context) = 'step'">
1276       <xsl:variable name="sdepth"
1277                     select="count($context/ancestor::substeps)"/>
1278       <xsl:variable name="stype" select="($sdepth mod $format.length)+1"/>
1279       <xsl:value-of select="substring($procedure.step.numeration.formats,$stype,1)"/>
1280     </xsl:when>
1281     <xsl:otherwise>
1282       <xsl:message>
1283         <xsl:text>Unexpected context in procedure.step.numeration: </xsl:text>
1284         <xsl:value-of select="local-name($context)"/>
1285       </xsl:message>
1286     </xsl:otherwise>
1287   </xsl:choose>
1288 </xsl:template>
1289
1290 <xsl:template match="step" mode="number">
1291   <xsl:param name="rest" select="''"/>
1292   <xsl:param name="recursive" select="1"/>
1293   <xsl:variable name="format">
1294     <xsl:call-template name="procedure.step.numeration"/>
1295   </xsl:variable>
1296   <xsl:variable name="num">
1297     <xsl:number count="step" format="{$format}"/>
1298   </xsl:variable>
1299   <xsl:choose>
1300     <xsl:when test="$recursive != 0 and ancestor::step">
1301       <xsl:apply-templates select="ancestor::step[1]" mode="number">
1302         <xsl:with-param name="rest" select="concat('.', $num, $rest)"/>
1303       </xsl:apply-templates>
1304     </xsl:when>
1305     <xsl:otherwise>
1306       <xsl:value-of select="concat($num, $rest)"/>
1307     </xsl:otherwise>
1308   </xsl:choose>
1309 </xsl:template>
1310
1311 <!-- ====================================================================== -->
1312 <!-- OrderedList Numeration -->
1313 <xsl:template name="output-orderedlist-starting-number">
1314   <xsl:param name="list"/>
1315   <xsl:param name="pi-start"/>
1316   <xsl:choose>
1317     <xsl:when test="not($list/@continuation = 'continues')">
1318       <xsl:choose>
1319         <xsl:when test="@startingnumber">
1320           <xsl:value-of select="@startingnumber"/>
1321         </xsl:when>
1322         <xsl:when test="$pi-start != ''">
1323           <xsl:value-of select="$pi-start"/>
1324         </xsl:when>
1325         <xsl:otherwise>1</xsl:otherwise>
1326       </xsl:choose>
1327     </xsl:when>
1328     <xsl:otherwise>
1329       <xsl:variable name="prevlist"
1330         select="$list/preceding::orderedlist[1]"/>
1331       <xsl:choose>
1332         <xsl:when test="count($prevlist) = 0">2</xsl:when>
1333         <xsl:otherwise>
1334           <xsl:variable name="prevlength" select="count($prevlist/listitem)"/>
1335           <xsl:variable name="prevstart">
1336             <xsl:call-template name="orderedlist-starting-number">
1337               <xsl:with-param name="list" select="$prevlist"/>
1338             </xsl:call-template>
1339           </xsl:variable>
1340           <xsl:value-of select="$prevstart + $prevlength"/>
1341         </xsl:otherwise>
1342       </xsl:choose>
1343     </xsl:otherwise>
1344   </xsl:choose>
1345 </xsl:template>
1346
1347 <xsl:template name="orderedlist-item-number">
1348   <!-- context node must be a listitem in an orderedlist -->
1349   <xsl:param name="node" select="."/>
1350   <xsl:choose>
1351     <xsl:when test="$node/@override">
1352       <xsl:value-of select="$node/@override"/>
1353     </xsl:when>
1354     <xsl:when test="$node/preceding-sibling::listitem">
1355       <xsl:variable name="pnum">
1356         <xsl:call-template name="orderedlist-item-number">
1357           <xsl:with-param name="node" select="$node/preceding-sibling::listitem[1]"/>
1358         </xsl:call-template>
1359       </xsl:variable>
1360       <xsl:value-of select="$pnum + 1"/>
1361     </xsl:when>
1362     <xsl:otherwise>
1363       <xsl:call-template name="orderedlist-starting-number">
1364         <xsl:with-param name="list" select="parent::*"/>
1365       </xsl:call-template>
1366     </xsl:otherwise>
1367   </xsl:choose>
1368 </xsl:template>
1369
1370 <xsl:template name="next.numeration">
1371   <xsl:param name="numeration" select="'default'"/>
1372   <xsl:choose>
1373     <!-- Change this list if you want to change the order of numerations -->
1374     <xsl:when test="$numeration = 'arabic'">loweralpha</xsl:when>
1375     <xsl:when test="$numeration = 'loweralpha'">lowerroman</xsl:when>
1376     <xsl:when test="$numeration = 'lowerroman'">upperalpha</xsl:when>
1377     <xsl:when test="$numeration = 'upperalpha'">upperroman</xsl:when>
1378     <xsl:when test="$numeration = 'upperroman'">arabic</xsl:when>
1379     <xsl:otherwise>arabic</xsl:otherwise>
1380   </xsl:choose>
1381 </xsl:template>
1382
1383 <xsl:template name="list.numeration">
1384   <xsl:param name="node" select="."/>
1385
1386   <xsl:choose>
1387     <xsl:when test="$node/@numeration">
1388       <xsl:value-of select="$node/@numeration"/>
1389     </xsl:when>
1390     <xsl:otherwise>
1391       <xsl:choose>
1392         <xsl:when test="$node/ancestor::orderedlist">
1393           <xsl:call-template name="next.numeration">
1394             <xsl:with-param name="numeration">
1395               <xsl:call-template name="list.numeration">
1396                 <xsl:with-param name="node" select="$node/ancestor::orderedlist[1]"/>
1397               </xsl:call-template>
1398             </xsl:with-param>
1399           </xsl:call-template>
1400         </xsl:when>
1401         <xsl:otherwise>
1402           <xsl:call-template name="next.numeration"/>
1403         </xsl:otherwise>
1404       </xsl:choose>
1405     </xsl:otherwise>
1406   </xsl:choose>
1407 </xsl:template>
1408
1409 <xsl:template match="orderedlist/listitem" mode="item-number">
1410   <xsl:variable name="numeration">
1411     <xsl:call-template name="list.numeration">
1412       <xsl:with-param name="node" select="parent::orderedlist"/>
1413     </xsl:call-template>
1414   </xsl:variable>
1415
1416   <xsl:variable name="type">
1417     <xsl:choose>
1418       <xsl:when test="$numeration='arabic'">1.</xsl:when>
1419       <xsl:when test="$numeration='loweralpha'">a.</xsl:when>
1420       <xsl:when test="$numeration='lowerroman'">i.</xsl:when>
1421       <xsl:when test="$numeration='upperalpha'">A.</xsl:when>
1422       <xsl:when test="$numeration='upperroman'">I.</xsl:when>
1423       <!-- What!? This should never happen -->
1424       <xsl:otherwise>
1425         <xsl:message>
1426           <xsl:text>Unexpected numeration: </xsl:text>
1427           <xsl:value-of select="$numeration"/>
1428         </xsl:message>
1429         <xsl:value-of select="1."/>
1430       </xsl:otherwise>
1431     </xsl:choose>
1432   </xsl:variable>
1433
1434   <xsl:variable name="item-number">
1435     <xsl:call-template name="orderedlist-item-number"/>
1436   </xsl:variable>
1437
1438   <xsl:if test="parent::orderedlist/@inheritnum='inherit'
1439                 and ancestor::listitem[parent::orderedlist]">
1440     <xsl:apply-templates select="ancestor::listitem[parent::orderedlist][1]"
1441                          mode="item-number"/>
1442   </xsl:if>
1443
1444   <xsl:number value="$item-number" format="{$type}"/>
1445 </xsl:template>
1446
1447 <!-- ====================================================================== -->
1448 <!-- ItemizedList "Numeration" -->
1449
1450 <xsl:template name="next.itemsymbol">
1451   <xsl:param name="itemsymbol" select="'default'"/>
1452   <xsl:choose>
1453     <!-- Change this list if you want to change the order of symbols -->
1454     <xsl:when test="$itemsymbol = 'disc'">circle</xsl:when>
1455     <xsl:when test="$itemsymbol = 'circle'">square</xsl:when>
1456     <xsl:otherwise>disc</xsl:otherwise>
1457   </xsl:choose>
1458 </xsl:template>
1459
1460 <xsl:template name="list.itemsymbol">
1461   <xsl:param name="node" select="."/>
1462
1463   <xsl:choose>
1464     <xsl:when test="@override">
1465       <xsl:value-of select="@override"/>
1466     </xsl:when>
1467     <xsl:when test="$node/@mark">
1468       <xsl:value-of select="$node/@mark"/>
1469     </xsl:when>
1470     <xsl:otherwise>
1471       <xsl:choose>
1472         <xsl:when test="$node/ancestor::itemizedlist">
1473           <xsl:call-template name="next.itemsymbol">
1474             <xsl:with-param name="itemsymbol">
1475               <xsl:call-template name="list.itemsymbol">
1476                 <xsl:with-param name="node" select="$node/ancestor::itemizedlist[1]"/>
1477               </xsl:call-template>
1478             </xsl:with-param>
1479           </xsl:call-template>
1480         </xsl:when>
1481         <xsl:otherwise>
1482           <xsl:call-template name="next.itemsymbol"/>
1483         </xsl:otherwise>
1484       </xsl:choose>
1485     </xsl:otherwise>
1486   </xsl:choose>
1487 </xsl:template>
1488
1489 <!-- ====================================================================== -->
1490
1491 <doc:template name="copyright.years" xmlns="">
1492 <refpurpose>Print a set of years with collapsed ranges</refpurpose>
1493
1494 <refdescription id="copyright.years-desc">
1495 <para>This template prints a list of year elements with consecutive
1496 years printed as a range. In other words:</para>
1497
1498 <screen><![CDATA[<year>1992</year>
1499 <year>1993</year>
1500 <year>1994</year>]]></screen>
1501
1502 <para>is printed <quote>1992-1994</quote>, whereas:</para>
1503
1504 <screen><![CDATA[<year>1992</year>
1505 <year>1994</year>]]></screen>
1506
1507 <para>is printed <quote>1992, 1994</quote>.</para>
1508
1509 <para>This template assumes that all the year elements contain only
1510 decimal year numbers, that the elements are sorted in increasing
1511 numerical order, that there are no duplicates, and that all the years
1512 are expressed in full <quote>century+year</quote>
1513 (<quote>1999</quote> not <quote>99</quote>) notation.</para>
1514 </refdescription>
1515
1516 <refparameter id="copyright.years-params">
1517 <variablelist>
1518 <varlistentry><term>years</term>
1519 <listitem>
1520 <para>The initial set of year elements.</para>
1521 </listitem>
1522 </varlistentry>
1523 <varlistentry><term>print.ranges</term>
1524 <listitem>
1525 <para>If non-zero, multi-year ranges are collapsed. If zero, all years
1526 are printed discretely.</para>
1527 </listitem>
1528 </varlistentry>
1529 <varlistentry><term>single.year.ranges</term>
1530 <listitem>
1531 <para>If non-zero, two consecutive years will be printed as a range,
1532 otherwise, they will be printed discretely. In other words, a single
1533 year range is <quote>1991-1992</quote> but discretely it's
1534 <quote>1991, 1992</quote>.</para>
1535 </listitem>
1536 </varlistentry>
1537 </variablelist>
1538 </refparameter>
1539
1540 <refreturn id="copyright.years-returns">
1541 <para>This template returns the formatted list of years.</para>
1542 </refreturn>
1543 </doc:template>
1544
1545 <xsl:template name="copyright.years">
1546   <xsl:param name="years"/>
1547   <xsl:param name="print.ranges" select="1"/>
1548   <xsl:param name="single.year.ranges" select="0"/>
1549   <xsl:param name="firstyear" select="0"/>
1550   <xsl:param name="nextyear" select="0"/>
1551
1552   <!--
1553   <xsl:message terminate="no">
1554     <xsl:text>CY: </xsl:text>
1555     <xsl:value-of select="count($years)"/>
1556     <xsl:text>, </xsl:text>
1557     <xsl:value-of select="$firstyear"/>
1558     <xsl:text>, </xsl:text>
1559     <xsl:value-of select="$nextyear"/>
1560     <xsl:text>, </xsl:text>
1561     <xsl:value-of select="$print.ranges"/>
1562     <xsl:text>, </xsl:text>
1563     <xsl:value-of select="$single.year.ranges"/>
1564     <xsl:text> (</xsl:text>
1565     <xsl:value-of select="$years[1]"/>
1566     <xsl:text>)</xsl:text>
1567   </xsl:message>
1568   -->
1569     
1570   <xsl:choose>
1571     <xsl:when test="$print.ranges = 0 and count($years) &gt; 0">
1572       <xsl:choose>
1573         <xsl:when test="count($years) = 1">
1574           <xsl:apply-templates select="$years[1]" mode="titlepage.mode"/>
1575         </xsl:when>
1576         <xsl:otherwise>
1577           <xsl:apply-templates select="$years[1]" mode="titlepage.mode"/>
1578           <xsl:text>, </xsl:text>
1579           <xsl:call-template name="copyright.years">
1580             <xsl:with-param name="years"
1581                             select="$years[position() &gt; 1]"/>
1582             <xsl:with-param name="print.ranges" select="$print.ranges"/>
1583             <xsl:with-param name="single.year.ranges"
1584                             select="$single.year.ranges"/>
1585           </xsl:call-template>
1586         </xsl:otherwise>
1587       </xsl:choose>
1588     </xsl:when>
1589     <xsl:when test="count($years) = 0">
1590       <xsl:variable name="lastyear" select="$nextyear - 1"/>
1591       <xsl:choose>
1592         <xsl:when test="$firstyear = 0">
1593           <!-- there weren't any years at all -->
1594         </xsl:when>
1595         <!-- Just output a year with range in its text -->
1596         <xsl:when test="contains($firstyear, '-') or contains($firstyear, ',')">
1597           <xsl:value-of select="$firstyear"/>
1598         </xsl:when>
1599         <xsl:when test="$firstyear = $lastyear">
1600           <xsl:value-of select="$firstyear"/>
1601         </xsl:when>
1602         <xsl:when test="$single.year.ranges = 0
1603                         and $lastyear = $firstyear + 1">
1604           <xsl:value-of select="$firstyear"/>
1605           <xsl:text>, </xsl:text>
1606           <xsl:value-of select="$lastyear"/>
1607         </xsl:when>
1608         <xsl:otherwise>
1609           <xsl:value-of select="$firstyear"/>
1610           <xsl:text>-</xsl:text>
1611           <xsl:value-of select="$lastyear"/>
1612         </xsl:otherwise>
1613       </xsl:choose>
1614     </xsl:when>
1615     <xsl:when test="contains($firstyear, '-') or contains($firstyear, ',')">
1616       <!-- Just output a year with range in its text -->
1617       <xsl:value-of select="$firstyear"/>
1618       <xsl:if test="count($years) != 0">
1619         <xsl:text>, </xsl:text>
1620       </xsl:if>
1621       <xsl:call-template name="copyright.years">
1622         <xsl:with-param name="years"
1623               select="$years[position() &gt; 1]"/>
1624         <xsl:with-param name="firstyear" select="$years[1]"/>
1625         <xsl:with-param name="nextyear" select="$years[1] + 1"/>
1626         <xsl:with-param name="print.ranges" select="$print.ranges"/>
1627         <xsl:with-param name="single.year.ranges"
1628                 select="$single.year.ranges"/>
1629       </xsl:call-template>
1630     </xsl:when>
1631     <xsl:when test="$firstyear = 0">
1632       <xsl:call-template name="copyright.years">
1633         <xsl:with-param name="years"
1634                         select="$years[position() &gt; 1]"/>
1635         <xsl:with-param name="firstyear" select="$years[1]"/>
1636         <xsl:with-param name="nextyear" select="$years[1] + 1"/>
1637         <xsl:with-param name="print.ranges" select="$print.ranges"/>
1638         <xsl:with-param name="single.year.ranges"
1639                         select="$single.year.ranges"/>
1640       </xsl:call-template>
1641     </xsl:when>
1642     <xsl:when test="$nextyear = $years[1]">
1643       <xsl:call-template name="copyright.years">
1644         <xsl:with-param name="years"
1645                         select="$years[position() &gt; 1]"/>
1646         <xsl:with-param name="firstyear" select="$firstyear"/>
1647         <xsl:with-param name="nextyear" select="$nextyear + 1"/>
1648         <xsl:with-param name="print.ranges" select="$print.ranges"/>
1649         <xsl:with-param name="single.year.ranges"
1650                         select="$single.year.ranges"/>
1651       </xsl:call-template>
1652     </xsl:when>
1653     <xsl:otherwise>
1654       <!-- we have years left, but they aren't in the current range -->
1655       <xsl:choose>
1656         <xsl:when test="$nextyear = $firstyear + 1">
1657           <xsl:value-of select="$firstyear"/>
1658           <xsl:text>, </xsl:text>
1659         </xsl:when>
1660         <xsl:when test="$single.year.ranges = 0
1661                         and $nextyear = $firstyear + 2">
1662           <xsl:value-of select="$firstyear"/>
1663           <xsl:text>, </xsl:text>
1664           <xsl:value-of select="$nextyear - 1"/>
1665           <xsl:text>, </xsl:text>
1666         </xsl:when>
1667         <xsl:otherwise>
1668           <xsl:value-of select="$firstyear"/>
1669           <xsl:text>-</xsl:text>
1670           <xsl:value-of select="$nextyear - 1"/>
1671           <xsl:text>, </xsl:text>
1672         </xsl:otherwise>
1673       </xsl:choose>
1674       <xsl:call-template name="copyright.years">
1675         <xsl:with-param name="years"
1676                         select="$years[position() &gt; 1]"/>
1677         <xsl:with-param name="firstyear" select="$years[1]"/>
1678         <xsl:with-param name="nextyear" select="$years[1] + 1"/>
1679         <xsl:with-param name="print.ranges" select="$print.ranges"/>
1680         <xsl:with-param name="single.year.ranges"
1681                         select="$single.year.ranges"/>
1682       </xsl:call-template>
1683     </xsl:otherwise>
1684   </xsl:choose>
1685 </xsl:template>
1686
1687 <!-- ====================================================================== -->
1688
1689 <doc:template name="find.path.params" xmlns="">
1690 <refpurpose>Search in a table for the "best" match for the node</refpurpose>
1691
1692 <refdescription id="find.path.params-desc">
1693 <para>This template searches in a table for the value that most-closely
1694 (in the typical best-match sense of XSLT) matches the current (element)
1695 node location.</para>
1696 </refdescription>
1697 </doc:template>
1698
1699 <xsl:template name="find.path.params">
1700   <xsl:param name="node" select="."/>
1701   <xsl:param name="table" select="''"/>
1702   <xsl:param name="location">
1703     <xsl:call-template name="xpath.location">
1704       <xsl:with-param name="node" select="$node"/>
1705     </xsl:call-template>
1706   </xsl:param>
1707
1708   <xsl:variable name="value">
1709     <xsl:call-template name="lookup.key">
1710       <xsl:with-param name="key" select="$location"/>
1711       <xsl:with-param name="table" select="$table"/>
1712     </xsl:call-template>
1713   </xsl:variable>
1714
1715   <xsl:choose>
1716     <xsl:when test="$value != ''">
1717       <xsl:value-of select="$value"/>
1718     </xsl:when>
1719     <xsl:when test="contains($location, '/')">
1720       <xsl:call-template name="find.path.params">
1721         <xsl:with-param name="node" select="$node"/>
1722         <xsl:with-param name="table" select="$table"/>
1723         <xsl:with-param name="location" select="substring-after($location, '/')"/>
1724       </xsl:call-template>
1725     </xsl:when>
1726   </xsl:choose>
1727 </xsl:template>
1728
1729 <xsl:template name="relative-uri">
1730   <xsl:param name="filename" select="."/>
1731   <xsl:param name="destdir" select="''"/>
1732   
1733   <xsl:variable name="srcurl">
1734     <xsl:call-template name="strippath">
1735       <xsl:with-param name="filename">
1736         <xsl:call-template name="xml.base.dirs">
1737           <xsl:with-param name="base.elem" 
1738                           select="$filename/ancestor-or-self::*
1739                                    [@xml:base != ''][1]"/>
1740         </xsl:call-template>
1741         <xsl:value-of select="$filename"/>
1742       </xsl:with-param>
1743     </xsl:call-template>
1744   </xsl:variable>
1745
1746   <xsl:variable name="srcurl.trimmed">
1747     <xsl:call-template name="trim.common.uri.paths">
1748       <xsl:with-param name="uriA" select="$srcurl"/>
1749       <xsl:with-param name="uriB" select="$destdir"/>
1750       <xsl:with-param name="return" select="'A'"/>
1751     </xsl:call-template>
1752   </xsl:variable>
1753
1754   <xsl:variable name="destdir.trimmed">
1755     <xsl:call-template name="trim.common.uri.paths">
1756       <xsl:with-param name="uriA" select="$srcurl"/>
1757       <xsl:with-param name="uriB" select="$destdir"/>
1758       <xsl:with-param name="return" select="'B'"/>
1759     </xsl:call-template>
1760   </xsl:variable>
1761
1762   <xsl:variable name="depth">
1763     <xsl:call-template name="count.uri.path.depth">
1764       <xsl:with-param name="filename" select="$destdir.trimmed"/>
1765     </xsl:call-template>
1766   </xsl:variable>
1767
1768   <xsl:call-template name="copy-string">
1769     <xsl:with-param name="string" select="'../'"/>
1770     <xsl:with-param name="count" select="$depth"/>
1771   </xsl:call-template>
1772   <xsl:value-of select="$srcurl.trimmed"/>
1773
1774 </xsl:template>
1775
1776 <!-- ===================================== -->
1777
1778 <xsl:template name="xml.base.dirs">
1779   <xsl:param name="base.elem" select="NONODE"/>
1780
1781   <!-- Recursively resolve xml:base attributes, up to a 
1782        full path with : in uri -->
1783   <xsl:if test="$base.elem/ancestor::*[@xml:base != ''] and
1784                 not(contains($base.elem/@xml:base, ':'))">
1785     <xsl:call-template name="xml.base.dirs">
1786       <xsl:with-param name="base.elem" 
1787                       select="$base.elem/ancestor::*[@xml:base != ''][1]"/>
1788     </xsl:call-template>
1789   </xsl:if>
1790   <xsl:call-template name="getdir">
1791     <xsl:with-param name="filename" select="$base.elem/@xml:base"/>
1792   </xsl:call-template>
1793
1794 </xsl:template>
1795
1796 <!-- ===================================== -->
1797
1798 <xsl:template name="strippath">
1799   <xsl:param name="filename" select="''"/>
1800   <xsl:choose>
1801     <!-- Leading .. are not eliminated -->
1802     <xsl:when test="starts-with($filename, '../')">
1803       <xsl:value-of select="'../'"/>
1804       <xsl:call-template name="strippath">
1805         <xsl:with-param name="filename" select="substring-after($filename, '../')"/>
1806       </xsl:call-template>
1807     </xsl:when>
1808     <xsl:when test="contains($filename, '/../')">
1809       <xsl:call-template name="strippath">
1810         <xsl:with-param name="filename">
1811           <xsl:call-template name="getdir">
1812             <xsl:with-param name="filename" select="substring-before($filename, '/../')"/>
1813           </xsl:call-template>
1814           <xsl:value-of select="substring-after($filename, '/../')"/>
1815         </xsl:with-param>
1816       </xsl:call-template>
1817     </xsl:when>
1818     <xsl:otherwise>
1819       <xsl:value-of select="$filename"/>
1820     </xsl:otherwise>
1821   </xsl:choose>
1822 </xsl:template>
1823
1824 <!-- ===================================== -->
1825
1826 <xsl:template name="getdir">
1827   <xsl:param name="filename" select="''"/>
1828   <xsl:if test="contains($filename, '/')">
1829     <xsl:value-of select="substring-before($filename, '/')"/>
1830     <xsl:text>/</xsl:text>
1831     <xsl:call-template name="getdir">
1832       <xsl:with-param name="filename" select="substring-after($filename, '/')"/>
1833     </xsl:call-template>
1834   </xsl:if>
1835 </xsl:template>
1836
1837 <!-- ===================================== -->
1838
1839 <doc:template name="string.upper" xmlns="">
1840 <refpurpose>Converts a string to all uppercase letters</refpurpose>
1841
1842 <refdescription id="string.upper-desc">
1843 <para>Given a string, this template does a language-aware conversion
1844 of that string to all uppercase letters, based on the values of the
1845 <literal>lowercase.alpha</literal> and
1846 <literal>uppercase.alpha</literal> gentext keys for the current
1847 locale. It affects only those characters found in the values of
1848 <literal>lowercase.alpha</literal> and
1849 <literal>uppercase.alpha</literal>. All other characters are left
1850 unchanged.</para>
1851 </refdescription>
1852
1853 <refparameter id="string.upper-params">
1854 <variablelist>
1855 <varlistentry><term>string</term>
1856 <listitem>
1857 <para>The string to convert to uppercase.</para>
1858 </listitem>
1859 </varlistentry>
1860 </variablelist>
1861 </refparameter>
1862 </doc:template>
1863 <xsl:template name="string.upper">
1864   <xsl:param name="string" select="''"/>
1865   <xsl:variable name="lowercase.alpha">
1866     <xsl:call-template name="gentext">
1867       <xsl:with-param name="key" select="'lowercase.alpha'"/>
1868     </xsl:call-template>
1869   </xsl:variable>
1870   <xsl:variable name="uppercase.alpha">
1871     <xsl:call-template name="gentext">
1872       <xsl:with-param name="key" select="'uppercase.alpha'"/>
1873     </xsl:call-template>
1874   </xsl:variable>
1875   <xsl:value-of select="translate($string,$lowercase.alpha,$uppercase.alpha)"/>
1876 </xsl:template>
1877
1878 <!-- ===================================== -->
1879
1880 <doc:template name="string.lower" xmlns="">
1881 <refpurpose>Converts a string to all lowercase letters</refpurpose>
1882
1883 <refdescription id="string.lower-desc">
1884 <para>Given a string, this template does a language-aware conversion
1885 of that string to all lowercase letters, based on the values of the
1886 <literal>uppercase.alpha</literal> and
1887 <literal>lowercase.alpha</literal> gentext keys for the current
1888 locale. It affects only those characters found in the values of
1889 <literal>uppercase.alpha</literal> and
1890 <literal>lowercase.alpha</literal>. All other characters are left
1891 unchanged.</para>
1892 </refdescription>
1893
1894 <refparameter id="string.lower-params">
1895 <variablelist>
1896 <varlistentry><term>string</term>
1897 <listitem>
1898 <para>The string to convert to lowercase.</para>
1899 </listitem>
1900 </varlistentry>
1901 </variablelist>
1902 </refparameter>
1903 </doc:template>
1904 <xsl:template name="string.lower">
1905   <xsl:param name="string" select="''"/>
1906   <xsl:variable name="uppercase.alpha">
1907     <xsl:call-template name="gentext">
1908       <xsl:with-param name="key" select="'uppercase.alpha'"/>
1909     </xsl:call-template>
1910   </xsl:variable>
1911   <xsl:variable name="lowercase.alpha">
1912     <xsl:call-template name="gentext">
1913       <xsl:with-param name="key" select="'lowercase.alpha'"/>
1914     </xsl:call-template>
1915   </xsl:variable>
1916   <xsl:value-of select="translate($string,$uppercase.alpha,$lowercase.alpha)"/>
1917 </xsl:template>
1918
1919 <!-- ===================================== -->
1920
1921 <doc:template name="select.choice.separator" xmlns="">
1922   <refpurpose>Returns localized choice separator</refpurpose>
1923   <refdescription id="select.choice.separator-desc">
1924     <para>This template enables auto-generation of an appropriate
1925     localized "choice" separator (for example, "and" or "or") before
1926     the final item in an inline list (though it could also be useful
1927     for generating choice separators for non-inline lists).</para>
1928     <para>It currently works by evaluating a processing instruction
1929     (PI) of the form &lt;?dbchoice&#xa0;choice="foo"?> :
1930     <itemizedlist>
1931       <listitem>
1932         <simpara>if the value of the <tag>choice</tag>
1933         pseudo-attribute is "and" or "or", returns a localized "and"
1934         or "or"</simpara>
1935       </listitem>
1936       <listitem>
1937         <simpara>otherwise returns the literal value of the
1938         <tag>choice</tag> pseudo-attribute</simpara>
1939       </listitem>
1940     </itemizedlist>
1941     The latter is provided only as a temporary workaround because the
1942     locale files do not currently have translations for the word
1943     <wordasword>or</wordasword>. So if you want to generate a a
1944     logical "or" separator in French (for example), you currently need
1945     to do this:
1946     <literallayout>&lt;?dbchoice choice="ou"?></literallayout>
1947     </para>
1948     <warning>
1949       <para>The <tag>dbchoice</tag> processing instruction is
1950       an unfortunate hack; support for it may disappear in the future
1951       (particularly if and when a more appropriate means for marking
1952       up "choice" lists becomes available in DocBook).</para>
1953     </warning>
1954   </refdescription>
1955 </doc:template>
1956 <xsl:template name="select.choice.separator">
1957   <xsl:variable name="choice">
1958     <xsl:call-template name="pi.dbchoice_choice"/>
1959   </xsl:variable>
1960   <xsl:choose>
1961     <!-- if value of $choice is "and" or "or", translate to equivalent in -->
1962     <!-- current locale -->
1963     <xsl:when test="$choice = 'and' or $choice = 'or'">
1964       <xsl:call-template name="gentext">
1965         <xsl:with-param name="key" select="$choice"/>
1966       </xsl:call-template>
1967     </xsl:when>
1968     <!--  otherwise, just output value of $choice, whatever it is -->
1969     <xsl:otherwise>
1970       <xsl:value-of select="$choice"/>
1971     </xsl:otherwise>
1972   </xsl:choose>
1973 </xsl:template>
1974
1975 <!-- ===================================== -->
1976
1977 <doc:template name="evaluate.info.profile" xmlns="">
1978   <refpurpose>Evaluates an info profile</refpurpose>
1979   <refdescription id="evaluate.info.profile-desc">
1980     <para>This template evaluates an "info profile" matching the XPath
1981     expression given by the <parameter>profile</parameter>
1982     parameter. It relies on the XSLT <function>evaluate()</function>
1983     extension function.</para>
1984
1985     <para>The value of the <parameter>profile</parameter> parameter
1986     can include the literal string <literal>$info</literal>. If found
1987     in the value of the <parameter>profile</parameter> parameter, the
1988     literal string <literal>$info</literal> string is replaced with
1989     the value of the <parameter>info</parameter> parameter, which
1990     should be a set of <replaceable>*info</replaceable> nodes; the
1991     expression is then evaluated using the XSLT
1992     <function>evaluate()</function> extension function.</para>
1993   </refdescription>
1994   <refparameter id="evaluate.info.profile-params">
1995     <variablelist>
1996        <varlistentry>
1997         <term>profile</term>
1998         <listitem>
1999           <para>A string representing an XPath expression </para>
2000         </listitem>
2001       </varlistentry>
2002        <varlistentry>
2003         <term>info</term>
2004         <listitem>
2005           <para>A set of *info nodes</para>
2006         </listitem>
2007       </varlistentry>
2008     </variablelist>
2009   </refparameter>
2010
2011   <refreturn id="evaluate.info.profile-returns">
2012     <para>Returns a node (the result of evaluating the
2013     <parameter>profile</parameter> parameter)</para>
2014   </refreturn>
2015 </doc:template>
2016   <xsl:template name="evaluate.info.profile">
2017     <xsl:param name="profile"/>
2018     <xsl:param name="info"/>
2019     <xsl:choose>
2020       <!-- * xsltproc and Xalan both support dyn:evaluate() -->
2021       <xsl:when test="function-available('dyn:evaluate')">
2022         <xsl:apply-templates
2023             select="dyn:evaluate($profile)" mode="get.refentry.metadata"/>
2024       </xsl:when>
2025       <!-- * Saxon has its own evaluate() & doesn't support dyn:evaluate() -->
2026       <xsl:when test="function-available('saxon:evaluate')">
2027         <xsl:apply-templates
2028             select="saxon:evaluate($profile)" mode="get.refentry.metadata"/>
2029       </xsl:when>
2030       <xsl:otherwise>
2031         <xsl:message terminate="yes">
2032 Error: The "info profiling" mechanism currently requires an XSLT
2033 engine that supports the evaluate() XSLT extension function. Your XSLT
2034 engine does not support it.
2035 </xsl:message>
2036       </xsl:otherwise>
2037     </xsl:choose>
2038   </xsl:template>
2039 </xsl:stylesheet>