Mega Code Archive

 
Categories / XML / XSLT StyleSheet
 

Local function

File: Data.xml <?xml version="1.0"?> <SCENE>   <TITLE>title 1</TITLE>   <STAGEDIR>A</STAGEDIR>   <SPEECH>     <SPEAKER>B</SPEAKER>     <LINE>C</LINE>     <LINE>D</LINE>     <LINE>E</LINE>     <LINE>F</LINE>   </SPEECH> </SCENE> File: Transform.xslt <?xml version="1.0"?> <xsl:transform xmlns:xsl="http://www.w3.org/1999/XSL/Transform"   xmlns:xs="http://www.w3.org/2001/XMLSchema"   xmlns:local="local-functions.uri" exclude-result-prefixes="xs local"   version="2.0">   <xsl:variable name="speakers" as="xs:string*"     select="for $w in distinct-values(//LINE)                       return upper-case($w)" />   <xsl:function name="local:split" as="xs:string*">     <xsl:param name="line" as="xs:string" />     <xsl:sequence select="tokenize($line, '\W')" />   </xsl:function>   <xsl:function name="local:is-character" as="xs:boolean">     <xsl:param name="word" as="xs:string" />     <xsl:sequence select="upper-case($word)=$speakers" />   </xsl:function>   <xsl:template name="scan-line">     <xsl:param name="words" as="xs:string*" />     <xsl:if test="count($words) ge 3">       <xsl:if         test="local:is-character($words[1]) and                    lower-case($words[2]) = 'and' and                    local:is-character($words[3])">           <xsl:value-of select="$words[position() = 1 to 3]"             separator=" " />       </xsl:if>     </xsl:if>   </xsl:template>   <xsl:template match="/">     <naming-lines>       <xsl:for-each select="//LINE">         <xsl:call-template name="scan-line">           <xsl:with-param name="words"             select="local:split(.)" />         </xsl:call-template>       </xsl:for-each>     </naming-lines>   </xsl:template> </xsl:transform> Output: <?xml version="1.0" encoding="UTF-8"?> <naming-lines/>