eXtensible Stylesheet Language Transforms (XSLT)
An Introduction |
Prof. David Bernstein |
Computer Science Department |
bernstdh@jmu.edu |
xsl
namespace<?xml version="1.0" ?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" indent="yes"/> <xsl:template match="/"> <HTML> <BODY> <xsl:apply-templates /> </BODY> </HTML> </xsl:template> <xsl:template match="text"> <P> <xsl:value-of select="." /> </P> </xsl:template> </xsl:stylesheet>
xsl:stylesheet
Element<xsl:stylesheet xmlns:xsl="http://www.w3.org/TR/WD-xsl" result-ns="html">
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"> <xsl:output method="html" indent="yes"/>
xsl:template
Element
match
|
The pattern that determines which nodes will be processed by this template. |
xsl:apply-templates
Element
select
|
The pattern that determines which nodes will be processed. If this attribute is omitted, all nodes will be processed. |
xsl:value-of
Element
select
|
The pattern that determines which nodes will be processed. If this attribute is omitted, the current node will be returned. If more than one node is matched, only the first will be returned. |
<?xml version="1.0" ?> <?xml-stylesheet type="text/xsl" href="reference.xsl" ?> <bibliography> <reference> <author> <firstname>C.E.</firstname> <lastname>White</lastname> </author> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <author> <firstname>A.L.</firstname> <lastname>Kornhauser</lastname> </author> <year>2000</year> <title>Some Map-Matching Algorithms for Personal Navigation Assistants</title> <journal> Transportation Research C </journal> </reference> <reference> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <author> <firstname>I.</firstname> <lastname>El Sanhouri</lastname> </author> <year>1999</year> <title>The Roles of Driver Information and Congestion Pricing Systems</title> <book> Behavioral and Network Impacts of Driver Information Systems <editor> <firstname>P.</firstname> <lastname> Nijkamp</lastname> </editor> <editor> <firstname>R.</firstname> <lastname>Emerink</lastname> </editor> <publisher>John Wiley and Sons</publisher> <pages>371-392</pages> </book> </reference> <reference> <author> <firstname>J.</firstname> <lastname>Padmos</lastname> </author> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <year>1997</year> <title>Personal Travel Assistants and the World Wide Web</title> <journal> Transportation Research Record <volume>1573</volume> <pages>52-56</pages> </journal> </reference> <reference> <author> <firstname>R.</firstname> <lastname>Guensler</lastname> </author> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <year>1996</year> <title>Transportation Resources on the Internet</title> <journal> ITE Journal <volume>66</volume> <pages>42-47</pages> </journal> </reference> <reference> <author> <firstname>I.</firstname> <lastname>El Sanhouri</lastname> </author> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <year>1994</year> <title>Integrating Driver Information Systems with Facility-Based Congestion Pricing</title> <journal> Transportation Research Record <volume> 1450</volume> <pages>44-52</pages> </journal> </reference> <reference> <author> <firstname>D.</firstname> <lastname>Bernstein</lastname> </author> <author> <firstname>A.</firstname> <lastname>Kanaan</lastname> </author> <year>1993</year> <title>Automatic Vehicle Identification Technologies and Functionalities</title> <journal> IVHS Journal <volume> 1</volume> <pages>191-204</pages> </journal> </reference> </bibliography>
<?xml version="1.0" ?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" indent="yes"/> <!-- reference.xsl v1.0 --> <!-- root element --> <xsl:template match="/"> <xsl:apply-templates /> </xsl:template> <!-- author --> <xsl:template match="author"> <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/>, </xsl:template> <!-- bibliography --> <xsl:template match="bibliography"> <xsl:apply-templates /> </xsl:template> <!-- book --> <!-- Note the use of the built-in text() function --> <!-- that prevents the children from being selected --> <xsl:template match="book"> <xsl:value-of select="text()" />, <xsl:apply-templates select="editor"/> <xsl:apply-templates select="publisher"/> <xsl:apply-templates select="pages"/>. </xsl:template> <!-- editor --> <xsl:template match="editor"> <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/>, </xsl:template> <!-- firstname --> <xsl:template match="firstname"> <xsl:value-of select="." /> </xsl:template> <!-- journal --> <!-- Note the use of the built-in text() function --> <!-- that prevents the children from being selected --> <xsl:template match="journal"> <xsl:value-of select="text()" />, <xsl:apply-templates select="volume"/> <xsl:apply-templates select="pages"/>. </xsl:template> <!-- lastname --> <xsl:template match="lastname"> <xsl:value-of select="." /> </xsl:template> <!-- pages --> <xsl:template match="pages"> pp. <xsl:value-of select="." /> </xsl:template> <!-- publisher --> <xsl:template match="publisher"> <xsl:value-of select="." />, </xsl:template> <!-- reference --> <xsl:template match="reference"> <xsl:apply-templates select="author"/> <xsl:apply-templates select="year"/> <xsl:apply-templates select="title"/> <xsl:apply-templates select="journal"/> <xsl:apply-templates select="book"/> </xsl:template> <!-- title --> <xsl:template match="title"> "<xsl:value-of select="." />", </xsl:template> <!-- volume --> <xsl:template match="volume"> Vol. <xsl:value-of select="." />, </xsl:template> <!-- year --> <xsl:template match="year"> (<xsl:value-of select="." />) </xsl:template> </xsl:stylesheet>
/
|
The child operator. It selects elements that are
children of the specified node. For example,
reference/year refers to the year
element that is a child of the reference element.
|
.
|
The current node operator. For example, ./year
refers to the year element that is a child of the
current element.
|
@
|
The attribute operator. For example, train/@number
refers to the number attribute of the train
element.
|
*
|
The wildcard operator. For example, timetable/*
refers to all children of the timetable
element.
|
[]
|
The index operator (1-based). |
position()
returns the index of the current node
(1-based)last()
returns the index of the last node
<?xml version="1.0"?> <?xml-stylesheet type="text/xsl" href="timetable.xsl"?> <timetable title="Boston...Providence...New London...New York" subtitle="Through services to Philadelphia...Washington...Newport News"> <train number="95" normaldays="Mo-Fr" reservations="YES" businessclass="YES"> <stop> <station>Boston, MA-South Station</station> <time>6:20AM</time> </stop> <stop> <station>Boston, MA-Back Bay</station> <time>6:25AM</time> </stop> <stop> <station>Route 128, MA</station> <time>7:07AM</time> </stop> <stop> <station>Providence, RI</station> <time>7:31AM</time> </stop> <stop> <station>Kingston, RI</station> <time></time> </stop> <stop> <station>Westerly, RI</station> <time></time> </stop> <stop> <station>Mystic, CT</station> <time></time> </stop> <stop> <station>New London, CT</station> <time>8:06AM</time> </stop> <stop> <station>Old Saybrook, CT</station> <time></time> </stop> <stop> <station>New Haven, CT</station> <time status="Ar">9:00AM</time> <time status="Dp">9:15AM</time> </stop> <stop> <station>Bridgeport, CT</station> <time></time> </stop> <stop> <station>Stamford, CT</station> <time></time> </stop> <stop> <station>New Rochelle, NY</station> <time></time> </stop> <stop> <station>New York, NY</station> <time status="Ar">10:50AM</time> </stop> <stop> <station>Newark, NJ</station> <time>11:26AM</time> </stop> <stop> <station>Metropark, NJ</station> <time>11:40AM</time> </stop> <stop> <station>Trenton, NJ</station> <time>12:04AM</time> </stop> <stop> <station>Philadelphia, PA</station> <time>12:32PM</time> </stop> <stop> <station>Wilmington, DE</station> <time>12:58PM</time> </stop> <stop> <station>Baltimore, MD</station> <time>1:49PM</time> </stop> <stop> <station>BWI Airport Rail Sta., MD</station> <time>2:02PM</time> </stop> <stop> <station>New Carrollton, MD</station> <time>2:17PM</time> </stop> <stop> <station>Washington, DC</station> <time>2:35PM</time> </stop> <stop> <station>Richmond, VA</station> <time>5:19PM</time> </stop> <stop> <station>Newport News, VA</station> <time status="Ar">7:07PM</time> </stop> </train> <train number="191" normaldays="Sa" reservations="YES" businessclass="YES"> <stop> <station>Boston, MA-South Station</station> <time>6:20AM</time> </stop> <stop> <station>Boston, MA-Back Bay</station> <time>6:25AM</time> </stop> <stop> <station>Route 128, MA</station> <time>7:07AM</time> </stop> <stop> <station>Providence, RI</station> <time>7:31AM</time> </stop> <stop> <station>Kingston, RI</station> <time></time> </stop> <stop> <station>Westerly, RI</station> <time></time> </stop> <stop> <station>Mystic, CT</station> <time></time> </stop> <stop> <station>New London, CT</station> <time>8:06AM</time> </stop> <stop> <station>Old Saybrook, CT</station> <time></time> </stop> <stop> <station>New Haven, CT</station> <time status="Ar">9:00AM</time> <time status="Dp">9:15AM</time> </stop> <stop> <station>Bridgeport, CT</station> <time></time> </stop> <stop> <station>Stamford, CT</station> <time></time> </stop> <stop> <station>New Rochelle, NY</station> <time></time> </stop> <stop> <station>New York, NY</station> <time status="Ar">10:50AM</time> </stop> <stop> <station>Newark, NJ</station> <time>11:26AM</time> </stop> <stop> <station>Metropark, NJ</station> <time>11:40AM</time> </stop> <stop> <station>Trenton, NJ</station> <time>12:04AM</time> </stop> <stop> <station>Philadelphia, PA</station> <time>12:32PM</time> </stop> <stop> <station>Wilmington, DE</station> <time>12:58PM</time> </stop> <stop> <station>Baltimore, MD</station> <time>1:49PM</time> </stop> <stop> <station>BWI Airport Rail Sta., MD</station> <time>2:02PM</time> </stop> <stop> <station>New Carrollton, MD</station> <time>2:17PM</time> </stop> <stop> <station>Washington, DC</station> <time>2:35PM</time> </stop> <stop> <station>Richmond, VA</station> <time></time> </stop> <stop> <station>Newport News, VA</station> <time></time> </stop> </train> <train number="171" normaldays="Daily" businessclass="YES"> <stop> <station>Boston, MA-South Station</station> <time>7:22AM</time> </stop> <stop> <station>Boston, MA-Back Bay</station> <time>7:27AM</time> </stop> <stop> <station>Route 128, MA</station> <time>7:42AM</time> </stop> <stop> <station>Providence, RI</station> <time>8:17AM</time> </stop> <stop> <station>Kingston, RI</station> <time>8:43AM</time> </stop> <stop> <station>Westerly, RI</station> <time>8:59AM</time> </stop> <stop> <station>Mystic, CT</station> <time>9:10AM</time> </stop> <stop> <station>New London, CT</station> <time>9:25AM</time> </stop> <stop> <station>Old Saybrook, CT</station> <time>9:47AM</time> </stop> <stop> <station>New Haven, CT</station> <time status="Ar">10:25AM</time> <time status="Dp">10:35AM</time> </stop> <stop> <station>Bridgeport, CT</station> <time>10:57AM</time> </stop> <stop> <station>Stamford, CT</station> <time>11:23AM</time> </stop> <stop> <station>New Rochelle, NY</station> <time>11:43AM</time> </stop> <stop> <station>New York, NY</station> <time status="Ar">12:20PM</time> </stop> <stop> <station>Newark, NJ</station> <time>12:56PM</time> </stop> <stop> <station>Metropark, NJ</station> <time></time> </stop> <stop> <station>Trenton, NJ</station> <time>1:34PM</time> </stop> <stop> <station>Philadelphia, PA</station> <time>2:02PM</time> </stop> <stop> <station>Wilmington, DE</station> <time>2:43PM</time> </stop> <stop> <station>Baltimore, MD</station> <time>3:42PM</time> </stop> <stop> <station>BWI Airport Rail Sta., MD</station> <time>3:55PM</time> </stop> <stop> <station>New Carrollton, MD</station> <time>4:10PM</time> </stop> <stop> <station>Washington, DC</station> <time>4:30PM</time> </stop> <stop> <station>Richmond, VA</station> <time></time> </stop> <stop> <station>Newport News, VA</station> <time></time> </stop> </train> </timetable>
<?xml version="1.0"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" indent="yes"/> <!-- Root --> <xsl:template match="/"> <HTML> <HEAD> </HEAD> <BODY BGCOLOR="#FFFFFF"> <xsl:apply-templates select="timetable"/> </BODY> </HTML> </xsl:template> <!-- Station --> <xsl:template match="station"> <B> <xsl:value-of select="text()" /> </B> </xsl:template> <!-- Stop --> <xsl:template match="stop"> <TD> <xsl:apply-templates select="station" /> </TD> </xsl:template> <!-- Time --> <xsl:template match="time"> <TD> <xsl:value-of select="text()" /> </TD> </xsl:template> <!-- Timetable --> <!-- Note the use of the attribute operator --> <xsl:template match="timetable"> <H2> <xsl:value-of select="@title"/> </H2> <H3> <xsl:value-of select="@subtitle"/> </H3> <TABLE> <xsl:apply-templates select="train"/> </TABLE> </xsl:template> <!-- Train --> <!-- Note the use of the attribute and child operators --> <xsl:template match="train"> <TR> <TD><xsl:value-of select="@number" /></TD> <TD><xsl:value-of select="@normaldays" /></TD> <xsl:apply-templates select="stop/time" /> </TR> </xsl:template> <!-- Note the use of the index, attribute, and child operators --> <xsl:template match="train[1]"> <TR> <TD><B>Train Number</B></TD> <TD><B>Normal Days</B></TD> <xsl:apply-templates select="stop" /> </TR> <TR> <TD><xsl:value-of select="@number" /></TD> <TD><xsl:value-of select="@normaldays" /></TD> <xsl:apply-templates select="stop/time" /> </TR> </xsl:template> </xsl:stylesheet>
=
|
The equal value operator. For example, time[@status = 'Ar']
refers to a time element with a status
attribute equal to "Ar".
|
>
|
The greater than value operator. |
<
|
The less than value operator. |
>=
|
The greater than or equal to value operator. |
<=
|
The less than or equal to value operator. |
!=
|
The not equal to value operator. |
|
xsl:if
Element
test
|
The pattern that determines the value of the test condition. |
xsl:if
Element (cont.)xsl:choose
Elementxsl:when
elementsxsl:otherwise
elementxsl:if
xsl:choose
Element (cont.)
<!-- author --> <!-- v2.0 Fixes first author and last author --> <xsl:template match="author"> <xsl:choose> <xsl:when test="position()=1"> <xsl:apply-templates select="lastname"/>, <xsl:apply-templates select="firstname"/> </xsl:when> <xsl:when test="position()=last()"> and <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:when> <xsl:otherwise> , <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:otherwise> </xsl:choose> </xsl:template>
<xsl:template match="*|/"> <xsl:apply-templates/> </xsl:template>
<xsl:template match="text()|@*"> <xsl:value-of select="."/> </xsl:template>
<?xml version="1.0" ?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" indent="yes"/> <!-- reference.xsl v2.0 --> <!-- root element --> <xsl:template match="/"> <HTML> <BODY> <xsl:apply-templates /> </BODY> </HTML> </xsl:template> <!-- author --> <!-- v2.0 Fixes first author and last author --> <xsl:template match="author"> <xsl:choose> <xsl:when test="position()=1"> <xsl:apply-templates select="lastname"/>, <xsl:apply-templates select="firstname"/> </xsl:when> <xsl:when test="position()=last()"> and <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:when> <xsl:otherwise> , <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:otherwise> </xsl:choose> </xsl:template> <!-- bibliography --> <xsl:template match="bibliography"> <xsl:apply-templates /> </xsl:template> <!-- book --> <!-- Note the use of the built-in text() function --> <!-- that prevents the children from being selected --> <xsl:template match="book"> <EM><xsl:value-of select="text()" /></EM> , Edited by <xsl:apply-templates select="editor"/> <xsl:apply-templates select="publisher"/> <xsl:apply-templates select="pages"/>. </xsl:template> <!-- editor --> <!-- v2.0 Fixes first editor and last editor --> <xsl:template match="editor"> <xsl:choose> <xsl:when test="position()=1"> <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:when> <xsl:when test="position()=last()"> and <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:when> <xsl:otherwise> , <xsl:apply-templates select="firstname"/> <xsl:apply-templates select="lastname"/> </xsl:otherwise> </xsl:choose> </xsl:template> <!-- firstname --> <xsl:template match="firstname"> <xsl:value-of select="." /> </xsl:template> <!-- journal --> <!-- Note the use of the built-in text() function --> <!-- that prevents the children from being selected --> <!-- --> <!-- v2.0 fixed problem with missing elements --> <xsl:template match="journal"> <EM><xsl:value-of select="text()" /></EM> <xsl:if test="volume"> ,<xsl:apply-templates select="volume"/> </xsl:if> <xsl:if test="pages"> ,<xsl:apply-templates select="pages"/> </xsl:if> . </xsl:template> <!-- lastname --> <xsl:template match="lastname"> <xsl:value-of select="." /> </xsl:template> <!-- pages --> <xsl:template match="pages"> pp. <xsl:value-of select="." /> </xsl:template> <!-- publisher --> <xsl:template match="publisher"> <xsl:value-of select="." />, </xsl:template> <!-- reference --> <xsl:template match="reference"> <P> <xsl:apply-templates select="author"/> <xsl:apply-templates select="year"/> <xsl:apply-templates select="title"/> <xsl:apply-templates select="journal"/> <xsl:apply-templates select="book"/> </P> </xsl:template> <!-- title --> <xsl:template match="title"> "<xsl:value-of select="." />", </xsl:template> <!-- volume --> <xsl:template match="volume"> Vol. <xsl:value-of select="." /> </xsl:template> <!-- year --> <xsl:template match="year"> (<xsl:value-of select="." />) </xsl:template> </xsl:stylesheet>
<?xml version="1.0"?> <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" indent="yes"/> <!-- Root --> <xsl:template match="/"> <HTML> <HEAD> <STYLE> SPAN.title {font-family: Arial; font-size: 18pt; font-style: bold} SPAN.subtitle {font-family: Arial; font-size: 14pt; font-style: bold; border-bottom-style: solid; border-width:4px;} SPAN.trainnumber {font-family: Arial; font-size: 12pt; font-style: bold} TABLE {font-family: Arial; font-size: 8pt;} TABLE.inline {display:inline;} TD.head {border-bottom-style: solid; border-width: 2px;} TR {height: 14pt;} TR.trainnumber {height: 14pt;} .orange {background-color: orange;} </STYLE> </HEAD> <BODY BGCOLOR="#FFFFFF"> <xsl:apply-templates /> </BODY> </HTML> </xsl:template> <!-- Station --> <xsl:template match="station"> <B> <xsl:apply-templates />  </B> </xsl:template> <!-- Stop --> <xsl:template match="stop"> <xsl:param name="position"/> <TR> <xsl:if test="$position=2"> <TD ALIGN="LEFT" VALIGN="TOP"> <xsl:apply-templates select="station"/> </TD> </xsl:if> <TD ALIGN="RIGHT" VALIGN="TOP"> <xsl:apply-templates select="time"/> </TD> </TR> </xsl:template> <!-- Text --> <xsl:template match="text()"> <xsl:value-of select="." /> </xsl:template> <!-- Time --> <xsl:template match="time"> <xsl:apply-templates /> <BR /> </xsl:template> <!-- Timetable --> <xsl:template match="timetable"> <SPAN CLASS="title"> <xsl:value-of select="./@title"/> </SPAN> <BR /> <SPAN CLASS="subtitle"> <xsl:value-of select="./@subtitle"/> </SPAN> <BR /> <xsl:apply-templates /> </xsl:template> <!-- Train --> <xsl:template match="train"> <TABLE CLASS="inline" CELLPADDING="0" CELLSPACING="0"> <xsl:if test="position()=2"> <COLGROUP> </COLGROUP> </xsl:if> <COLGROUP> <xsl:if test="@reservations"> <xsl:attribute name="CLASS">orange</xsl:attribute> </xsl:if> </COLGROUP> <TR CLASS="trainnumber"> <xsl:if test="position()=2"> <TD CLASS="head" ALIGN="LEFT"> <B>Train Number</B> </TD> </xsl:if> <TD CLASS="head" ALIGN="CENTER"> <SPAN CLASS="trainnumber"> <xsl:value-of select="./@number" /> </SPAN> </TD> </TR> <TR> <xsl:if test="position()=2"> <TD CLASS="head" ALIGN="LEFT"> <B>Normal Days of Operation</B> </TD> </xsl:if> <TD CLASS="head" ALIGN="CENTER"> <xsl:value-of select="./@normaldays" /> </TD> </TR> <TR> <xsl:if test="position()=2"> <TD CLASS="head" ALIGN="LEFT"> <B>   Will Also Operate</B> </TD> </xsl:if> <TD CLASS="head" ALIGN="CENTER"> <xsl:value-of select="./@willalsooperate" />  </TD> </TR> <TR> <xsl:if test="position()=2"> <TD CLASS="head" ALIGN="LEFT"> <B>   Will Not Operate</B> </TD> </xsl:if> <TD CLASS="head" ALIGN="CENTER"> <xsl:value-of select="./@willnotoperate" />  </TD> </TR> <TR> <xsl:if test="position()=2"> <TD CLASS="head" ALIGN="LEFT"> <B>On Board Service</B> </TD> </xsl:if> <TD CLASS="head" ALIGN="CENTER"> <xsl:if test="@businessclass"> <IMG SRC="businessclass.gif" /> </xsl:if> <xsl:if test="@reservations"> <IMG SRC="reservations.gif" /> </xsl:if> <xsl:if test="@sleepingcar"> <IMG SRC="sleepingcar.gif" /> </xsl:if> </TD> </TR> <xsl:apply-templates select="stop"> <xsl:with-param name="position"> <xsl:value-of select="position()"/> </xsl:with-param> </xsl:apply-templates> </TABLE> </xsl:template> </xsl:stylesheet>