2 <!DOCTYPE xsl:stylesheet [
3 <!ENTITY lowercase "'abcdefghijklmnopqrstuvwxyz'">
4 <!ENTITY uppercase "'ABCDEFGHIJKLMNOPQRSTUVWXYZ'">
6 <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
7 xmlns:fo="http://www.w3.org/1999/XSL/Format"
8 xmlns:xlink="http://www.w3.org/1999/xlink"
9 xmlns:stext="http://nwalsh.com/xslt/ext/com.nwalsh.saxon.TextFactory"
10 xmlns:xtext="com.nwalsh.xalan.Text"
11 xmlns:lxslt="http://xml.apache.org/xslt"
12 exclude-result-prefixes="xlink stext xtext lxslt"
13 extension-element-prefixes="stext xtext"
16 <!-- ********************************************************************
17 $Id: graphics.xsl 9941 2014-09-06 16:35:04Z bobstayton $
18 ********************************************************************
20 This file is part of the XSL DocBook Stylesheet distribution.
21 See ../README or http://docbook.sf.net/release/xsl/current/ for
22 copyright and other information.
25 Colin Paul Adams, <colin@colina.demon.co.uk>
26 Paul Grosso, <pgrosso@arbortext.com>
28 ******************************************************************** -->
30 <!-- ==================================================================== -->
31 <!-- Graphic format tests for the FO backend -->
33 <xsl:param name="graphic.notations">
34 <!-- n.b. exactly one leading space, one trailing space, and one inter-word space -->
36 <xsl:when test="$fop1.extensions != 0">
37 <xsl:text> BMP GIF TIFF SVG PNG EPS JPG JPEG linespecific </xsl:text>
39 <xsl:when test="$fop.extensions != 0">
40 <xsl:text> BMP GIF TIFF SVG PNG EPS JPG JPEG linespecific </xsl:text>
42 <xsl:when test="$arbortext.extensions != 0">
43 <xsl:text> PNG PDF JPG JPEG linespecific GIF GIF87a GIF89a TIFF BMP </xsl:text>
45 <xsl:when test="$xep.extensions != 0">
46 <xsl:text> SVG PNG PDF JPG JPEG linespecific GIF GIF87a GIF89a TIFF BMP </xsl:text>
49 <xsl:text> PNG PDF JPG JPEG linespecific GIF GIF87a GIF89a TIFF BMP </xsl:text>
54 <xsl:template name="is.graphic.format">
55 <xsl:param name="format"/>
56 <xsl:if test="contains($graphic.notations, concat(' ',$format,' '))">1</xsl:if>
59 <xsl:param name="graphic.extensions">
60 <!-- n.b. exactly one leading space, one trailing space, and one inter-word space -->
62 <xsl:when test="$fop1.extensions != 0">
63 <xsl:text> bmp gif tif tiff svg png pdf jpg jpeg eps </xsl:text>
65 <xsl:when test="$fop.extensions != 0">
66 <xsl:text> bmp gif tif tiff svg png pdf jpg jpeg eps </xsl:text>
68 <xsl:when test="$arbortext.extensions != 0">
69 <xsl:text> png pdf jpg jpeg gif tif tiff bmp </xsl:text>
71 <xsl:when test="$xep.extensions != 0">
72 <xsl:text> svg png pdf jpg jpeg gif tif tiff bmp eps </xsl:text>
75 <xsl:text> svg png pdf jpg jpeg gif tif tiff bmp eps </xsl:text>
80 <xsl:template name="is.graphic.extension">
81 <xsl:param name="ext"/>
82 <xsl:variable name="lcext" select="translate($ext,
83 'ABCDEFGHIJKLMNOPQRSTUVWXYZ',
84 'abcdefghijklmnopqrstuvwxyz')"/>
86 <xsl:if test="contains($graphic.extensions,
87 concat(' ', $lcext, ' '))">1</xsl:if>
91 <!-- ==================================================================== -->
93 <xsl:template match="screenshot">
95 <xsl:call-template name="anchor"/>
96 <xsl:apply-templates/>
100 <xsl:template match="screenshot/title">
101 <xsl:call-template name="formal.object.heading">
102 <xsl:with-param name="object" select=".."/>
106 <xsl:template match="screeninfo">
109 <!-- ==================================================================== -->
110 <!-- Override these templates for FO -->
111 <!-- ==================================================================== -->
113 <xsl:template name="image.scalefit">
115 <xsl:when test="$ignore.image.scaling != 0">0</xsl:when>
116 <xsl:when test="@contentwidth">0</xsl:when>
117 <xsl:when test="@contentdepth and
118 @contentdepth != '100%'">0</xsl:when>
119 <xsl:when test="@scale">0</xsl:when>
120 <xsl:when test="@scalefit"><xsl:value-of select="@scalefit"/></xsl:when>
121 <xsl:when test="@width or @depth">1</xsl:when>
122 <xsl:when test="$default.image.width != ''">1</xsl:when>
123 <xsl:otherwise>0</xsl:otherwise>
127 <xsl:template name="image.scale">
129 <xsl:when test="$ignore.image.scaling != 0">0</xsl:when>
130 <xsl:when test="@contentwidth or @contentdepth">1.0</xsl:when>
131 <xsl:when test="@scale">
132 <xsl:value-of select="@scale div 100.0"/>
134 <xsl:otherwise>1.0</xsl:otherwise>
138 <xsl:template name="image.filename">
140 <xsl:when test="svg:*" xmlns:svg="http://www.w3.org/2000/svg">
141 <!-- no filename for inline SVG content -->
143 <xsl:when test="mml:*" xmlns:mml="http://www.w3.org/1998/Math/MathML">
144 <!-- no filename for inline MathML content -->
146 <xsl:when test="local-name(.) = 'graphic'
147 or local-name(.) = 'inlinegraphic'">
148 <!-- handle legacy graphic and inlinegraphic by new template -->
149 <xsl:call-template name="mediaobject.filename">
150 <xsl:with-param name="object" select="."/>
154 <!-- imagedata, videodata, audiodata -->
155 <xsl:call-template name="mediaobject.filename">
156 <xsl:with-param name="object" select=".."/>
162 <xsl:template name="image.src">
163 <xsl:param name="filename"/>
166 <xsl:when test="svg:*" xmlns:svg="http://www.w3.org/2000/svg">
167 <!-- no src attribute for inline SVG content -->
169 <xsl:when test="mml:*" xmlns:mml="http://www.w3.org/1998/Math/MathML">
170 <!-- no src attribute for inline MathML content -->
173 <xsl:call-template name="fo-external-image">
174 <xsl:with-param name="filename">
175 <xsl:if test="$img.src.path != '' and
176 not(starts-with($filename, '/')) and
177 not(starts-with($filename, 'file:/')) and
178 not(contains($filename, '://'))">
179 <xsl:value-of select="$img.src.path"/>
181 <xsl:value-of select="$filename"/>
188 <xsl:template name="image.content.type">
189 <xsl:if test="@format">
190 <xsl:call-template name="graphic.format.content-type">
191 <xsl:with-param name="format" select="@format"/>
196 <xsl:template name="image.bgcolor">
197 <xsl:call-template name="pi.dbfo_background-color">
198 <xsl:with-param name="node" select=".."/>
202 <xsl:template name="image.width">
204 <xsl:when test="$ignore.image.scaling != 0">auto</xsl:when>
205 <xsl:when test="contains(@width,'%')">
206 <xsl:value-of select="@width"/>
208 <xsl:when test="@width and not(@width = '')">
209 <xsl:call-template name="length-spec">
210 <xsl:with-param name="length" select="@width"/>
211 <xsl:with-param name="default.units" select="'px'"/>
214 <xsl:when test="not(@depth) and $default.image.width != ''">
215 <xsl:call-template name="length-spec">
216 <xsl:with-param name="length" select="$default.image.width"/>
217 <xsl:with-param name="default.units" select="'px'"/>
220 <xsl:otherwise>auto</xsl:otherwise>
224 <xsl:template name="image.height">
226 <xsl:when test="$ignore.image.scaling != 0">auto</xsl:when>
227 <xsl:when test="contains(@depth,'%')">
228 <xsl:value-of select="@depth"/>
230 <xsl:when test="@depth">
231 <xsl:call-template name="length-spec">
232 <xsl:with-param name="length" select="@depth"/>
233 <xsl:with-param name="default.units" select="'px'"/>
236 <xsl:otherwise>auto</xsl:otherwise>
240 <xsl:template name="image.content.width">
241 <xsl:param name="scalefit" select="0"/>
242 <xsl:param name="scale" select="'1.0'"/>
245 <xsl:when test="$ignore.image.scaling != 0">auto</xsl:when>
246 <xsl:when test="contains(@contentwidth,'%')">
247 <xsl:value-of select="@contentwidth"/>
249 <xsl:when test="@contentwidth">
250 <xsl:call-template name="length-spec">
251 <xsl:with-param name="length" select="@contentwidth"/>
252 <xsl:with-param name="default.units" select="'px'"/>
255 <xsl:when test="number($scale) != 1.0">
256 <xsl:value-of select="$scale * 100"/>
257 <xsl:text>%</xsl:text>
259 <xsl:when test="$scalefit = 1">scale-to-fit</xsl:when>
260 <xsl:otherwise>auto</xsl:otherwise>
264 <xsl:template name="image.content.height">
265 <xsl:param name="scalefit" select="0"/>
266 <xsl:param name="scale" select="0"/>
269 <xsl:when test="$ignore.image.scaling != 0">auto</xsl:when>
270 <xsl:when test="contains(@contentdepth,'%')">
271 <xsl:value-of select="@contentdepth"/>
273 <xsl:when test="@contentdepth">
274 <xsl:call-template name="length-spec">
275 <xsl:with-param name="length" select="@contentdepth"/>
276 <xsl:with-param name="default.units" select="'px'"/>
279 <xsl:when test="number($scale) != 1.0">
280 <xsl:value-of select="$scale * 100"/>
281 <xsl:text>%</xsl:text>
283 <xsl:when test="$scalefit = 1">scale-to-fit</xsl:when>
284 <xsl:otherwise>auto</xsl:otherwise>
288 <xsl:template name="image.align">
289 <xsl:value-of select="@align"/>
292 <xsl:template name="image.valign">
293 <xsl:if test="@valign">
295 <xsl:when test="ancestor::inlinemediaobject or ancestor-or-self::inlinegraphic">
297 <xsl:when test="@valign = 'top'">baseline</xsl:when>
298 <xsl:when test="@valign = 'middle'">central</xsl:when>
299 <xsl:when test="@valign = 'bottom'">text-before-edge</xsl:when>
304 <xsl:when test="@valign = 'top'">before</xsl:when>
305 <xsl:when test="@valign = 'middle'">center</xsl:when>
306 <xsl:when test="@valign = 'bottom'">after</xsl:when>
314 <xsl:template name="process.image">
315 <!-- When this template is called, the current node should be -->
316 <!-- a graphic, inlinegraphic, imagedata, or videodata. All -->
317 <!-- those elements have the same set of attributes, so we can -->
318 <!-- handle them all in one place. -->
320 <!-- Compute each attribute value with its own customizable template call -->
321 <xsl:variable name="scalefit">
322 <xsl:call-template name="image.scalefit"/>
325 <xsl:variable name="scale">
326 <xsl:call-template name="image.scale"/>
329 <xsl:variable name="filename">
330 <xsl:call-template name="image.filename"/>
333 <xsl:variable name="src">
334 <xsl:call-template name="image.src">
335 <xsl:with-param name="filename" select="$filename"/>
339 <xsl:variable name="content.type">
340 <xsl:call-template name="image.content.type"/>
343 <xsl:variable name="bgcolor">
344 <xsl:call-template name="image.bgcolor"/>
347 <xsl:variable name="width">
348 <xsl:call-template name="image.width"/>
351 <xsl:variable name="height">
352 <xsl:call-template name="image.height"/>
355 <xsl:variable name="content.width">
356 <xsl:call-template name="image.content.width">
357 <xsl:with-param name="scalefit" select="$scalefit"/>
358 <xsl:with-param name="scale" select="$scale"/>
362 <xsl:variable name="content.height">
363 <xsl:call-template name="image.content.height">
364 <xsl:with-param name="scalefit" select="$scalefit"/>
365 <xsl:with-param name="scale" select="$scale"/>
369 <xsl:variable name="align">
370 <xsl:call-template name="image.align"/>
373 <xsl:variable name="valign">
374 <xsl:call-template name="image.valign"/>
377 <xsl:variable name="element.name">
379 <xsl:when test="svg:*" xmlns:svg="http://www.w3.org/2000/svg">
380 <xsl:text>fo:instream-foreign-object</xsl:text>
382 <xsl:when test="mml:*" xmlns:mml="http://www.w3.org/1998/Math/MathML">
383 <xsl:text>fo:instream-foreign-object</xsl:text>
386 <xsl:text>fo:external-graphic</xsl:text>
391 <xsl:element name="{$element.name}">
393 <xsl:if test="$src != ''">
394 <xsl:attribute name="src">
395 <xsl:value-of select="$src"/>
399 <xsl:if test="$width != ''">
400 <xsl:attribute name="width">
401 <xsl:value-of select="$width"/>
405 <xsl:if test="$height != ''">
406 <xsl:attribute name="height">
407 <xsl:value-of select="$height"/>
411 <xsl:if test="$content.width != ''">
412 <xsl:attribute name="content-width">
413 <xsl:value-of select="$content.width"/>
417 <xsl:if test="$content.height != ''">
418 <xsl:attribute name="content-height">
419 <xsl:value-of select="$content.height"/>
423 <xsl:if test="$content.type != ''">
424 <xsl:attribute name="content-type">
425 <xsl:value-of select="concat('content-type:',$content.type)"/>
429 <xsl:if test="$bgcolor != ''">
430 <xsl:attribute name="background-color">
431 <xsl:value-of select="$bgcolor"/>
435 <xsl:if test="$align != ''">
436 <xsl:attribute name="text-align">
437 <xsl:value-of select="$align"/>
441 <xsl:if test="$valign != ''">
442 <xsl:variable name="att.name">
444 <xsl:when test="ancestor::inlinemediaobject or ancestor-or-self::inlinegraphic">
445 <xsl:text>alignment-baseline</xsl:text>
448 <xsl:text>display-align</xsl:text>
452 <xsl:attribute name="{$att.name}">
453 <xsl:value-of select="$valign"/>
457 <!-- copy literal SVG elements to output -->
458 <xsl:if test="svg:*" xmlns:svg="http://www.w3.org/2000/svg">
459 <xsl:call-template name="process.svg"/>
462 <xsl:if test="mml:*" xmlns:mml="http://www.w3.org/1998/Math/MathML">
463 <xsl:call-template name="process.mml"/>
469 <!-- ==================================================================== -->
471 <xsl:template match="graphic">
473 <xsl:when test="parent::inlineequation">
474 <xsl:call-template name="process.image"/>
478 <xsl:call-template name="anchor"/>
479 <xsl:if test="@align">
480 <xsl:attribute name="text-align">
481 <xsl:value-of select="@align"/>
484 <xsl:call-template name="process.image"/>
490 <xsl:template match="inlinegraphic">
491 <xsl:variable name="vendor" select="system-property('xsl:vendor')"/>
492 <xsl:variable name="filename">
494 <xsl:when test="@entityref">
495 <xsl:value-of select="unparsed-entity-uri(@entityref)"/>
498 <xsl:apply-templates select="@fileref"/>
504 <xsl:when test="@format='linespecific'">
506 <xsl:when test="$use.extensions != '0'
507 and $textinsert.extension != '0'">
509 <xsl:when test="contains($vendor, 'SAXON')">
510 <stext:insertfile href="{$filename}" encoding="{$textdata.default.encoding}"/>
512 <xsl:when test="contains($vendor, 'Apache Software Foundation')">
513 <xtext:insertfile href="{$filename}"/>
516 <xsl:message terminate="yes">
517 <xsl:text>Don't know how to insert files with </xsl:text>
518 <xsl:value-of select="$vendor"/>
524 <xsl:message terminate="yes">
525 <xsl:text>Cannot insert </xsl:text><xsl:value-of select="$filename"/>
526 <xsl:text>. Check use.extensions and textinsert.extension parameters.</xsl:text>
532 <xsl:call-template name="process.image"/>
537 <!-- ==================================================================== -->
539 <xsl:template match="mediaobject|mediaobjectco">
541 <xsl:variable name="olist" select="imageobject|imageobjectco
542 |videoobject|audioobject
545 <xsl:variable name="object.index">
546 <xsl:call-template name="select.mediaobject.index">
547 <xsl:with-param name="olist" select="$olist"/>
548 <xsl:with-param name="count" select="1"/>
552 <xsl:variable name="object" select="$olist[position() = $object.index]"/>
554 <xsl:variable name="align">
555 <xsl:value-of select="$object/descendant::imagedata[@align][1]/@align"/>
558 <xsl:variable name="id">
559 <xsl:call-template name="object.id"/>
562 <fo:block id="{$id}">
563 <xsl:if test="$align != '' ">
564 <xsl:attribute name="text-align">
565 <xsl:value-of select="$align"/>
569 <xsl:apply-templates select="$object"/>
570 <xsl:apply-templates select="caption"/>
574 <xsl:template match="inlinemediaobject">
575 <xsl:call-template name="select.mediaobject"/>
578 <!-- ==================================================================== -->
580 <xsl:template match="imageobjectco">
582 <!-- select one imageobject? -->
583 <xsl:when test="$use.role.for.mediaobject != 0 and
584 count(imageobject) > 1 and
586 <xsl:variable name="olist" select="imageobject"/>
588 <xsl:variable name="object.index">
589 <xsl:call-template name="select.mediaobject.index">
590 <xsl:with-param name="olist" select="$olist"/>
591 <xsl:with-param name="count" select="1"/>
595 <xsl:variable name="object" select="$olist[position() = $object.index]"/>
597 <xsl:apply-templates select="$object"/>
600 <!-- otherwise process them all -->
601 <xsl:apply-templates select="imageobject"/>
605 <xsl:apply-templates select="calloutlist"/>
609 <xsl:template match="imageobject">
611 <xsl:when test="imagedata">
612 <xsl:apply-templates select="imagedata"/>
615 <fo:instream-foreign-object>
616 <xsl:apply-templates mode="copy-all"/>
617 </fo:instream-foreign-object>
622 <!-- ==================================================================== -->
624 <xsl:template match="*" mode="copy-all">
626 <xsl:for-each select="@*">
629 <xsl:apply-templates mode="copy-all"/>
633 <xsl:template match="text()|comment()|processing-instruction()" mode="copy-all">
637 <xsl:template name="process.mml">
638 <xsl:apply-templates mode="copy-all" select="*"/>
641 <xsl:template name="process.svg">
642 <xsl:apply-templates mode="copy-all" select="*"/>
645 <!-- ==================================================================== -->
647 <xsl:template match="imagedata">
649 <xsl:when test="@format='linespecific'">
650 <xsl:variable name="vendor" select="system-property('xsl:vendor')"/>
652 <xsl:variable name="filename">
653 <xsl:call-template name="mediaobject.filename">
654 <xsl:with-param name="object" select=".."/>
659 <xsl:when test="$use.extensions != '0'
660 and $textinsert.extension != '0'">
662 <xsl:when test="contains($vendor, 'SAXON')">
663 <stext:insertfile href="{$filename}" encoding="{$textdata.default.encoding}"/>
665 <xsl:when test="contains($vendor, 'Apache Software Foundation')">
666 <xtext:insertfile href="{$filename}"/>
669 <xsl:message terminate="yes">
670 <xsl:text>Don't know how to insert files with </xsl:text>
671 <xsl:value-of select="$vendor"/>
677 <xsl:message terminate="yes">
678 <xsl:text>Cannot insert </xsl:text><xsl:value-of select="$filename"/>
679 <xsl:text>. Check use.extensions and textinsert.extension parameters.</xsl:text>
685 <xsl:call-template name="process.image"/>
690 <!-- ==================================================================== -->
692 <xsl:template match="videoobject">
693 <xsl:apply-templates select="videodata"/>
696 <xsl:template match="videodata">
697 <xsl:call-template name="process.image"/>
700 <!-- ==================================================================== -->
702 <xsl:template match="audioobject">
703 <xsl:apply-templates select="audiodata"/>
706 <xsl:template match="audiodata">
707 <xsl:call-template name="process.image"/>
710 <!-- ==================================================================== -->
712 <xsl:template match="textobject">
713 <xsl:apply-templates/>
716 <xsl:template match="textdata">
717 <xsl:variable name="vendor" select="system-property('xsl:vendor')"/>
718 <xsl:variable name="filename">
720 <xsl:when test="@entityref">
721 <xsl:value-of select="unparsed-entity-uri(@entityref)"/>
724 <xsl:apply-templates select="@fileref"/>
729 <xsl:variable name="encoding">
731 <xsl:when test="@encoding">
732 <xsl:value-of select="@encoding"/>
735 <xsl:value-of select="$textdata.default.encoding"/>
741 <xsl:when test="$use.extensions != '0'
742 and $textinsert.extension != '0'">
744 <xsl:when test="element-available('stext:insertfile')">
745 <stext:insertfile href="{$filename}" encoding="{$encoding}"/>
747 <xsl:when test="element-available('xtext:insertfile')">
748 <xtext:insertfile href="{$filename}"/>
751 <xsl:message terminate="yes">
752 <xsl:text>Don't know how to insert files with </xsl:text>
753 <xsl:value-of select="$vendor"/>
759 <xsl:message terminate="yes">
760 <xsl:text>Cannot insert </xsl:text><xsl:value-of select="$filename"/>
761 <xsl:text>. Check use.extensions and textinsert.extension parameters.</xsl:text>
767 <!-- ==================================================================== -->
769 <xsl:template match="mediaobject/caption|figure/caption">
771 <xsl:if test="@align = 'right' or @align = 'left' or @align='center'">
772 <xsl:attribute name="text-align"><xsl:value-of
773 select="@align"/></xsl:attribute>
775 <xsl:apply-templates/>
779 <!-- ==================================================================== -->
781 <xsl:template name="fo-external-image">
782 <xsl:param name="filename"/>
785 <xsl:when test="$fop.extensions != 0">
786 <xsl:value-of select="$filename"/>
789 <xsl:value-of select="concat('url(', $filename, ')')"/>
794 <!-- Resolve xml:base attributes -->
795 <xsl:template match="@fileref">
796 <!-- need a check for absolute urls -->
798 <xsl:when test="contains(., ':') or starts-with(.,'/')">
799 <!-- it has a uri scheme or starts with '/', so it is an absolute uri -->
800 <xsl:value-of select="."/>
802 <xsl:when test="$keep.relative.image.uris != 0">
803 <!-- leave it alone -->
804 <xsl:value-of select="."/>
807 <!-- its a relative uri -->
808 <xsl:call-template name="relative-uri">