<!--

# =============================================================================

# Copyright © 2016 Typéfi Systems. All rights reserved.

#

# Unless required by applicable law or agreed to in writing, software

# is distributed on an "as is" basis, without warranties or conditions of any

# kind, either express or implied.

# =============================================================================

-->

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:tps="http://www.typefi.com/ContentXML" xmlns:xd="http://www.pnp-software.com/XSLTdoc" version="2.0" exclude-result-prefixes="#all">





    
    <xd:doc type="stylesheet">

        
<xd:short>

            Splits paragraphs that contain nested block elements

            (such as 
<xd:xml><table /></xd:xml><xd:xml><boxed-text /></xd:xml>, lists)

            into 2 or more paragraphs during the preprocessing stage.

        
</xd:short>

        
<xd:detail>

            For example, the fragment

            
<xd:xml>

                
<p>

                    text1

                    
<table>...</table>

                    text2

                
</p>

            
</xd:xml>

            is preprocessed into

            
<xd:xml>

                
<p>text1</p>

                
<table>...</table>

                
<p>text2</p>

            
</xd:xml>

        
</xd:detail>

        
<xd:cvsId>   $Revision$</xd:cvsId>

    
</xd:doc>






    
<xsl:template name="apply-break-up">

        
<xsl:processing-instruction name="breakup-context" select="name()" />



        
<xsl:for-each-group select="node() except tps:breaking-whitespace-adjacents(node())" group-adjacent="tps:is-breaking(.)">

            
<xsl:variable name="group-position" select="position()" />



            
<xsl:choose>

                
<xsl:when test="current-grouping-key()">

                    
<xsl:for-each select="current-group()">

                        
<xsl:call-template name="breakup-pi">

                            
<xsl:with-param name="position" select="$group-position" />

                        
</xsl:call-template>



                        
<xsl:apply-templates select="." mode="pre-processing" />

                    
</xsl:for-each>

                
</xsl:when>



                
<xsl:otherwise>

                    
<xsl:call-template name="breakup-pi">

                        
<xsl:with-param name="position" select="$group-position" />

                    
</xsl:call-template>



                    
<xsl:element name="{parent::element()/name()}">

                        
<xsl:apply-templates select="../attribute()" mode="pre-processing" />

                        
<xsl:apply-templates select="current-group()" mode="pre-processing" />

                    
</xsl:element>

                
</xsl:otherwise>

            
</xsl:choose>

        
</xsl:for-each-group>

    
</xsl:template>





    
<xsl:function name="tps:breaking-whitespace-adjacents" as="node()*">

        
<xsl:param name="nodes" as="node()*" />



        
<xsl:sequence select="$nodes[not(normalize-space())] [following-sibling::node()[1][self::element()][tps:is-breaking(.)] or preceding-sibling::node()[1][self::element()][tps:is-breaking(.)]]" />

    
</xsl:function>





    
<xsl:template name="breakup-pi">

        
<xsl:param name="position" as="xs:integer" />



        
<xsl:processing-instruction name="breakup-group" select="$position" />

    
</xsl:template>





    
<xsl:function name="tps:get-breakup-position" as="xs:integer?">

        
<xsl:param name="context" as="node()" />



        
<xsl:variable name="pi" as="xs:string?" select="$context/preceding-sibling::node()[1]/self::processing-instruction('breakup-group')" />



        
<xsl:sequence select="if ($pi) then $pi cast as xs:integer else ()" />

    
</xsl:function>





    
<!-- If all child nodes are breaking the parent then parent element is not recreated so we return only its name -->

    
<xsl:function name="tps:get-broken-element-name" as="xs:string?">

        
<xsl:param name="breakup-element" as="element()" />



        
<xsl:sequence select="$breakup-element/preceding-sibling::processing-instruction('breakup-context')[1]" />

    
</xsl:function>





    
<xsl:function name="tps:get-breakup-ancestors" as="element()*">

        
<xsl:param name="context" as="node()" />



        
<xsl:sequence select="$context/ancestor::*[tps:get-breakup-position(.)]" />

    
</xsl:function>





    
<!-- Test if current preprocessed element is the first part of the broken element or its parent wasn't broken at all -->

    
<xsl:function name="tps:is-initial-breakup-element" as="xs:boolean">

        
<xsl:param name="element" as="element()" />



        
<xsl:sequence select="string(tps:get-breakup-position($element)) = ('', '1')" />

    
</xsl:function>





    
<xsl:function name="tps:is-broken" as="xs:boolean">

        
<xsl:param name="element" as="element()" />



        
<xsl:sequence select="exists($element/node()[tps:is-breaking(.)])" />

    
</xsl:function>





    
<!--

        @Description:   A function to determine whether a current node breaks it's parent.

                        Assume only elements can break their parents.

        
-->

    
<xsl:function name="tps:is-breaking" as="xs:boolean">

        
<xsl:param name="node" as="node()" />



        
<xsl:variable name="result" as="xs:boolean">

            
<xsl:apply-templates select="$node" mode="break-parent" />

        
</xsl:variable>



        
<xsl:sequence select="$result" />

    
</xsl:function>





    
<xsl:template match="node()" mode="break-parent">

        
<xsl:sequence select="false()" />

    
</xsl:template>



</xsl:stylesheet>













































































v