| <?xml version="1.0" encoding="UTF-8" ?> |
| <!-- |
| |
| DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER |
| |
| Copyright 2008, 2010 Oracle and/or its affiliates. All rights reserved. |
| |
| Use is subject to license terms. |
| |
| Licensed under the Apache License, Version 2.0 (the "License"); you may not |
| use this file except in compliance with the License. You may obtain a copy |
| of the License at http://www.apache.org/licenses/LICENSE-2.0. You can also |
| obtain a copy of the License at http://odftoolkit.org/docs/license.txt |
| |
| Unless required by applicable law or agreed to in writing, software |
| distributed under the License is distributed on an "AS IS" BASIS, WITHOUT |
| WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| |
| See the License for the specific language governing permissions and |
| limitations under the License. |
| |
| --> |
| |
| <!-- This stylesheet creates a "flat" schema from an ODF schema. --> |
| <!-- In the resulting schema, all defines have been resolved and --> |
| <!-- other simplifications have been made. --> |
| <!-- The rsulting schema IS NOT equivalent to the original ODF --> |
| <!-- schema, and it IS NOT a valid RNG schema. It can be used --> |
| <!-- only for documentation purposes. --> |
| |
| <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" |
| xmlns:rng="http://relaxng.org/ns/structure/1.0" |
| xmlns:a="http://relaxng.org/ns/compatibility/annotations/1.0" |
| xmlns:dc="http://purl.org/dc/elements/1.1/" |
| xmlns="http://relaxng.org/ns/structure/1.0" version="1.0"> |
| <xsl:output method="xml" indent="yes"/> |
| |
| <!-- The paramter 'incl-default-values' specifies whether default --> |
| <!-- value definition should be included into the schema --> |
| <xsl:param name="incl-default-values" select="'true'"/> |
| |
| <!-- The parameter 'incl-types' specifies whether attribute type --> |
| <!-- information shall be included --> |
| <xsl:param name="incl-types" select="'true'"/> |
| |
| <!-- The parameter 'incl-conditions' specifies whether elements --> |
| <!-- like <optional> shall be included as attributes --> |
| <xsl:param name="incl-conditions" select="'true'"/> |
| |
| <!-- The parameter 'incl-content-model' specifies whether the --> |
| <!-- full content of elements shall be included in a normalizes fashion --> |
| <xsl:param name="incl-content-model" select="'false'"/> |
| |
| <!-- The parameter 'incl-elements' specifies whether child elements --> |
| <!-- information shall be included --> |
| <xsl:param name="incl-elements" select="'true'"/> |
| |
| |
| <xsl:variable name="include-default-values" select="$incl-default-values = 'true'"/> |
| <xsl:variable name="include-types" select="$incl-types = 'true'"/> |
| <xsl:variable name="include-condition-attr" select="$incl-conditions = 'true'"/> |
| <xsl:variable name="include-content-model" select="$incl-content-model = 'true'"/> |
| <xsl:variable name="include-elements" select="$incl-elements = 'true'"/> |
| <xsl:variable name="include-ref-comments" select="false()"/> |
| |
| <!-- ********** --> |
| <!-- ** root ** --> |
| <!-- ********** --> |
| <xsl:template match="/rng:grammar"> |
| <rng:grammar |
| xmlns:rng="http://relaxng.org/ns/structure/1.0" |
| xmlns:a="http://relaxng.org/ns/compatibility/annotations/1.0" |
| xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0" |
| xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0" |
| xmlns:config="urn:oasis:names:tc:opendocument:xmlns:config:1.0" |
| xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0" |
| xmlns:table="urn:oasis:names:tc:opendocument:xmlns:table:1.0" |
| xmlns:draw="urn:oasis:names:tc:opendocument:xmlns:drawing:1.0" |
| xmlns:presentation="urn:oasis:names:tc:opendocument:xmlns:presentation:1.0" |
| xmlns:dr3d="urn:oasis:names:tc:opendocument:xmlns:dr3d:1.0" |
| xmlns:chart="urn:oasis:names:tc:opendocument:xmlns:chart:1.0" |
| xmlns:form="urn:oasis:names:tc:opendocument:xmlns:form:1.0" |
| xmlns:script="urn:oasis:names:tc:opendocument:xmlns:script:1.0" |
| xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0" |
| xmlns:number="urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0" |
| xmlns:anim="urn:oasis:names:tc:opendocument:xmlns:animation:1.0" |
| xmlns:dc="http://purl.org/dc/elements/1.1/" |
| xmlns:xlink="http://www.w3.org/1999/xlink" |
| xmlns:math="http://www.w3.org/1998/Math/MathML" |
| xmlns:xforms="http://www.w3.org/2002/xforms" |
| xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" |
| xmlns:svg="urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0" |
| xmlns:smil="urn:oasis:names:tc:opendocument:xmlns:smil-compatible:1.0" |
| xmlns:db="urn:oasis:names:tc:opendocument:xmlns:database:1.0" |
| xmlns:grddl="http://www.w3.org/2003/g/data-view#" |
| xmlns:xhtml="http://www.w3.org/1999/xhtml"> |
| <xsl:for-each select="rng:start|document(rng:include/@href)/rng:grammar/rng:start"> |
| <start> |
| <xsl:apply-templates mode="collect-content"/> |
| </start> |
| </xsl:for-each> |
| <!-- select all <element> nodes in the file or in included files --> |
| <xsl:for-each select="//rng:element|document(//rng:include/@href)//rng:element"> |
| <xsl:choose> |
| <xsl:when test="@name"> |
| <xsl:variable name="name" select="@name"/> |
| <xsl:if test="not(preceding::rng:element[@name=$name])"> |
| <xsl:comment>*** <<xsl:value-of select="@name"/>> ***</xsl:comment> |
| <element name="{@name}"> |
| <!-- collect content --> |
| <xsl:for-each select="//rng:element[@name=$name]|document(//rng:include/@href)//rng:element[@name=$name]"> |
| <xsl:apply-templates mode="collect-content"/> |
| </xsl:for-each> |
| </element> |
| </xsl:if> |
| </xsl:when> |
| <xsl:when test="rng:choice/rng:name"> |
| <xsl:variable name="element" select="."/> |
| <xsl:for-each select="rng:choice/rng:name"> |
| <xsl:comment>*** <<xsl:value-of select="."/>> ***</xsl:comment> |
| <element name="{.}"> |
| <!-- collect content --> |
| <xsl:apply-templates select="$element/*" |
| mode="collect-content"/> |
| </element> |
| </xsl:for-each> |
| </xsl:when> |
| </xsl:choose> |
| </xsl:for-each> |
| |
| <xsl:if test="$include-types"> |
| <xsl:for-each select="/rng:grammar/rng:define|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define"> |
| <xsl:variable name="name" select="@name"/> |
| <xsl:if test="//rng:attribute//rng:ref[@name=$name]|document(/rng:grammar/rng:include/@href)//rng:attribute//rng:ref[@name=$name]"> |
| <xsl:if test="not(preceding-sibling::rng:define[@name = $name])"> |
| <xsl:variable name="count" select="count(/rng:grammar/rng:define[@name = $name]|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name = $name])"/> |
| <define name="{@name}"> |
| <xsl:choose> |
| <xsl:when test="$count>1"> |
| <choice> |
| <xsl:apply-templates select="/rng:grammar/rng:define[@name = $name]/*|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name = $name]/*" mode="collect-type"/> |
| </choice> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:apply-templates mode="collect-type"/> |
| </xsl:otherwise> |
| </xsl:choose> |
| </define> |
| </xsl:if> |
| </xsl:if> |
| </xsl:for-each> |
| </xsl:if> |
| |
| </rng:grammar> |
| </xsl:template> |
| |
| |
| <!-- **************** --> |
| <!-- ** attributes ** --> |
| <!-- **************** --> |
| |
| <!-- match <attribute> elements that have a name attribute --> |
| <xsl:template match="rng:attribute[@name]" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <attribute name="{@name}"> |
| <xsl:if test="$include-default-values"> |
| <xsl:apply-templates select="@a:defaultValue"/> |
| </xsl:if> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| <!-- collect attribute type --> |
| <xsl:if test="$include-types"> |
| <xsl:apply-templates mode="collect-type"/> |
| </xsl:if> |
| </attribute> |
| </xsl:template> |
| |
| <!-- match <attribute> elements that have a <name> descendent --> |
| <xsl:template match="rng:attribute[rng:choice/rng:name]" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:variable name="attribute" select="."/> |
| <xsl:for-each select="rng:choice/rng:name"> |
| <attribute name="{.}"> |
| <!-- collect attribute type --> |
| <xsl:if test="$include-default-values"> |
| <xsl:apply-templates select="$attribute/@a:defaultValue"/> |
| </xsl:if> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| <xsl:if test="$include-types"> |
| <xsl:apply-templates select="$attribute/*" |
| mode="collect-type"/> |
| </xsl:if> |
| </attribute> |
| </xsl:for-each> |
| </xsl:template> |
| |
| <!-- ignore attribute definitions with any name --> |
| <xsl:template match="rng:attribute[rng:anyName]" mode="collect-content"/> |
| |
| <!-- match @a:default-value" --> |
| <xsl:template match="@a:defaultValue"> |
| <xsl:attribute name="a:defaultValue"> |
| <xsl:value-of select="."/> |
| </xsl:attribute> |
| </xsl:template> |
| |
| <!-- ************** --> |
| <!-- ** elements ** --> |
| <!-- ************** --> |
| |
| <!-- match <element> elements that have a name attribute --> |
| <xsl:template match="rng:element[@name]" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:if test="$include-elements"> |
| <element name="{@name}"> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| </element> |
| </xsl:if> |
| </xsl:template> |
| |
| <!-- match <element> elements that have a <name> descendent --> |
| <xsl:template match="rng:element[rng:choice/rng:name]" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:if test="$include-elements"> |
| <xsl:for-each select="rng:choice/rng:name"> |
| <element name="{.}"> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| </element> |
| </xsl:for-each> |
| </xsl:if> |
| </xsl:template> |
| |
| <!-- ignore attribute definitions with any name --> |
| <xsl:template match="rng:element[rng:anyName]" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <element> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| <anyName/> |
| </element> |
| </xsl:template> |
| |
| <!-- ignore name elements (they are covered by the fore-each loop already) --> |
| <xsl:template match="rng:name" mode="collect-content"/> |
| |
| <!-- ignore data elements (they may only occure in elements here) --> |
| <xsl:template match="rng:data" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <data type="{@type}"> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| </data> |
| </xsl:template> |
| |
| <xsl:template match="rng:text" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <text> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| </text> |
| </xsl:template> |
| |
| <xsl:template match="rng:empty" mode="collect-content"> |
| <xsl:if test="$include-content-model"> |
| <empty/> |
| </xsl:if> |
| </xsl:template> |
| |
| <!-- ************* --> |
| <!-- ** control ** --> |
| <!-- ************* --> |
| |
| <!--match <ref> elements --> |
| <xsl:template match="rng:ref" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:if test="$include-ref-comments"> |
| <xsl:comment><xsl:value-of select="@name"/></xsl:comment> |
| </xsl:if> |
| <!-- match <define> with same name in the current file and within |
| included files. --> |
| <xsl:variable name="name" select="@name"/> |
| <xsl:choose> |
| <xsl:when test="$include-content-model"> |
| <xsl:variable name="combine" select="/rng:grammar/rng:define[@name=$name]/@combine|/rng:grammar/rng:include/rng:define[@name=$name]/@combine|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name=$name]/@combine"></xsl:variable> |
| <xsl:choose> |
| <xsl:when test="$combine"> |
| <xsl:element name="{$combine}"> |
| <xsl:apply-templates |
| select="/rng:grammar/rng:define[@name=$name]|/rng:grammar/rng:include/rng:define[@name=$name]|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name=$name]" |
| mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$condition-attr"/> |
| </xsl:apply-templates> |
| </xsl:element> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:apply-templates |
| select="/rng:grammar/rng:define[@name=$name]|/rng:grammar/rng:include/rng:define[@name=$name]|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name=$name]" |
| mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$condition-attr"/> |
| </xsl:apply-templates> |
| </xsl:otherwise> |
| </xsl:choose> |
| </xsl:when> |
| <xsl:when test="@name='boolean'"> |
| <!-- Booleans are no XSD datatype, but should not be expanded --> |
| <ref name="boolean"> |
| <xsl:if test="$condition-attr"> |
| <xsl:attribute name="condition"> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:attribute> |
| </xsl:if> |
| </ref> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:apply-templates |
| select="/rng:grammar/rng:define[@name=$name]|/rng:grammar/rng:include/rng:define[@name=$name]|document(/rng:grammar/rng:include/@href)/rng:grammar/rng:define[@name=$name]" |
| mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$condition-attr"/> |
| </xsl:apply-templates> |
| </xsl:otherwise> |
| </xsl:choose> |
| <xsl:if test="$include-ref-comments"> |
| <xsl:comment>/<xsl:value-of select="@name"/></xsl:comment> |
| </xsl:if> |
| </xsl:template> |
| |
| <xsl:template match="rng:define" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:variable name="new-condition"> |
| <xsl:choose> |
| <xsl:when test="$include-condition-attr and @combine and string-length($condition-attr) > 0"> |
| <xsl:value-of select="concat($condition-attr, '/', @combine)"/> |
| </xsl:when> |
| <xsl:when test="$include-condition-attr and @combine"> |
| <xsl:value-of select="@combine"/> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:otherwise> |
| </xsl:choose> |
| </xsl:variable> |
| <xsl:apply-templates select="*" mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$new-condition"/> |
| </xsl:apply-templates> |
| </xsl:template> |
| |
| <!-- match conditions and lists --> |
| <xsl:template match="rng:interleave|rng:mixed|rng:optional|rng:choice|rng:group|rng:zeroOrMore|rng:oneOrMore" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:variable name="new-condition"> |
| <xsl:choose> |
| <xsl:when test="$include-condition-attr and string-length($condition-attr) > 0"> |
| <xsl:value-of select="concat($condition-attr, '/', name(.))"/> |
| </xsl:when> |
| <xsl:when test="$include-condition-attr"> |
| <xsl:value-of select="name(.)"/> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:value-of select="$condition-attr"/> |
| </xsl:otherwise> |
| </xsl:choose> |
| </xsl:variable> |
| <xsl:choose> |
| <xsl:when test="$include-content-model"> |
| <xsl:copy> |
| <xsl:apply-templates mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$new-condition"/> |
| </xsl:apply-templates> |
| </xsl:copy> |
| </xsl:when> |
| <xsl:otherwise> |
| <xsl:apply-templates mode="collect-content"> |
| <xsl:with-param name="condition-attr" select="$new-condition"/> |
| </xsl:apply-templates> |
| </xsl:otherwise> |
| </xsl:choose> |
| </xsl:template> |
| |
| <!-- Turn dc:description into a comment --> |
| <xsl:template match="dc:description" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:comment><xsl:value-of select="."/></xsl:comment> |
| </xsl:template> |
| |
| <!-- match all other elements and ignore them --> |
| <xsl:template match="*" mode="collect-content"> |
| <xsl:param name="condition-attr"/> |
| <xsl:message>Ignored element <<xsl:value-of select="name(.)"/>>, content: <xsl:value-of select="."/>, parent: <xsl:value-of select="name(..)"/>, grandparent: <xsl:value-of select="name(../..)"/>, define name: <xsl:value-of select="ancestor::rng:define[1]/@name"/>, condition: <xsl:value-of select="$condition-attr"/></xsl:message> |
| </xsl:template> |
| |
| <xsl:template match="text()" mode="collect-content"> |
| <xsl:if test="string-length(normalize-space(.))>0"> |
| <xsl:message>Ignored <xsl:value-of select="."/></xsl:message> |
| </xsl:if> |
| </xsl:template> |
| |
| <!-- ********************* --> |
| <!-- ** attribute types ** --> |
| <!-- ********************* --> |
| |
| <!-- match <ref> elements --> |
| <xsl:template match="rng:ref" mode="collect-type"> |
| <!-- references are assumed to be type names --> |
| <ref name="{@name}"/> |
| </xsl:template> |
| |
| <!-- match <data> elements --> |
| <xsl:template match="rng:data" mode="collect-type"> |
| <!-- data types are data types --> |
| <data type="{@type}"> |
| <xsl:apply-templates mode="collect-type"/> |
| </data> |
| </xsl:template> |
| |
| <!-- ignore name choices --> |
| |
| <xsl:template match="rng:choice[rng:name]" mode="collect-type"/> |
| |
| <!-- match elements that get copied --> |
| <xsl:template match="rng:choice|rng:list|rng:group|rng:oneOrMore|rng:zeroOrMore|rng:empty|rng:text|rng:optional" mode="collect-type"> |
| <xsl:copy><xsl:apply-templates mode="collect-type"/></xsl:copy> |
| </xsl:template> |
| |
| <!-- match <value> elements --> |
| <xsl:template match="rng:param" mode="collect-type"> |
| <param name="{@name}"><xsl:value-of select="."/></param> |
| </xsl:template> |
| |
| <!-- match <value> elements --> |
| <xsl:template match="rng:value" mode="collect-type"> |
| <value><xsl:value-of select="."/></value> |
| </xsl:template> |
| |
| <!-- Turn dc:description into a comment --> |
| <xsl:template match="dc:description" mode="collect-type"> |
| <xsl:param name="condition-attr"/> |
| <xsl:comment><xsl:value-of select="."/></xsl:comment> |
| </xsl:template> |
| |
| <!-- match everything else and ignore it --> |
| <xsl:template match="*" mode="collect-type"> |
| <xsl:message>Ignored element <<xsl:value-of select="name(.)"/>> while collecting type information, content: <xsl:value-of select="."/>, parent: <xsl:value-of select="name(..)"/>, grandparent: <xsl:value-of select="name(../..)"/>, define name: <xsl:value-of select="ancestor::rng:define[1]/@name"/></xsl:message> |
| </xsl:template> |
| |
| <xsl:template match="text()" mode="collect-type"/> |
| |
| </xsl:stylesheet> |