Hi All, I am hoping that someone can help me, XSLT is not my
strongest subject and I have come across something that I suspect is very
simple but I just can't figure it out.
I have used the Navi.xslt from the 'Building CWS Website' video tutorials and
it works fine in some areas, However in one certain area I would like to keep the
navigation on the sub page(s) consistent with the page above them. For example
the page structure is as follows:
- Home
- About Us
- Location
- Contact Us
- Places to eat
- Place A
- Place B
- Place C
Say for example if you click on 'Place A' I do not want the
navigation to change to child pages of 'Place A' I want the navigation to stay
constant with the 'Places to Eat' page.
I would assume that I need to take a copy of the Navi.xslt and make some changes
to keep this static for these particular pages which I have tried but I cannot
seem to get the code right.
You shouldn't copy the file and make changes - it's never a good idea to have multiple almost identical files; too many places for stuff to go out of sync :-)
What you need to figure out (and I don't have the Navi.xslt file here to check) is how to change what is probably one or two XPath selections, in what I assume is an xsl:for-each statement, so they select the correct node(s) to start from.
Can you put a link to the file somewhere (or if it's less than ~50 lines post it here)?
I agree with the almost identical files comment I just wasnt sure how else to do it. The Navi.xslt is below:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxml="urn:schemas-microsoft-com:xslt" xmlns:umbraco.library="urn:umbraco.library" exclude-result-prefixes="msxml umbraco.library"> <xsl:output method="xml" omit-xml-declaration="yes"/> <xsl:param name="currentPage"/> <xsl:template match="/"> <!-- Root Node --> <xsl:variable name="rootNode" select="$currentPage/ancestor-or-self::root" /> <!-- Homepage --> <xsl:variable name="homeNode" select="$rootNode/Home [@isDoc]" /> <ul id="navi"> <li> <!-- Add the CSS class 'selected' if the homeNode ID matches our currentPage node ID --> <xsl:if test="$homeNode/@id = $currentPage/@id"> <xsl:attribute name="class"> <xsl:text>selected</xsl:text> </xsl:attribute> </xsl:if> <!--Create a link to the homepage --> <a href="{umbraco.library:NiceUrl($homeNode/@id)}"> <xsl:value-of select="$homeNode/@nodeName" /> </a> </li> <!-- For each child node of the homeNode that is a document (isDoc)and the level is 2 and the property umbracoNaviHide is NOT 1 (true/checked)--> <xsl:for-each select="$homeNode/* [@isDoc and @level = 2 and string(umbracoNaviHide) != '1']"> <li> <!-- Add the CSS class 'selected' if the currentPage or parent nodes (up the tree to the root)ID matches our current node's ID in the for each loop --> <xsl:if test="$currentPage/ancestor-or-self::* [@isDoc]/@id = current()/@id"> <xsl:attribute name="class"> <xsl:text>selected</xsl:text> </xsl:attribute> </xsl:if> <!-- Create the link --> <a href="{umbraco.library:NiceUrl(@id)}"> <xsl:value-of select="@nodeName" /> </a> </li> </xsl:for-each> </ul> </xsl:template> </xsl:stylesheet>
Thought I'd just post one that should do the trick - it's a simple subnav macro, which goes upwards from currentPage to find the current "section" (i.e., a node at level 2, which can easily be changed) and then renders any children below that:
I apreciate your time on this Chriztian. I did have a sub one working an hour or so ago that would show the next level down i.e on the 'About Us' page it would show Location and Directions. The problem was then when visited one of those pages the navigation would disappear as they had no sub pages.
and then hid the link to homepage. To make it clear this navigation will not appear on the hompeage as this is controlled by hardcoded links that will not change so at no point does the Home node need to be pointed to.
You're welcome Ben — it's using "match templates" instead of a "for-each" approach. I can only recommend you learn that - it'll get you much neater and maintainable code, especially for navigations, lists etc.
repeated navigation using navi.xslt
Hi All, I am hoping that someone can help me, XSLT is not my strongest subject and I have come across something that I suspect is very simple but I just can't figure it out.
I have used the Navi.xslt from the 'Building CWS Website' video tutorials and it works fine in some areas, However in one certain area I would like to keep the navigation on the sub page(s) consistent with the page above them. For example the page structure is as follows:
- Home
- About Us
- Location
- Contact Us
- Places to eat
- Place A
- Place B
- Place C
Say for example if you click on 'Place A' I do not want the navigation to change to child pages of 'Place A' I want the navigation to stay constant with the 'Places to Eat' page.
I would assume that I need to take a copy of the Navi.xslt and make some changes to keep this static for these particular pages which I have tried but I cannot seem to get the code right.
Is anyone able to advise?
Cheers
Ben
Hi Ben,
You shouldn't copy the file and make changes - it's never a good idea to have multiple almost identical files; too many places for stuff to go out of sync :-)
What you need to figure out (and I don't have the Navi.xslt file here to check) is how to change what is probably one or two XPath selections, in what I assume is an xsl:for-each statement, so they select the correct node(s) to start from.
Can you put a link to the file somewhere (or if it's less than ~50 lines post it here)?
/Chriztian
I agree with the almost identical files comment I just wasnt sure how else to do it. The Navi.xslt is below:
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxml="urn:schemas-microsoft-com:xslt"
xmlns:umbraco.library="urn:umbraco.library"
exclude-result-prefixes="msxml umbraco.library">
<xsl:output method="xml" omit-xml-declaration="yes"/>
<xsl:param name="currentPage"/>
<xsl:template match="/">
<!-- Root Node -->
<xsl:variable name="rootNode" select="$currentPage/ancestor-or-self::root" />
<!-- Homepage -->
<xsl:variable name="homeNode" select="$rootNode/Home [@isDoc]" />
<ul id="navi">
<li>
<!-- Add the CSS class 'selected' if the homeNode ID matches our currentPage node ID -->
<xsl:if test="$homeNode/@id = $currentPage/@id">
<xsl:attribute name="class">
<xsl:text>selected</xsl:text>
</xsl:attribute>
</xsl:if>
<!--Create a link to the homepage -->
<a href="{umbraco.library:NiceUrl($homeNode/@id)}">
<xsl:value-of select="$homeNode/@nodeName" />
</a>
</li>
<!-- For each child node of the homeNode that is a document (isDoc)and the level is 2 and the property umbracoNaviHide is NOT 1 (true/checked)-->
<xsl:for-each select="$homeNode/* [@isDoc and @level = 2 and string(umbracoNaviHide) != '1']">
<li>
<!-- Add the CSS class 'selected' if the currentPage or parent nodes (up the tree to the root)ID matches our current node's ID in the for each loop -->
<xsl:if test="$currentPage/ancestor-or-self::* [@isDoc]/@id = current()/@id">
<xsl:attribute name="class">
<xsl:text>selected</xsl:text>
</xsl:attribute>
</xsl:if>
<!-- Create the link -->
<a href="{umbraco.library:NiceUrl(@id)}">
<xsl:value-of select="@nodeName" />
</a>
</li>
</xsl:for-each>
</ul>
</xsl:template>
</xsl:stylesheet>
Hi Ben,
Hmm - that one won't even show pages below level 2... is there a "SubNavi.xslt" or something, that renders the submenus?
/Chriztian
Hi Ben,
Thought I'd just post one that should do the trick - it's a simple subnav macro, which goes upwards from currentPage to find the current "section" (i.e., a node at level 2, which can easily be changed) and then renders any children below that:
/Chriztian
I apreciate your time on this Chriztian. I did have a sub one working an hour or so ago that would show the next level down i.e on the 'About Us' page it would show Location and Directions. The problem was then when visited one of those pages the navigation would disappear as they had no sub pages.
I think that all I changed was:
<!-- Homepage -->
<xsl:variable name="homeNode" select="$rootNode/Home [@isDoc]" />
to
<!-- Homepage -->
<xsl:variable name="homeNode" select="$rootNode/About[@isDoc]" />
and then hid the link to homepage. To make it clear this navigation will not appear on the hompeage as this is controlled by hardcoded links that will not change so at no point does the Home node need to be pointed to.
Does that make sense?
Chriztian, that code you posted worked a treat, thank you very much. I will study it not to figure out how it works, it doesnt look that complicated.
Thank you once again.
You're welcome Ben — it's using "match templates" instead of a "for-each" approach. I can only recommend you learn that - it'll get you much neater and maintainable code, especially for navigations, lists etc.
Maybe check this out: http://pimpmyxslt.com/presentations/2010/xslt-beyond-for-each/
/Chriztian
is working on a reply...