1<?xml version="1.0" encoding="UTF-8"?>
2<!--***********************************************************
3 *
4 * Licensed to the Apache Software Foundation (ASF) under one
5 * or more contributor license agreements.  See the NOTICE file
6 * distributed with this work for additional information
7 * regarding copyright ownership.  The ASF licenses this file
8 * to you under the Apache License, Version 2.0 (the
9 * "License"); you may not use this file except in compliance
10 * with the License.  You may obtain a copy of the License at
11 *
12 *   http://www.apache.org/licenses/LICENSE-2.0
13 *
14 * Unless required by applicable law or agreed to in writing,
15 * software distributed under the License is distributed on an
16 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17 * KIND, either express or implied.  See the License for the
18 * specific language governing permissions and limitations
19 * under the License.
20 *
21 ***********************************************************-->
22
23
24<!--
25	For further documentation and updates visit http://xml.openoffice.org/odf2xhtml
26-->
27<xsl:stylesheet version="1.0"
28	xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
29	xmlns:chart="urn:oasis:names:tc:opendocument:xmlns:chart:1.0"
30	xmlns:config="urn:oasis:names:tc:opendocument:xmlns:config:1.0"
31	xmlns:dc="http://purl.org/dc/elements/1.1/"
32	xmlns:dom="http://www.w3.org/2001/xml-events"
33	xmlns:dr3d="urn:oasis:names:tc:opendocument:xmlns:dr3d:1.0"
34	xmlns:draw="urn:oasis:names:tc:opendocument:xmlns:drawing:1.0"
35	xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0"
36	xmlns:form="urn:oasis:names:tc:opendocument:xmlns:form:1.0"
37	xmlns:math="http://www.w3.org/1998/Math/MathML"
38	xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0"
39	xmlns:number="urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0"
40	xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0"
41	xmlns:ooo="http://openoffice.org/2004/office"
42	xmlns:oooc="http://openoffice.org/2004/calc"
43	xmlns:ooow="http://openoffice.org/2004/writer"
44	xmlns:script="urn:oasis:names:tc:opendocument:xmlns:script:1.0"
45	xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0"
46	xmlns:svg="urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0"
47	xmlns:table="urn:oasis:names:tc:opendocument:xmlns:table:1.0"
48	xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0"
49	xmlns:xforms="http://www.w3.org/2002/xforms"
50	xmlns:xlink="http://www.w3.org/1999/xlink"
51	xmlns:xsd="http://www.w3.org/2001/XMLSchema"
52	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
53	exclude-result-prefixes="chart config dc dom dr3d draw fo form math meta number office ooo oooc ooow script style svg table text xforms xlink xsd xsi xforms xsd xsi"
54	xmlns="http://www.w3.org/1999/xhtml">
55
56
57	<!-- ************** -->
58	<!-- *** header *** -->
59	<!-- ************** -->
60
61	<xsl:template name="create-header">
62		<xsl:param name="globalData" />
63
64		<xsl:element name="head">
65		<xsl:attribute name="profile">http://dublincore.org/documents/dcmi-terms/</xsl:attribute>
66			<xsl:if test="$debugEnabled"><xsl:message>CSS helper variable will be created....</xsl:message></xsl:if>
67			<xsl:call-template name='xhtml-header-properties'>
68				<xsl:with-param name="globalData" select="$globalData" />
69			</xsl:call-template>
70
71			<xsl:if test="$debugEnabled"><xsl:message>CSS variable ready, header will be created....</xsl:message></xsl:if>
72			<!-- constructing the css header simulating inheritance of style-families by style order -->
73			<xsl:call-template name='create-css-styleheader'>
74				<xsl:with-param name="globalData" select="$globalData" />
75			</xsl:call-template>
76			<xsl:if test="$debugEnabled"><xsl:message>CSS header creation finished!</xsl:message></xsl:if>
77		</xsl:element>
78
79	</xsl:template>
80
81
82	<!-- Creating a CSS style header from the collected styles of the 'globalData' parameter -->
83	<xsl:template name='create-css-styleheader'>
84		<xsl:param name="globalData" />
85
86		<xsl:element name="style">
87			<xsl:attribute name="type">text/css</xsl:attribute>
88<xsl:text>
89	</xsl:text>
90	<xsl:call-template name='create-page-layout'>
91		<xsl:with-param name="globalData" select="$globalData" />
92	</xsl:call-template>
93<xsl:text>table { border-collapse:collapse; border-spacing:0; empty-cells:show }
94	</xsl:text>
95	<xsl:choose>
96		<xsl:when test="/*/office:body/office:spreadsheet"><xsl:text>td, th { vertical-align:top; font-size:10pt;}
97	</xsl:text></xsl:when>
98		<xsl:otherwise><xsl:text>td, th { vertical-align:top; font-size:12pt;}
99	</xsl:text></xsl:otherwise>
100	</xsl:choose>
101<xsl:text>h1, h2, h3, h4, h5, h6 { clear:both }
102	</xsl:text>
103<xsl:text>ol, ul { margin:0; padding:0;}
104	</xsl:text>
105<xsl:text>li { list-style: none; margin:0; padding:0;}
106	</xsl:text>
107<xsl:comment> "li span.odfLiEnd" - IE 7 issue</xsl:comment>
108<xsl:text>
109	</xsl:text>
110<xsl:text>li span. { clear: both; line-height:0; width:0; height:0; margin:0; padding:0; }
111	</xsl:text>
112<xsl:text>span.footnodeNumber { padding-right:1em; }
113	</xsl:text>
114<xsl:text>span.annotation_style_by_filter { font-size:95%; font-family:Arial; background-color:#fff000;  margin:0; border:0; padding:0;  }
115	</xsl:text>
116<xsl:text>* { margin:0;}
117	</xsl:text>
118			<xsl:call-template name="write-mapped-CSS-styles">
119				<xsl:with-param name="globalData" select="$globalData" />
120			</xsl:call-template>
121		</xsl:element>
122	</xsl:template>
123
124	<xsl:template name="write-mapped-CSS-styles">
125		<xsl:param name="globalData" />
126		<xsl:param name="styleNo" select="1"/>
127		<xsl:param name="emptyStyles"/>
128
129		<xsl:choose>
130			<xsl:when test="$globalData/all-styles/style[$styleNo]">
131			<!-- If there is still a style to be written -->
132				<!-- setting the context -->
133				<xsl:for-each select="$globalData/all-styles/style[$styleNo]">
134				<xsl:choose>
135					<xsl:when test="final-properties != ''">
136					<!-- NOTE: easy process, as only the style family in conjunction with the style name, makes the style unambigous -->
137				<xsl:text>.</xsl:text><!--<xsl:value-of select="@style:family" /><xsl:text>:</xsl:text>--><xsl:value-of select="translate(@style:name, '.,;: %()[]/\+', '_____________')"/><xsl:text> { </xsl:text> <xsl:value-of select="final-properties" /><xsl:text>}
138	</xsl:text>
139						<xsl:call-template name="write-mapped-CSS-styles">
140							<xsl:with-param name="globalData" select="$globalData" />
141							<xsl:with-param name="emptyStyles" select="$emptyStyles"/>
142							<xsl:with-param name="styleNo" select="$styleNo + 1"/>
143						</xsl:call-template>
144					</xsl:when>
145					<xsl:otherwise>
146						<xsl:call-template name="write-mapped-CSS-styles">
147							<xsl:with-param name="globalData" select="$globalData" />
148							<xsl:with-param name="emptyStyles" select="concat($emptyStyles, '.', @style:name, ' ')"/>
149							<xsl:with-param name="styleNo" select="$styleNo + 1"/>
150						</xsl:call-template>
151					</xsl:otherwise>
152				</xsl:choose>
153				</xsl:for-each>
154			</xsl:when>
155			<xsl:otherwise>
156			<!-- Otherwise all styles have been processed and the empty styles have to be given out -->
157				<xsl:comment> ODF styles with no properties representable as CSS </xsl:comment><xsl:text>
158	</xsl:text><xsl:value-of select="$emptyStyles"/><xsl:text>{ }
159	</xsl:text>
160			</xsl:otherwise>
161		</xsl:choose>
162	</xsl:template>
163
164
165	<!-- Creating CSS page layout based on first office master style -->
166	<xsl:template name='create-page-layout'>
167		<xsl:param name="globalData" />
168
169		<!-- approximation to find the correct master page style (with page dimensions) -->
170		<xsl:variable name="masterPageNames">
171            <!-- set context to styles.xml -->
172            <xsl:for-each select="$globalData/all-doc-styles/style">
173                <!-- Loop over every style:style containing a @style:master-page-name attribute -->
174                <xsl:for-each select="key('masterPage','count')">
175                        <!-- set context to styles.xml -->
176                        <xsl:for-each select="/*/office:body">
177                            <!-- Check if this style is being used in the body -->
178                            <xsl:if test="key('elementUsingStyle', ../@style:name)">
179                                <!-- Check every master-page-name if it is not emtpy and return as ';' separated list  -->
180                                <xsl:if test="string-length(../@style:master-page-name) &gt; 0"><xsl:value-of select="../@style:master-page-name"/>;</xsl:if>
181                            </xsl:if>
182                        </xsl:for-each>
183                </xsl:for-each>
184            </xsl:for-each>
185		</xsl:variable>
186		<!-- Take the first of the masterpage list and get the according style:master-page element and find the @style:page-layout-name  -->
187		<xsl:variable name="pageLayoutName" select="key('masterPageElements', substring-before($masterPageNames,';'))/@style:page-layout-name"/>
188		 <!-- Find the according style:page-layout and store the properties in a variable  -->
189		<xsl:variable name="pageProperties" select="key('pageLayoutElements', $pageLayoutName)/style:page-layout-properties"/>
190
191<xsl:text>@page { </xsl:text>
192
193		<xsl:call-template name="page-size">
194			<xsl:with-param name="globalData"       select="$globalData" />
195			<xsl:with-param name="pageProperties"   select="$pageProperties" />
196		</xsl:call-template>
197		<xsl:call-template name="page-margin">
198			<xsl:with-param name="globalData"       select="$globalData" />
199			<xsl:with-param name="pageProperties"   select="$pageProperties" />
200		</xsl:call-template>
201
202<xsl:text> }
203	</xsl:text>
204
205	</xsl:template>
206
207
208	<xsl:template name="page-size">
209		<xsl:param name="globalData" />
210		<xsl:param name="pageProperties" />
211
212		<xsl:variable name="printOrientation"  select="$pageProperties/@style:print-orientation" />
213		<xsl:variable name="pageWidth"         select="$pageProperties/@fo:page-width" />
214		<xsl:variable name="pageHeight"        select="$pageProperties/@fo:page-height" />
215		<xsl:choose>
216			<xsl:when test="$pageWidth and $pageHeight">
217				<xsl:text>size: </xsl:text>
218				<xsl:value-of select="$pageWidth" />
219				<xsl:text> </xsl:text>
220				<xsl:value-of select="$pageHeight" />
221				<xsl:text>; </xsl:text>
222			</xsl:when>
223			<xsl:when test="$printOrientation">
224				<xsl:text>size: </xsl:text>
225				<xsl:value-of select="$printOrientation" />
226				<xsl:text>; </xsl:text>
227			</xsl:when>
228		</xsl:choose>
229	</xsl:template>
230
231
232
233	<xsl:template name="page-margin">
234		<xsl:param name="globalData" />
235		<xsl:param name="pageProperties" />
236
237		<xsl:variable name="marginTop"  select="$pageProperties/@fo:margin-top" />
238		<xsl:if test="$marginTop">
239			<xsl:text>margin-top: </xsl:text>
240			<xsl:value-of select="$marginTop" />
241			<xsl:text>; </xsl:text>
242		</xsl:if>
243		<xsl:variable name="marginBottom"  select="$pageProperties/@fo:margin-bottom" />
244		<xsl:if test="$marginBottom">
245			<xsl:text>margin-bottom: </xsl:text>
246			<xsl:value-of select="$marginBottom" />
247			<xsl:text>; </xsl:text>
248		</xsl:if>
249		<xsl:variable name="marginLeft"  select="$pageProperties/@fo:margin-left" />
250		<xsl:if test="$marginLeft">
251			<xsl:text>margin-left: </xsl:text>
252			<xsl:value-of select="$marginLeft" />
253			<xsl:text>; </xsl:text>
254		</xsl:if>
255		<xsl:variable name="marginRight"  select="$pageProperties/@fo:margin-right" />
256		<xsl:if test="$marginRight">
257			<xsl:text>margin-right: </xsl:text>
258			<xsl:value-of select="$marginRight" />
259		</xsl:if>
260	</xsl:template>
261
262
263	<!-- *************************** -->
264	<!-- *** Common XHTML header *** -->
265	<!-- *************************** -->
266
267	<xsl:template name='xhtml-header-properties'>
268		<xsl:param name="globalData" />
269
270		<xsl:variable name="netloc">
271		<xsl:for-each select="$globalData/meta-file/*/office:meta/meta:user-defined">
272		<xsl:if test="./@meta:name='ODF.base'">
273		<xsl:value-of select="." />
274		</xsl:if>
275		</xsl:for-each>
276		<xsl:for-each select="$globalData/meta-file/*/office:meta/meta:user-defined">
277		<xsl:if test="./@meta:name='ODF.filename'">
278		<xsl:value-of select="." />
279		</xsl:if>
280		</xsl:for-each>
281		</xsl:variable>
282
283		<xsl:variable name="lang">
284			 <xsl:choose>
285				 <xsl:when test="$globalData/meta-file/*/office:meta/dc:language">
286					 <xsl:value-of select="$globalData/meta-file/*/office:meta/dc:language" />
287				 </xsl:when>
288				 <xsl:otherwise>en-US</xsl:otherwise>
289			 </xsl:choose>
290		</xsl:variable>
291
292		<xsl:variable name="prov">
293			 <xsl:choose>
294				 <xsl:when test="$globalData/meta-file/*/office:meta/meta:printed-by">
295					 <xsl:value-of select="concat('Printed by &quot;',$globalData/meta-file/*/office:meta/meta:printed-by,'&quot;[dc:publisher] on &quot;',$globalData/meta-file/*/office:meta/meta:print-date,'&quot;[dc:date] in &quot;',$lang,'&quot;[dc:language]')" />
296				 </xsl:when>
297				 <xsl:otherwise />
298			 </xsl:choose>
299		</xsl:variable>
300
301		<xsl:variable name="keywords">
302			<xsl:for-each select="$globalData/meta-file/*/office:meta/meta:keyword">
303				<xsl:value-of select="." />
304					<xsl:if test="position() != last()">
305						<xsl:text>, </xsl:text>
306					</xsl:if>
307			</xsl:for-each>
308		</xsl:variable>
309
310		<!-- explicit output content-type for low-tech browser (e.g. IE6) -->
311		<xsl:element name="meta">
312			<xsl:attribute name="http-equiv">Content-Type</xsl:attribute>
313			<xsl:attribute name="content">application/xhtml+xml; charset=utf-8</xsl:attribute>
314		</xsl:element>
315
316		<!-- title of document for browser frame title -->
317		<xsl:element name="title">
318		<xsl:attribute name="lang" namespace="http://www.w3.org/XML/1998/namespace">
319			<xsl:value-of select="$lang" />
320		</xsl:attribute>
321
322			<xsl:choose>
323				<xsl:when test="$globalData/meta-file/*/office:meta/dc:title">
324					<xsl:value-of select="$globalData/meta-file/*/office:meta/dc:title" />
325				</xsl:when>
326				<!-- providing the mandatory title is a workaround for an IE bug-->
327				<xsl:otherwise>
328					<xsl:text>- no title specified</xsl:text>
329				</xsl:otherwise>
330			</xsl:choose>
331		</xsl:element>
332
333		<!-- title, in DC syntax -->
334		<xsl:element name="meta">
335			<xsl:attribute name="name">DCTERMS.title</xsl:attribute>
336			<xsl:attribute name="content">
337			   <xsl:value-of select="$globalData/meta-file/*/office:meta/dc:title" />
338			</xsl:attribute>
339			<xsl:attribute name="lang" namespace="http://www.w3.org/XML/1998/namespace">
340			   <xsl:value-of select="$lang" />
341			</xsl:attribute>
342		</xsl:element>
343
344		<!-- the identifier for source  (identifier) -->
345		<xsl:call-template name="add-meta-tag">
346			<xsl:with-param name="meta-name" select="'DCTERMS.identifier'" />
347			<xsl:with-param name="meta-data" select="translate($netloc, ' ','')" />
348			<xsl:with-param name="meta-enc" select="'DCTERMS.URI'" />
349		</xsl:call-template>
350
351		<!-- the language for source  (language) -->
352		<xsl:call-template name="add-meta-tag">
353			<xsl:with-param name="meta-name" select="'DCTERMS.language'" />
354			<xsl:with-param name="meta-data" select="$lang" />
355			<xsl:with-param name="meta-enc" select="'DCTERMS.RFC4646'" />
356		</xsl:call-template>
357
358		<!-- a bit commercial (generator) -->
359		<xsl:element name="meta">
360			<xsl:attribute name="name">DCTERMS.source</xsl:attribute>
361			<xsl:attribute name="content">http://xml.openoffice.org/odf2xhtml</xsl:attribute>
362		</xsl:element>
363
364		<!-- the author of the input source (author) -->
365		<xsl:call-template name="add-meta-tag">
366			<xsl:with-param name="meta-name" select="'DCTERMS.creator'" />
367			<xsl:with-param name="meta-data" select="$globalData/meta-file/*/office:meta/meta:initial-creator" />
368		</xsl:call-template>
369
370		<!-- creation-date of the input source (issued) -->
371		<xsl:call-template name="add-meta-tag">
372			<xsl:with-param name="meta-name" select="'DCTERMS.issued'" />
373			<xsl:with-param name="meta-data" select="$globalData/meta-file/*/office:meta/meta:creation-date" />
374			<xsl:with-param name="meta-enc" select="'DCTERMS.W3CDTF'" />
375		</xsl:call-template>
376
377		<!-- name of last changing person of the input source (changedby) -->
378		<xsl:call-template name="add-meta-tag">
379			<xsl:with-param name="meta-name" select="'DCTERMS.contributor'" />
380			<xsl:with-param name="meta-data" select="$globalData/meta-file/*/office:meta/dc:creator" />
381		</xsl:call-template>
382
383		<!-- last changing date of the input source (changed) -->
384		<xsl:call-template name="add-meta-tag">
385			<xsl:with-param name="meta-name" select="'DCTERMS.modified'" />
386			<xsl:with-param name="meta-data" select="$globalData/meta-file/*/office:meta/dc:date" />
387			<xsl:with-param name="meta-enc" select="'DCTERMS.W3CDTF'" />
388		</xsl:call-template>
389
390		<!-- Last print, as provenance -->
391		<xsl:if test="$prov">
392		<xsl:call-template name="add-meta-tag">
393			<xsl:with-param name="meta-name" select="'DCTERMS.provenance'" />
394			<xsl:with-param name="meta-data" select="$prov" />
395			<xsl:with-param name="meta-lang" select="$lang" />
396		</xsl:call-template>
397		</xsl:if>
398
399		<!-- keywords about the input source (keywords) -->
400		<xsl:call-template name="add-meta-tag">
401			<xsl:with-param name="meta-name" select="'DCTERMS.subject'" />
402			<xsl:with-param name="meta-data" select="normalize-space(concat($globalData/meta-file/*/office:meta/dc:subject,',   ',$keywords))" />
403			<xsl:with-param name="meta-lang" select="$lang" />
404		</xsl:call-template>
405
406		<!-- detailed description about the input source (description) -->
407		<xsl:call-template name="add-meta-tag">
408			<xsl:with-param name="meta-name" select="'DCTERMS.description'" />
409			<xsl:with-param name="meta-data" select="$globalData/meta-file/*/office:meta/dc:description" />
410			<xsl:with-param name="meta-lang" select="$lang" />
411		</xsl:call-template>
412
413
414		<!-- user defined use of DCTERM tags -->
415		<xsl:for-each select="$globalData/meta-file/*/office:meta/meta:user-defined[starts-with(@meta:name,'DCTERMS.')][not(.='')]">
416		<xsl:call-template name="add-meta-tag">
417			<xsl:with-param name="meta-name" select="@meta:name" />
418			<xsl:with-param name="meta-data" select="." />
419			<!-- <xsl:with-param name="meta-lang" select="$lang" /> -->
420		</xsl:call-template>
421		</xsl:for-each>
422		<!-- user defined use of DC tags (legacy) -->
423		<xsl:for-each select="$globalData/meta-file/*/office:meta/meta:user-defined[starts-with(@meta:name,'DC.')][not(.='')]">
424		<xsl:call-template name="add-meta-tag">
425			<xsl:with-param name="meta-name" select="@meta:name" />
426			<xsl:with-param name="meta-data" select="." />
427			<!-- <xsl:with-param name="meta-lang" select="$lang" /> -->
428		</xsl:call-template>
429		</xsl:for-each>
430
431		<link rel="schema.DC" href="http://purl.org/dc/elements/1.1/" hreflang="en" />
432		<link rel="schema.DCTERMS" href="http://purl.org/dc/terms/" hreflang="en" />
433		<link rel="schema.DCTYPE" href="http://purl.org/dc/dcmitype/" hreflang="en" />
434		<link rel="schema.DCAM" href="http://purl.org/dc/dcam/" hreflang="en" />
435		<!-- W3C GRDDL Profile -->
436		<!--
437		<link rel="transformation" href="http://xml.openoffice.org/odf2xhtml/rdf-extract.xsl" />
438		-->
439
440		<!-- base URL of document for resolving relative links
441		NOTE: CHROME has a problem, with relative references as from content table, referencing to root directory instead of document
442		<xsl:element name="base">
443			<xsl:attribute name="href">-->
444				<!-- earlier 'targetURL' was used for an absoulte reference of base provided by the Office (file URL)
445					<xsl:value-of select="$targetURL" />
446					now '.' let relative links work, even if document has been moved -->
447				<!--<xsl:text>.</xsl:text>
448			</xsl:attribute>
449		</xsl:element>-->
450	</xsl:template>
451
452	<!-- generic template for adding common meta tags -->
453	<xsl:template name="add-meta-tag">
454		<xsl:param name="meta-name" />
455		<xsl:param name="meta-data" />
456		<xsl:param name="meta-enc" />
457		<xsl:param name="meta-lang" />
458
459		<xsl:if test="$meta-data">
460			<xsl:element name="meta">
461				<xsl:attribute name="name">
462					<xsl:value-of select="$meta-name" />
463				</xsl:attribute>
464				<xsl:attribute name="content">
465					<xsl:value-of select="$meta-data" />
466				</xsl:attribute>
467				<xsl:if test="$meta-enc">
468				<xsl:attribute name="scheme">
469					<xsl:value-of select="$meta-enc" />
470				</xsl:attribute>
471				</xsl:if>
472				<xsl:if test="$meta-lang">
473				<xsl:attribute name="lang" namespace="http://www.w3.org/XML/1998/namespace">
474					<xsl:value-of select="$meta-lang" />
475				</xsl:attribute>
476				</xsl:if>
477			</xsl:element>
478		</xsl:if>
479	</xsl:template>
480
481</xsl:stylesheet>
482