Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • Sam 184 posts 209 karma points
    Feb 05, 2011 @ 20:38
    Sam
    0

    Previous and next links to move through same level nodes with sorting

    Hi everyone,

    I am using code from another thread to have previous/next links to move through same level nodes but am trying to move it into templates to apply sorting. Is there a way to apply sorting to this or am I doing this the wrong way? Here's the code:

    <xsl:template match="/">
                    <ul id="prevNextMenu">
                      <xsl:apply-templates select="$currentPage/descendant-or-self::* /PortfolioItem">
                                    <xsl:sort select="@createDate" data-type="text" order="descending" />
                            </xsl:apply-templates>
                    </ul>
    </xsl:template>

    <xsl:template match="PortfolioItem">
      
    <xsl:variable name="nextId" select="number($currentPage/following-sibling::* [@isDoc]/@id)"/>
    <xsl:variable name="prevId" select="number($currentPage/preceding-sibling::* [@isDoc]/@id)"/>
      
          <xsl:if test="$prevId &gt; 0">
          <li>
            <a href="{umbraco.library:NiceUrl($prevId)}">Previous</a>
          </li>
        </xsl:if>

        <xsl:if test="$nextId &gt; 0">
          <li>
            <a href="{umbraco.library:NiceUrl($nextId)}">Next</a>
          </li>
        </xsl:if>
      
    </xsl:template>

    The sorting seems wrong because how can you sort a previous and next link? Perhaps the sorting needs to be applied to the <li> itself.

    Any ideas? Thanks :)

    Sam.

  • Sam 184 posts 209 karma points
    Feb 05, 2011 @ 21:35
    Sam
    0

    This works perfect but without the sorting:

    <xsl:template match="/">
     
      <ul id="prevNextMenu">

    <xsl:variable name="nextId" select="number($currentPage/following-sibling::* [@isDoc][1]/@id)"/>
    <xsl:variable name="prevId" select="number($currentPage/preceding-sibling::* [@isDoc][1]/@id)"/>
      
          <xsl:if test="$prevId &gt; 0">
            
          <li>
            <a href="{umbraco.library:NiceUrl($prevId)}">Previous</a>
          </li>
        </xsl:if>

        <xsl:if test="$nextId &gt; 0">
          
          <li>
            <a href="{umbraco.library:NiceUrl($nextId)}">Next</a>
          </li>
        </xsl:if>
                     
      </ul>
     
    </xsl:template>

    Not sure what was going wrong in the original post? 'Descendant' should actually say 'ancestor' in my first example.

    Sam.

     

  • Chriztian Steinmeier 2800 posts 8790 karma points MVP 8x admin c-trib
    Feb 05, 2011 @ 21:44
    Chriztian Steinmeier
    0

    Hi Sam,

    That makes more sense (ancestor-or-self::) - also, you've applied the [1] predicate necessary to get only the immediate sibling. Was gonna say that :-)

    The preceding- and following-sibling:: axes always work in document order, so won't work with sorting, unless you create a new sorted node set, and apply templates to that set instead. 

    /Chriztian

  • Sam 184 posts 209 karma points
    Feb 05, 2011 @ 21:56
    Sam
    0

    Thanks Chriztian,

    I did wonder why the [1] was there. On a plus note, document order can be sorted by creation date in umbraco via right click on the tree so no need to sort by createDate in the xslt :)) happy times!

    I was gonna say I actually wanted to build something a bit more complex but I'm still a bit lame at xslt. I have 4 pages so I wanted:

    Page 1) 1 2 3 4 Next

    Page 2) Previous 1 2 3 4 Next

    Page3) Previous 1 2 3 4 Next

    Page4) Previous 1 2 3 4

    ...with the bold menu items being <li class ="selected">. But somehow I think that's a bit too much after reading paging examples with queries and stuff. I will stick at it though! Thanks again :)

    Sam.

  • Josh Reid 182 posts 258 karma points
    Feb 06, 2011 @ 02:28
    Josh Reid
    0

    Hi Sam

    This should be pretty straight fwd, as long as the pages are different nodes and not a queried page set ie 10 items of single list split across 4 pages (though thats possible it's just more maths based than the sepearte nodes approach as follows).

    Note: Just wrote it for you now (un-tested)... You can pass a rootId by macro parameter if you want or defaults to parent of currentPage...

    <!-- The fun starts here -->
      
    <!-- Input the root you want here -->
    <xsl:variable name="rootId">
      <xsl:choose>
        <xsl:when test="/macro/rootId!=''">
          <xsl:value-of select="/macro/rootId"/>
        </xsl:when>
        <xsl:otherwise>
          <xsl:value-of select="$currentPage/parent::*[@isDoc]/@id"/>
        </xsl:otherwise>
      </xsl:choose>
    </xsl:variable>

    <xsl:variable name="root" select="umbraco.library:GetXmlNodeById($rootId)"/>

    <xsl:if test="$root/* [@isDoc and string(umbracoNaviHide) != '1']">
      
    <ul class="paging">
      <xsl:for-each select="$root/* [@isDoc and string(umbracoNaviHide) != '1']">
     
        <xsl:if test="position()=1 and $currentPage!=.">
          <li><a href="{umbraco.library:NiceUrl(./preceding-sibling::* [@isDoc][1]/@id)}">Previous</a></li>
        </xsl:if>
        <li>
          <xsl:if test="$currentPage=.">
            <xsl:attribute name="class">current</xsl:attribute>
          </xsl:if>
          <a href="{umbraco.library:NiceUrl(@id)}">
            <xsl:value-of select="position()"/>
          </a>
        </li>
        <xsl:if test="position()=last() and $currentPage!=.">
          <li><a href="{umbraco.library:NiceUrl(./following-sibling::* [@isDoc][1]/@id)}">Next</a></li>
        </xsl:if>
    </xsl:for-each>
     
    </ul>

    </xsl:if>

    Cheers
    Josh

  • Sam 184 posts 209 karma points
    Feb 06, 2011 @ 16:12
    Sam
    0

    Hi Josh,

    Thanks, the nodes are different pages yes, not 10 per page or anything. No luck with the above though, I have picked the root via macro and no list shows on my page, no error parsing, just no list at all. The xslt saves without error too.

    The nodes are the same (and unique) doctype called 'PortfolioItem', could that help in making this list?

    Sam.

  • Josh Reid 182 posts 258 karma points
    Feb 06, 2011 @ 21:25
    Josh Reid
    0

    Oh, will test n edit...

  • Josh Reid 182 posts 258 karma points
    Feb 06, 2011 @ 21:31
    Josh Reid
    1

    Sorry Sam- was going a bit fast for my own good ;)

    The preceding and following siblngs should be relative to the $currentPage not the current item in loop...

    So complete working (tested) code is:

    <!-- Input the root you want here -->
      <xsl:variable name="rootId">
      <xsl:choose>
        <xsl:when test="/macro/rootId!=''">
          <xsl:value-of select="/macro/rootId"/>
        </xsl:when>
        <xsl:otherwise>
          <xsl:value-of select="$currentPage/parent::*[@isDoc]/@id"/>
        </xsl:otherwise>
      </xsl:choose>
    </xsl:variable>

    <xsl:variable name="root" select="umbraco.library:GetXmlNodeById($rootId)"/>
      
    <xsl:if test="$root/* [@isDoc and string(umbracoNaviHide) != '1']">
      
    <ul class="paging">
      <xsl:for-each select="$root/* [@isDoc and string(umbracoNaviHide) != '1']">
      
        <xsl:if test="position()=1 and $currentPage!=current()">
          <li><a href="{umbraco.library:NiceUrl($currentPage/preceding-sibling::* [@isDoc][1]/@id)}">Previous</a></li>
        </xsl:if>
        <li>
          <xsl:if test="$currentPage=.">
            <xsl:attribute name="class">current</xsl:attribute>
          </xsl:if>
          <a href="{umbraco.library:NiceUrl(./@id)}">
            <xsl:value-of select="position()"/>
          </a>
        </li>
        <xsl:if test="position()=last() and $currentPage!=current()">
          <li><a href="{umbraco.library:NiceUrl($currentPage/following-sibling::* [@isDoc][1]/@id)}">Next</a></li>
        </xsl:if>
    </xsl:for-each>
      
    </ul>

    </xsl:if>

    Cheers
    Josh

  • Sam 184 posts 209 karma points
    Feb 06, 2011 @ 22:24
    Sam
    0

    Thanks Josh,

    That's great :))  What I'm using at the moment is this so you end up with:

    Previous | Back to portfolio | Next

    <xsl:template match="/">
      
    <ul class="prevNext">

    <xsl:variable name="nextId" select="number($currentPage/following-sibling::* [@isDoc][1]/@id)"/>
    <xsl:variable name="prevId" select="number($currentPage/preceding-sibling::* [@isDoc][1]/@id)"/>
      
          <xsl:if test="$prevId &gt; 0">
          <li>
            <a href="{umbraco.library:NiceUrl($prevId)}">Prev</a><xsl:text>&nbsp;|&nbsp;</xsl:text>
          </li>
        </xsl:if>
          <li>
            <a href="{umbraco.library:NiceUrl($currentPage/parent::* /@id)}">Back to <xsl:value-of select="$currentPage/parent::* /@nodeName"/></a>
          </li>  
        <xsl:if test="$nextId &gt; 0">
          <li>
            <xsl:text>&nbsp;|&nbsp;</xsl:text><a href="{umbraco.library:NiceUrl($nextId)}">Next</a>
          </li>
        </xsl:if>
                      
    </ul>
     
    </xsl:template>

    Regarding the following lines:

    <xsl:if test="position()=1 and $currentPage!=.">

    and

    <xsl:if test="position()=1 and $currentPage!=current()">

    As you mentioned, does the top one mean current item in loop and the bottom one current item in relation to $currentPage? I've never seen the !=. before.

    Thanks.

    Sam.

  • Josh Reid 182 posts 258 karma points
    Feb 06, 2011 @ 22:38
    Josh Reid
    0

    Oh they actually mean the same thing, one is just easier to type (.) and the other is easier to see.

    Inside a for-each these are the same: . and current() - it is the current item in loop.

    The line I changed (and was referring too) is this:

          <li><a href="{umbraco.library:NiceUrl($currentPage/following-sibling::* [@isDoc][1]/@id)}">Next</a></li>

    It looks like you are all sorted (without paging), hope I helped, mark it solution if it did ;)

    Thanks
    J

  • Sam 184 posts 209 karma points
    Feb 06, 2011 @ 22:44
    Sam
    0

    Thanks Josh, that's a great help, I'm learning all the time :)

    Sam.

Please Sign in or register to post replies

Write your reply to:

Draft