1 <?xml version="1.0" encoding="UTF-8"?>
4 odt2phpwiki: OpenDocument to Phpwiki transformation
6 Copyright (C) 2007 Bernhard Haumacher (haui at haumacher dot de)
7 Copyright (C) 2008 Marc-Etienne Vargenau, Alcatel-Lucent
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License along
20 with this program; if not, write to the Free Software Foundation, Inc.,
21 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
23 This program is based on the OpenDocument to Mediawiki converter by
26 Modifications to convert to Phpwiki were made by Marc-Etienne Vargenau
27 and are Copyright (C) 2008 Alcatel-Lucent
29 Standard Alcatel-Lucent disclaimer for contributing to open source
31 "The OpenDocument to Phpwiki converter ("Contribution") has not been tested and/or
32 validated for release as or in products, combinations with products or
33 other commercial use. Any use of the Contribution is entirely made at
34 the user's own responsibility and the user can not rely on any features,
35 functionalities or performances Alcatel-Lucent has attributed to the
38 THE CONTRIBUTION BY ALCATEL-LUCENT IS PROVIDED AS IS, WITHOUT WARRANTY
39 OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE
40 WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, COMPLIANCE,
41 NON-INTERFERENCE AND/OR INTERWORKING WITH THE SOFTWARE TO WHICH THE
42 CONTRIBUTION HAS BEEN MADE, TITLE AND NON-INFRINGEMENT. IN NO EVENT SHALL
43 ALCATEL-LUCENT BE LIABLE FOR ANY DAMAGES OR OTHER LIABLITY, WHETHER IN
44 CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
45 CONTRIBUTION OR THE USE OR OTHER DEALINGS IN THE CONTRIBUTION, WHETHER
46 TOGETHER WITH THE SOFTWARE TO WHICH THE CONTRIBUTION RELATES OR ON A STAND
50 <stylesheet version="1.0"
51 xmlns="http://www.w3.org/1999/XSL/Transform"
53 xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0"
54 xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0"
55 xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0"
56 xmlns:table="urn:oasis:names:tc:opendocument:xmlns:table:1.0"
57 xmlns:draw="urn:oasis:names:tc:opendocument:xmlns:drawing:1.0"
58 xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0"
59 xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0"
60 xmlns:number="urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0"
61 xmlns:svg="urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0"
62 xmlns:chart="urn:oasis:names:tc:opendocument:xmlns:chart:1.0"
63 xmlns:dr3d="urn:oasis:names:tc:opendocument:xmlns:dr3d:1.0"
64 xmlns:form="urn:oasis:names:tc:opendocument:xmlns:form:1.0"
65 xmlns:script="urn:oasis:names:tc:opendocument:xmlns:script:1.0"
66 xmlns:xlink="http://www.w3.org/1999/xlink"
67 xmlns:dc="http://purl.org/dc/elements/1.1/"
68 xmlns:math="http://www.w3.org/1998/Math/MathML"
69 xmlns:dom="http://www.w3.org/2001/xml-events"
70 xmlns:xforms="http://www.w3.org/2002/xforms"
71 xmlns:xsd="http://www.w3.org/2001/XMLSchema"
72 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
76 == Customization options ==
79 <!-- Constant defining the newline token. -->
80 <param name="NL" select="' '"/>
82 <!-- String that a tabulator is expanded with in preformatted paragraphs. -->
83 <param name="CODE_TAB_REPLACEMENT">
84 <variable name="document-value"
85 select="/office:document/office:meta/meta:user-defined[@meta:name='CODE_TAB_REPLACEMENT']"/>
87 <when test="boolean($document-value)">
88 <value-of select="$document-value"/>
92 <value-of select="' '"/>
98 Switch that suppresses separation of paragraphs with empty lines.
99 (Set to 1 to activate) -->
100 <param name="CODE_JOIN_PARAGRAPHS"
101 select="boolean(string(/office:document/office:meta/meta:user-defined[@meta:name='CODE_JOIN_PARAGRAPHS']) != 'false')"/>
103 <param name="CODE_STYLES">
104 <variable name="document-value"
105 select="/office:document/office:meta/meta:user-defined[@meta:name='CODE_STYLES']"/>
107 <when test="boolean($document-value)">
108 <value-of select="$document-value"/>
112 <value-of select="''"/>
118 == Wiki style constants ==
121 <!-- Bold character style. -->
122 <variable name="BOLD_BIT" select="1"/>
124 <!-- Italic character style. -->
125 <variable name="ITALIC_BIT" select="2"/>
127 <!-- Subscript character style. -->
128 <variable name="SUBSCRIPT_BIT" select="4"/>
130 <!-- Superscript character style. -->
131 <variable name="SUPERSCRIPT_BIT" select="8"/>
133 <!-- Typewriter character style. -->
134 <variable name="TYPEWRITER_BIT" select="16"/>
136 <!-- Preformatted text paragraph style. -->
137 <variable name="CODE_BIT" select="32"/>
139 <!-- Centered paragraph style. -->
140 <variable name="CENTER_BIT" select="64"/>
142 <!-- Right aligned paragraph style. -->
143 <variable name="RIGHT_BIT" select="128"/>
145 <!-- Constant defining the empty style. -->
146 <variable name="NO_STYLE" select="0"/>
152 media-type="text/plain"
158 == Reference resolution ==
163 match="//style:style"
168 name="list-style-ref"
169 match="//text:list-style"
175 match="//style:font-face"
180 name="reference-resolution"
181 match="//text:reference-mark | //text:reference-mark-start"
187 Multiple pages (draw only)
190 <template match="draw:page">
191 <value-of select="concat(' <!-- Page ', @draw:name, '--> ')"/>
193 <value-of select="' ---- '"/>
201 <template match="text:list">
203 Check, whether this list is used to implement the outline numbering
204 for headings. Such list must not be exported, because within the wiki,
205 automatic outline numbering is performed. An outline list has a single
206 text:h element as its single leaf grandchild.
208 This method of section numbering seems not to be used when creating new
209 documents with OpenOffice.org 2.2, but the document containing the
210 OpenDocument specification version 1.1 uses such numbering through nested
214 <when test="boolean(./descendant::node()[not(./self::text:list) and not(./self::text:list-item) and not(./ancestor-or-self::text:h)])">
219 <apply-templates select=".//text:h"/>
224 <template match="text:list-item">
225 <if test="position() > 1 or boolean(ancestor::text:list-item)">
226 <value-of select="$NL"/>
228 <variable name="list-style"
229 select="key('list-style-ref',ancestor::text:list[boolean(@text:style-name)][1]/@text:style-name)"/>
230 <call-template name="mk-list-token">
231 <with-param name="list-style" select="$list-style"/>
232 <with-param name="level" select="count(ancestor::text:list)"/>
236 <if test="position() = last() and not(boolean(ancestor::text:list-item))">
237 <!-- End of (potentially nested) list is marked with a double newline. -->
238 <value-of select="$NL"/>
239 <value-of select="$NL"/>
243 <template name="mk-list-token">
244 <param name="list-style"/>
245 <param name="level"/>
247 <if test="$level > 1">
248 <call-template name="mk-list-token">
249 <with-param name="list-style" select="$list-style"/>
250 <with-param name="level" select="$level - 1"/>
254 <variable name="number-style" select="$list-style/text:list-level-style-number[@text:level=$level]"/>
255 <variable name="bullet-style" select="$list-style/text:list-level-style-bullet[@text:level=$level]"/>
257 <when test="boolean($number-style)">
259 <when test="string-length($number-style/@style:num-format) > 0">
267 <when test="boolean($bullet-style)">
278 <template match="text:h">
279 <if test="string-length(.) > 0">
280 <variable name="token">
281 <call-template name="mk-heading-prefix">
282 <with-param name="level" select="@text:outline-level"/>
285 <value-of select="$token"/>
288 <value-of select="$NL"/>
292 <template match="text:index-title">
296 <value-of select="$NL"/>
300 Function generating a wiki heading prefix.
303 The heading level. The value must be between 1 and 3.
305 <template name="mk-heading-prefix">
306 <param name="level"/>
308 <when test="$level > 3">
309 <call-template name="mk-heading-prefix">
310 <with-param name="level" select="3 - $level"/>
313 <when test="$level > 0">
315 <call-template name="mk-heading-prefix">
316 <with-param name="level" select="$level + 1"/>
323 Function generating a token consisting of the given character
324 repeated 'level' times.
327 The lengh of the result.
329 The character that should be repeated 'level' times.
331 <template name="mk-token">
332 <param name="level"/>
334 <if test="$level > 0">
335 <value-of select="$char"/>
336 <call-template name="mk-token">
337 <with-param name="level" select="$level - 1"/>
338 <with-param name="char" select="$char"/>
348 <template match="table:table">
350 <text><?plugin MediawikiTable</text>
352 <text>{| class="bordered"</text>
363 <template match="table:table-header-rows">
367 <template match="table:table-row[position() < last()] | table:table-header-rows/table:table-row">
374 <template match="table:table-row">
378 <template match="table:table-header-rows//table:table-cell">
380 <if test="@table:number-columns-spanned">
381 <text>colspan="</text>
382 <value-of select="@table:number-columns-spanned"/>
386 <value-of select="$NL"/>
389 <template match="table:table-cell">
391 <if test="@table:number-columns-spanned">
392 <text>colspan="</text>
393 <value-of select="@table:number-columns-spanned"/>
397 <value-of select="$NL"/>
405 <template match="text:span[@text:style-name='WikiMath']">
406 <value-of select="'<math>'"/>
408 <value-of select="'</math>'"/>
416 <template match="text:a">
417 <variable name="link-ref" select="@xlink:href"/>
419 <when test="string-length($link-ref) > 0">
420 <variable name="link-label" select="string(.)"/>
422 <value-of select="$link-ref"/>
424 <value-of select="$link-label"/>
439 <template match="text:span[@text:style-name='WikiLink']">
440 <value-of select="'['"/>
441 <variable name="link-def" select="string(.)"/>
442 <variable name="link-label" select="normalize-space(substring-before($link-def, '['))"/>
443 <variable name="link-ref" select="normalize-space(substring-before(substring-after($link-def, '['), ']'))"/>
445 <when test="boolean($link-ref)">
446 <value-of select="concat($link-label, '|', $link-ref)"/>
449 <value-of select="$link-def"/>
452 <value-of select="']'"/>
460 <template match="text:p[string-length(.) > 0]">
461 <variable name="style">
462 <call-template name="mk-style-set">
463 <with-param name="node" select="."/>
467 <variable name="code"
468 select="($style mod (2 * $CODE_BIT)) - ($style mod ($CODE_BIT)) != 0"/>
469 <variable name="center"
470 select="($style mod (2 * $CENTER_BIT)) - ($style mod ($CENTER_BIT)) != 0"/>
471 <variable name="right"
472 select="($style mod (2 * $RIGHT_BIT)) - ($style mod ($RIGHT_BIT)) != 0"/>
475 <when test="$center">
480 <value-of select="' '"/>
487 <when test="$center">
493 <variable name="paragraph-right"
494 select="./following-sibling::*[1]/self::text:p"/>
497 <when test="boolean($paragraph-right)">
499 Insert end of line only if not within a list. Within wiki lists,
500 a line break leaves the current list item.
503 <when test="boolean(ancestor::text:list-item)">
504 <text><br/> </text>
507 <variable name="style-right">
508 <call-template name="mk-style-set">
509 <with-param name="node" select="$paragraph-right"/>
513 <variable name="code-right"
514 select="($style-right mod (2 * $CODE_BIT)) - ($style-right mod ($CODE_BIT)) != 0"/>
517 <when test="$code-right">
519 <when test="$CODE_JOIN_PARAGRAPHS">
520 <value-of select="$NL"/>
524 <value-of select="$NL"/>
525 <value-of select="' '"/>
526 <value-of select="$NL"/>
531 <value-of select="$NL"/>
532 <value-of select="$NL"/>
537 <value-of select="$NL"/>
538 <value-of select="$NL"/>
542 <when test="boolean(./following-sibling::*[1]/self::text:h) or boolean(./following-sibling::*[1]/self::table:table) or boolean(./following-sibling::*[1]/self::text:bibliography)">
543 <!-- Newline before following heading or table. -->
544 <value-of select="$NL"/>
545 <value-of select="$NL"/>
547 <when test="./following-sibling::*[1]/self::text:list and not(ancestor::text:list-item)">
548 <value-of select="$NL"/>
549 <value-of select="$NL"/>
554 <template match="text:p[string-length(.) = 0 and string-length(preceding-sibling::*[1]/self::text:p) > 0]">
555 <value-of select="$NL"/>
560 == Preformatted text ==
563 <template match="text:s">
564 <variable name="style">
565 <call-template name="mk-style-set">
566 <with-param name="node" select="."/>
570 <variable name="code"
571 select="($style mod (2 * $CODE_BIT)) - ($style mod ($CODE_BIT)) != 0"/>
575 <when test="@text:c">
576 <call-template name="mk-token">
577 <with-param name="level" select="@text:c"/>
578 <with-param name="char" select="' '"/>
582 <value-of select="' '"/>
588 <template match="text:tab">
589 <variable name="style">
590 <call-template name="mk-style-set">
591 <with-param name="node" select="."/>
595 <variable name="code"
596 select="($style mod (2 * $CODE_BIT)) - ($style mod ($CODE_BIT)) != 0"/>
599 <value-of select="$CODE_TAB_REPLACEMENT"/>
603 <template match="text:line-break">
604 <variable name="style">
605 <call-template name="mk-style-set">
606 <with-param name="node" select="."/>
610 <variable name="code"
611 select="($style mod (2 * $CODE_BIT)) - ($style mod ($CODE_BIT)) != 0"/>
614 <value-of select="$NL"/>
615 <value-of select="' '"/>
623 <template match="text:note-body">
624 <variable name="note" select="./parent::text:note"/>
626 <if test="$note/@text:note-class = 'footnote'">
627 <text><ref name="</text>
628 <value-of select="$note/@text:id"/>
631 <text></ref></text>
635 <template match="text:note-ref[@text:note-class='footnote']">
636 <text><ref name="</text>
637 <value-of select="@text:ref-name"/>
646 <template match="draw:text-box[boolean(.//draw:image)]">
647 <variable name="image" select=".//draw:image[1]"/>
649 <variable name="image-description">
654 <call-template name="mk-image-name">
655 <with-param name="image" select="$image"/>
658 <value-of select="normalize-space($image-description)"/>
662 <template match="draw:image[not(boolean(ancestor::draw:text-box))]">
664 <call-template name="mk-image-name">
665 <with-param name="image" select="."/>
670 <template name="mk-image-name">
671 <param name="image"/>
673 <variable name="base-name">
674 <call-template name="mk-base-name">
675 <with-param name="href" select="$image/@xlink:href"/>
679 <if test="not(starts-with($base-name, 'Image:'))">
680 <value-of select="'Image:'"/>
682 <value-of select="$base-name"/>
685 <template name="mk-base-name">
688 <variable name="result" select="substring-after($href, '/')"/>
690 <when test="boolean($result)">
691 <call-template name="mk-base-name">
692 <with-param name="href" select="$result"/>
696 <value-of select="$href"/>
706 <!-- TODO: text:bibliography-mark -->
708 <template match="text:reference-ref">
709 <variable name="reference-mark" select="key('reference-resolution', @text:ref-name)"/>
712 <when test="boolean($reference-mark)">
714 In wiki syntax, only a local reference to a heading can be inserted.
715 If the link target is a descendant of a heading element, a link can be
716 inserted in the result. -->
717 <variable name="header-anchor" select="$reference-mark/ancestor::text:h[1]"/>
718 <if test="boolean($header-anchor)">
720 <value-of select="string($header-anchor)"/>
724 <variable name="reference-text" select="string(.)"/>
727 <!-- Check, whether the reference text is cached in the document. -->
728 <when test="string-length($reference-text) > 0">
729 <value-of select="$reference-text"/>
734 TODO: Evaluate the @text:reference-format attribute and
735 generate the replacement text (difficult).-->
736 <text>(REFERENCE TEXT UNAVAILABLE: "</text>
737 <value-of select="@text:ref-name"/>
742 <if test="boolean($header-anchor)">
748 <text>(UNDEFINED REFERENCE: "</text>
749 <value-of select="@text:ref-name"/>
755 <template match="text:reference-mark">
756 <!-- TODO: Output an anchor. -->
760 <template match="text:reference-mark-start">
761 <!-- TODO: Output an anchor. -->
768 <template match="text:p/text() | text:h/text() | text:span/text() | text:sequence/text() | text:sequence-ref/text() | text:a/text() | text:bookmark-ref/text() | text:reference-mark/text() | text:date/text() | text:time/text() | text:page-number/text() | text:sender-firstname/text() | text:sender-lastname/text() | text:sender-initials/text() | text:sender-title/text() | text:sender-position/text() | text:sender-email/text() | text:sender-phone-private/text() | text:sender-fax/text() | text:sender-company/text() | text:sender-phone-work/text() | text:sender-street/text() | text:sender-city/text() | text:sender-postal-code/text() | text:sender-country/text() | text:sender-state-or-province/text() | text:author-name/text() | text:author-initials/text() | text:chapter/text() | text:file-name/text() | text:template-name/text() | text:sheet-name/text() | text:variable-get/text() | text:variable-input/text() | text:user-field-get/text() | text:user-field-input/text() | text:expression/text() | text:text-input/text() | text:initial-creator/text() | text:creation-date/text() | text:creation-time/text() | text:description/text() | text:user-defined/text() | text:print-date/text() | text:printed-by/text() | text:title/text() | text:subject/text() | text:keywords/text() | text:editing-cycles/text() | text:editing-duration/text() | text:modification-date/text() | text:creator/text() | text:modification-time/text() | text:page-count/text() | text:paragraph-count/text() | text:word-count/text() | text:character-count/text() | text:table-count/text() | text:image-count/text() | text:object-count/text() | text:database-display/text() | text:database-row-number/text() | text:database-name/text() | text:page-variable-get/text() | text:placeholder/text() | text:conditional-text/text() | text:hidden-text/text() | text:execute-macro/text() | text:dde-connection/text() | text:measure/text() | text:table-formula/text()">
770 <when test="boolean(./ancestor::table:table-header-rows | ./ancestor::text:h)">
772 No explicit styles within table headings or section headings,
773 because those styles are consistently declared by the Wiki engine. -->
774 <value-of select="."/>
777 <when test="string-length(.) > 0">
778 <variable name="style">
779 <call-template name="mk-style-set">
780 <with-param name="node" select="."/>
784 <variable name="current-paragraph"
785 select="./ancestor::text:p[1]"/>
786 <variable name="paragraph-id"
787 select="generate-id($current-paragraph)"/>
788 <variable name="frames"
789 select="$current-paragraph/descendant::draw:frame"/>
790 <variable name="frame-count"
791 select="count($frames)"/>
794 The current style context consists of all text nodes that are
795 descendants of the paragraph ancestor of this text node but not
796 descendants of any frame nodes that are descendants of the current
797 text nodes paragraph.
799 <variable name="context"
800 select="$current-paragraph//text()[not(boolean(./ancestor::draw:frame[1]) and count(./ancestor::draw:frame[1] | $frames) = $frame-count)]"/>
801 <variable name="context-size" select="count($context)"/>
803 <variable name="context-index">
804 <call-template name="mk-context-index">
805 <with-param name="current-id" select="generate-id(.)"/>
806 <with-param name="context" select="$context"/>
807 <with-param name="test-index" select="1"/>
811 <variable name="style-left">
813 <when test="$context-index > 1">
814 <variable name="left" select="$context[$context-index - 1]"/>
816 The preceding text node is a child of this nodes topmost
817 styled ancestor. This means that the result of the
818 transformation will be directly concatenated.
820 <call-template name="mk-style-set">
821 <with-param name="node" select="$left"/>
825 <value-of select="$NO_STYLE"/>
829 <variable name="style-right">
831 <when test="$context-index < count($context)">
832 <variable name="right" select="$context[$context-index + 1]"/>
834 The preceding text node is a child of this nodes topmost
835 styled ancestor. This means that the result of the
836 transformation will be directly concatenated.
838 <call-template name="mk-style-set">
839 <with-param name="node" select="$right"/>
843 <value-of select="$NO_STYLE"/>
848 <variable name="bold"
849 select="($style mod (2 * $BOLD_BIT)) != 0"/>
850 <variable name="italic"
851 select="($style mod (2 * $ITALIC_BIT)) - ($style mod ($ITALIC_BIT)) != 0"/>
852 <variable name="superscript"
853 select="($style mod (2 * $SUPERSCRIPT_BIT)) - ($style mod ($SUPERSCRIPT_BIT)) != 0"/>
854 <variable name="subscript"
855 select="($style mod (2 * $SUBSCRIPT_BIT)) - ($style mod ($SUBSCRIPT_BIT)) != 0"/>
856 <variable name="code"
857 select="($style mod (2 * $CODE_BIT)) - ($style mod ($CODE_BIT)) != 0"/>
858 <variable name="typewriter"
859 select="($style mod (2 * $TYPEWRITER_BIT)) - ($style mod ($TYPEWRITER_BIT)) != 0"/>
861 <variable name="bold-left"
862 select="($style-left mod (2 * $BOLD_BIT)) != 0"/>
863 <variable name="italic-left"
864 select="($style-left mod (2 * $ITALIC_BIT)) - ($style-left mod ($ITALIC_BIT)) != 0"/>
865 <variable name="superscript-left"
866 select="($style-left mod (2 * $SUPERSCRIPT_BIT)) - ($style-left mod ($SUPERSCRIPT_BIT)) != 0"/>
867 <variable name="subscript-left"
868 select="($style-left mod (2 * $SUBSCRIPT_BIT)) - ($style-left mod ($SUBSCRIPT_BIT)) != 0"/>
869 <variable name="typewriter-left"
870 select="($style-left mod (2 * $TYPEWRITER_BIT)) - ($style-left mod ($TYPEWRITER_BIT)) != 0"/>
872 <variable name="bold-right"
873 select="($style-right mod (2 * $BOLD_BIT)) != 0"/>
874 <variable name="italic-right"
875 select="($style-right mod (2 * $ITALIC_BIT)) - ($style-right mod ($ITALIC_BIT)) != 0"/>
876 <variable name="superscript-right"
877 select="($style-right mod (2 * $SUPERSCRIPT_BIT)) - ($style-right mod ($SUPERSCRIPT_BIT)) != 0"/>
878 <variable name="subscript-right"
879 select="($style-right mod (2 * $SUBSCRIPT_BIT)) - ($style-right mod ($SUBSCRIPT_BIT)) != 0"/>
880 <variable name="typewriter-right"
881 select="($style-right mod (2 * $TYPEWRITER_BIT)) - ($style-right mod ($TYPEWRITER_BIT)) != 0"/>
883 <!-- Debugging: Add style infos to the output. -->
885 <value-of select="'{'"/>
886 <value-of select="$style-left"/>
887 <value-of select="'-'"/>
888 <value-of select="$style"/>
889 <value-of select="','"/>
890 <value-of select="$context-size"/>
891 <value-of select="'}'"/>
894 <if test="$superscript and not($superscript-left)">
895 <text><sup></text>
897 <if test="$subscript and not($subscript-left)">
898 <text><sub></text>
900 <if test="not($code) and $typewriter and not($typewriter-left)">
901 <text><tt></text>
903 <if test="$bold and not($bold-left)">
904 <text><b></text>
906 <if test="$italic and not($italic-left)">
910 <call-template name="render-quoted-text">
911 <with-param name="text" select="."/>
914 <if test="$italic and not($italic-right)">
917 <if test="$bold and not($bold-right)">
918 <text></b></text>
920 <if test="not($code) and $typewriter and not($typewriter-right)">
921 <text></tt></text>
923 <if test="$subscript and not($subscript-right)">
924 <text></sub></text>
926 <if test="$superscript and not($superscript-right)">
927 <text></sup></text>
930 <!-- Debugging: Add style details to the output. -->
932 <value-of select="'{'"/>
933 <value-of select="$style"/>
934 <value-of select="'-'"/>
935 <value-of select="$style-right"/>
936 <value-of select="'}'"/>
944 Function for looking up the position of a node identified by the given
945 'current-id' within a node set 'context'.
947 The search starts with the the index 'test-index'. The search is recursive
948 in the 'test-index' argument. To save recursion depth, each recursive call
949 iteratively tests a fixed number of indexes (by loop unrolling).
951 <template name="mk-context-index">
952 <param name="current-id"/>
953 <param name="context"/>
954 <param name="test-index"/>
956 <variable name="context-size" select="count($context)"/>
959 <when test="context-size < $test-index">
961 <when test="$current-id = generate-id($context[$test-index])">
962 <value-of select="$test-index"/>
964 <when test="context-size < ($test-index + 1)">
966 <when test="$current-id = generate-id($context[$test-index + 1])">
967 <value-of select="$test-index + 1"/>
969 <when test="context-size < ($test-index + 2)">
971 <when test="$current-id = generate-id($context[$test-index + 2])">
972 <value-of select="$test-index + 2"/>
974 <when test="context-size < ($test-index + 3)">
976 <when test="$current-id = generate-id($context[$test-index + 3])">
977 <value-of select="$test-index + 3"/>
979 <when test="context-size < ($test-index + 4)">
981 <when test="$current-id = generate-id($context[$test-index + 4])">
982 <value-of select="$test-index + 4"/>
984 <when test="context-size < ($test-index + 5)">
986 <when test="$current-id = generate-id($context[$test-index + 5])">
987 <value-of select="$test-index + 5"/>
989 <when test="context-size < ($test-index + 6)">
992 <call-template name="mk-context-index">
993 <with-param name="current-id" select="$current-id"/>
994 <with-param name="context" select="$context"/>
995 <with-param name="test-index" select="$test-index + 6"/>
1001 <template name="render-quoted-text">
1002 <param name="text"/>
1005 <when test="contains($text, '<') or contains($text, '[') or starts-with($text, '----') or starts-with($text, '=') or starts-with($text, '*') or starts-with($text, ';') or starts-with($text, '#')">
1006 <text><nowiki></text>
1008 <when test="contains($text, '</nowiki>')">
1009 <call-template name="render-escaped-text">
1010 <with-param name="text" select="$text"/>
1014 <call-template name="render-encoded-text">
1015 <with-param name="text" select="$text"/>
1019 <text></nowiki></text>
1022 <call-template name="render-encoded-text">
1023 <with-param name="text" select="$text"/>
1029 <template name="render-escaped-text">
1030 <param name="text"/>
1033 <when test="contains($text, '<')">
1034 <call-template name="render-encoded-text">
1035 <with-param name="text" select="substring-before($text, '<')"/>
1037 <value-of select="'&lt;'"/>
1038 <call-template name="render-escaped-text">
1039 <with-param name="text" select="substring-after($text, '<')"/>
1043 <call-template name="render-encoded-text">
1044 <with-param name="text" select="$text"/>
1050 <template name="render-encoded-text">
1051 <param name="text"/>
1054 <when test="contains($text, ' ')">
1055 <value-of select="substring-before($text, ' ')"/>
1056 <value-of select="'&nbsp;'"/>
1057 <call-template name="render-encoded-text">
1058 <with-param name="text" select="substring-after($text, ' ')"/>
1062 <value-of select="$text"/>
1068 == Wiki styles: bold, italics, ... ==
1071 <template name="mk-style-set">
1072 <param name="node"/>
1076 select="$node/ancestor-or-self::*[@text:style-name][1]"
1080 <when test="boolean($context)">
1083 select="key('style-ref', $context/@text:style-name)"
1086 <!-- Debugging: Print inspected styles. -->
1089 <value-of select="'=== '"/>
1090 <value-of select="$style/@style:name"/>
1091 <value-of select="' ==='"/>
1095 <call-template name="mk-style-set-internal">
1096 <with-param name="node" select="$context"/>
1097 <with-param name="style" select="$style"/>
1098 <with-param name="style-set" select="$NO_STYLE"/>
1099 <with-param name="style-mask" select="$NO_STYLE"/>
1103 <value-of select="$NO_STYLE"/>
1109 Compute the wiki style set that corresponds
1110 to the given office style at the given context node.
1113 A node in which context the style is computed. If neither the given style
1114 nor one of its linked styles does specify a style of the given type,
1115 ancestor nodes of the given context node are considered.
1117 A style:style element node. The style of the requested type is searched
1118 in the given style and its linked styles.
1120 A bit set of styles already defined by the context.
1122 A bit set of styles that must not be taken from the currently inspected
1123 style, because those styles are already defined by the context.
1125 @return A bit set composed of the wiki style constants.
1127 <template name="mk-style-set-internal">
1128 <param name="node"/>
1129 <param name="style"/>
1130 <param name="style-set"/>
1131 <param name="style-mask"/>
1133 <variable name="text-properties" select="$style/style:text-properties"/>
1135 <!-- Decompose style-mask into individual bits. -->
1136 <variable name="bold-requested"
1137 select="($style-mask mod (2 * $BOLD_BIT)) = 0"/>
1138 <variable name="italic-requested"
1139 select="($style-mask mod (2 * $ITALIC_BIT)) - ($style-mask mod ($ITALIC_BIT)) = 0"/>
1140 <variable name="superscript-requested"
1141 select="($style-mask mod (2 * $SUPERSCRIPT_BIT)) - ($style-mask mod ($SUPERSCRIPT_BIT)) = 0"/>
1142 <variable name="subscript-requested"
1143 select="($style-mask mod (2 * $SUBSCRIPT_BIT)) - ($style-mask mod ($SUBSCRIPT_BIT)) = 0"/>
1144 <variable name="typewriter-requested"
1145 select="($style-mask mod (2 * $TYPEWRITER_BIT)) - ($style-mask mod ($TYPEWRITER_BIT)) = 0"/>
1146 <variable name="code-requested"
1147 select="($style-mask mod (2 * $CODE_BIT)) - ($style-mask mod ($CODE_BIT)) = 0"/>
1148 <variable name="center-requested"
1149 select="($style-mask mod (2 * $CENTER_BIT)) - ($style-mask mod ($CENTER_BIT)) = 0"/>
1150 <variable name="right-requested"
1151 select="($style-mask mod (2 * $RIGHT_BIT)) - ($style-mask mod ($RIGHT_BIT)) = 0"/>
1153 <!-- Extract styles that are not already defined by the context. -->
1154 <variable name="bold-style">
1156 <when test="$bold-requested and boolean($text-properties/@fo:font-weight='bold')">
1157 <!-- Bold found in current style. -->
1158 <value-of select="$BOLD_BIT"/>
1161 <value-of select="$NO_STYLE"/>
1165 <variable name="bold-mask">
1167 <when test="$bold-requested and boolean($text-properties/@fo:font-weight)">
1169 Other value than "bold" means that the character style is not
1170 bold and no parent style must be considered.
1172 <value-of select="$BOLD_BIT"/>
1175 <value-of select="$NO_STYLE"/>
1180 <variable name="italic-style">
1182 <when test="$italic-requested and boolean($text-properties/@fo:font-style='italic')">
1183 <!-- Italic found in current style. -->
1184 <value-of select="$ITALIC_BIT"/>
1187 <value-of select="$NO_STYLE"/>
1191 <variable name="italic-mask">
1193 <when test="$italic-requested and boolean($text-properties/@fo:font-style)">
1195 Other value than "italic" means that the character style is not
1196 italic and no parent style must be considered.
1198 <value-of select="$ITALIC_BIT"/>
1201 <value-of select="$NO_STYLE"/>
1206 <variable name="superscript-style">
1208 <when test="$superscript-requested and contains($text-properties/@style:text-position, 'super')">
1209 <value-of select="$SUPERSCRIPT_BIT"/>
1212 <value-of select="$NO_STYLE"/>
1216 <variable name="superscript-mask">
1218 <when test="$superscript-requested and boolean($text-properties/@style:text-position)">
1219 <value-of select="$SUPERSCRIPT_BIT"/>
1222 <value-of select="$NO_STYLE"/>
1227 <variable name="subscript-style">
1229 <when test="$subscript-requested and contains($text-properties/@style:text-position, 'sub')">
1230 <value-of select="$SUBSCRIPT_BIT"/>
1233 <value-of select="$NO_STYLE"/>
1237 <variable name="subscript-mask">
1239 <when test="$subscript-requested and boolean($text-properties/@style:text-position)">
1240 <value-of select="$SUBSCRIPT_BIT"/>
1243 <value-of select="$NO_STYLE"/>
1248 <variable name="typewriter-style">
1250 <when test="$typewriter-requested and ($style/@style:family='text') and boolean($text-properties/@style:font-name)">
1251 <variable name="font-face"
1252 select="key('font-face-ref', $text-properties/@style:font-name)"/>
1254 <when test="$font-face/@style:font-pitch='fixed'">
1255 <value-of select="$TYPEWRITER_BIT"/>
1258 <value-of select="$NO_STYLE"/>
1263 <value-of select="$NO_STYLE"/>
1267 <variable name="typewriter-mask">
1269 <!-- Note: Suppress the typewriter style on text within a code paragraph. -->
1270 <when test="$typewriter-requested and boolean($text-properties/@style:font-name)">
1271 <value-of select="$TYPEWRITER_BIT"/>
1274 <value-of select="$NO_STYLE"/>
1279 <variable name="code-style">
1281 <when test="$code-requested and ($style/@style:family='paragraph') and boolean($text-properties/@style:font-name)">
1282 <variable name="font-face"
1283 select="key('font-face-ref', $text-properties/@style:font-name)"/>
1285 <when test="$font-face/@style:font-pitch='fixed' or (boolean(@style:display-name) and contains($CODE_STYLES, $style/@style:display-name))">
1286 <value-of select="$CODE_BIT"/>
1289 <value-of select="$NO_STYLE"/>
1294 <value-of select="$NO_STYLE"/>
1298 <variable name="code-mask">
1300 <when test="$code-requested and ($style/@style:family='paragraph') and boolean($text-properties/@style:font-name)">
1301 <value-of select="$CODE_BIT"/>
1304 <value-of select="$NO_STYLE"/>
1309 <variable name="center-style">
1311 <when test="$center-requested and ($style/@style:family='paragraph') and boolean($style/style:paragraph-properties/@fo:text-align='center')">
1312 <value-of select="$CENTER_BIT"/>
1315 <value-of select="$NO_STYLE"/>
1319 <variable name="center-mask">
1321 <when test="$center-requested and ($style/@style:family='paragraph') and boolean($style/style:paragraph-properties/@fo:text-align)">
1322 <value-of select="$CENTER_BIT"/>
1325 <value-of select="$NO_STYLE"/>
1330 <variable name="right-style">
1332 <when test="$right-requested and ($style/@style:family='paragraph') and boolean($style/style:paragraph-properties/@fo:text-align='end')">
1333 <value-of select="$RIGHT_BIT"/>
1336 <value-of select="$NO_STYLE"/>
1340 <variable name="right-mask">
1342 <when test="$center-requested and ($style/@style:family='paragraph') and boolean($style/style:paragraph-properties/@fo:text-align)">
1343 <value-of select="$RIGHT_BIT"/>
1346 <value-of select="$NO_STYLE"/>
1352 <!-- Compute the updated styles and mask. -->
1354 Note: The bit masks style-mask, bold-style, italic-style,... are
1355 guaranteed to be disjoint, therefore, addition can be use instead
1356 of bitwise or (which is missing in XPath). -->
1357 <variable name="updated-style"
1358 select="$style-set + $bold-style + $italic-style + $superscript-style + $subscript-style + $code-style + $typewriter-style + $center-style + $right-style"/>
1359 <variable name="updated-mask"
1360 select="$style-mask + $bold-mask + $italic-mask + $superscript-mask + $subscript-mask + $code-mask + $typewriter-mask + $center-mask + $right-mask"/>
1362 <!-- Inspect linked and nested styles. -->
1364 <when test="boolean($style/@style:parent-style-name)">
1365 <!-- Look through the style, the current style is based on. -->
1366 <call-template name="mk-style-set-internal">
1367 <with-param name="node" select="$node"/>
1368 <with-param name="style" select="key('style-ref', $style/@style:parent-style-name)"/>
1369 <with-param name="style-set" select="$updated-style"/>
1370 <with-param name="style-mask" select="$updated-mask"/>
1374 <variable name="ancestors" select="$node/ancestor::*[@text:style-name][1]"/>
1376 <!-- Debugging: Print currently inspected style. -->
1379 <value-of select="'{'"/>
1380 <value-of select="$style/@style:name"/>
1381 <value-of select="','"/>
1382 <value-of select="$updated-style"/>
1383 <value-of select="','"/>
1384 <value-of select="$updated-mask"/>
1385 <value-of select="','"/>
1386 <value-of select="local-name($ancestors)"/>
1387 <value-of select="',('"/>
1388 <value-of select="$node"/>
1389 <value-of select="')'"/>
1390 <value-of select="'}'"/>
1395 If there is an ancestor that has a style, use that style,
1396 otherwise, a style is not found. -->
1398 <when test="boolean($ancestors)">
1399 <!-- Look through the style of the nearest ancestor that has a style. -->
1400 <call-template name="mk-style-set-internal">
1401 <with-param name="node" select="$ancestors"/>
1402 <with-param name="style" select="key('style-ref', $ancestors/@text:style-name)"/>
1403 <with-param name="style-set" select="$updated-style"/>
1404 <with-param name="style-mask" select="$updated-mask"/>
1408 <!-- No more styles to inspect. Return the result. -->
1409 <value-of select="$updated-style"/>
1418 == Descending the tree ==
1421 <template match="/">
1423 <value-of select="$NL"/>
1424 <if test="boolean(//text:note[@text:note-class='footnote'])">
1425 <value-of select="$NL"/>
1427 <value-of select="$NL"/>
1428 <text><references/></text>
1429 <value-of select="$NL"/>
1433 <template match="office:document-content">
1437 <template match="office:body">
1441 <template match="office:* | text:* | draw:frame | draw:text-box | draw:frame | draw:a">
1445 <template match="node()">