[Home] [By Thread] [By Date] [Recent Entries]
On Aug 19, 2008, at 9:18 PM, Quinn Taylor wrote:
Ken, thanks so much for taking the time to help out. Sure enough, your solution works as advertised. :-) And, after reading the documentation more thoroughly, I realized there aren't for loops on variables, since XSL is a functional language. :-) Must've had that confused with <xsl:for-each> on XML elements. Regardless, I think I came up with a more straightforward solution that minimizes "yo-yo" recursion. Just thought I'd share. You can also see it in action here (for now): http://dysart.cs.byu.edu/svn/cs628/code/ Thanks for the help, hope this is of use to someone else. - Quinn <?xml version="1.0"?> <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0"> <xsl:output method="html" indent="yes"/> <xsl:template match="*"> <xsl:call-template name="printLinkedPath"> <xsl:with-param name="path">/path/to/resource</xsl:with-param> </xsl:call-template> </xsl:template> <!-- Split path components at '/', add parent links for each component. --> <xsl:template name="printLinkedPath"> <xsl:param name="path"/> <xsl:choose> <xsl:when test="$path = '/'"> <root> </xsl:when> <xsl:otherwise> <xsl:call-template name="printComponentOfPath"> <xsl:with-param name="path" select="$path"/> <xsl:with-param name="levels"> <xsl:call-template name="occurences"> <xsl:with-param name="needle" select="'/'"/> <xsl:with-param name="haystack" select="$path"/> </xsl:call-template> </xsl:with-param> </xsl:call-template> </xsl:otherwise> </xsl:choose> </xsl:template> <!-- Print links for each component except the last, with " / " in between. --> <xsl:template name="printComponentOfPath"> <xsl:param name="path"/> <xsl:param name="levels" select="0"/> <xsl:variable name="tail" select="substring-after($path,'/')"/> <xsl:choose> <!-- If there is no text after a slash, this is the last component. --> <xsl:when test="not($tail)"> <xsl:text> / </xsl:text> <xsl:value-of select="$path"/> </xsl:when> <!-- Otherwise, print a link for this component an continue on. --> <xsl:otherwise> <xsl:variable name="parentPath"> <xsl:call-template name="parentPath"> <xsl:with-param name="levels" select="$levels"/> </xsl:call-template> </xsl:variable> <xsl:variable name="head" select="substring-before($path,'/')"/> <xsl:choose> <xsl:when test="$head"> <xsl:text> / </xsl:text> <a href="{$parentPath}"><xsl:value-of select="$head"/></a> </xsl:when> <xsl:otherwise> <a href="{$parentPath}"><root></a> <!-- Leading "/" --> </xsl:otherwise> </xsl:choose> <!-- Recursive call to print next path component. --> <xsl:call-template name="printComponentOfPath"> <xsl:with-param name="path" select="$tail"/> <xsl:with-param name="levels" select="$levels - 1"/> </xsl:call-template> </xsl:otherwise> </xsl:choose> </xsl:template> <!-- Find the number of occurrences of needle in haystack. --> <xsl:template name="occurences"> <xsl:param name="needle"/> <xsl:param name="haystack"/> <xsl:param name="found" select="0"/> <!-- Find the next needle; return the count so far if none exists. --> <xsl:choose> <xsl:when test="contains($haystack,$needle)"> <xsl:call-template name="occurences"> <xsl:with-param name="needle" select="$needle"/> <xsl:with-param name="haystack" select="substring-after($haystack, $needle)"/> <xsl:with-param name="found" select="$found + 1"/> </xsl:call-template> </xsl:when> <xsl:otherwise> <xsl:value-of select="$found"/> </xsl:otherwise> </xsl:choose> </xsl:template> <!-- Create a parent path with N occurrences of "../" --> <xsl:template name="parentPath"> <xsl:param name="levels" select="0"/> <xsl:if test="$levels > 0"> <xsl:call-template name="parentPath"> <xsl:with-param name="levels" select="$levels - 1"/> </xsl:call-template> <xsl:text>../</xsl:text> </xsl:if> </xsl:template> </xsl:stylesheet>
|

Cart



