[XSL-LIST Mailing List Archive Home] [By Thread] [By Date] [Recent Entries] [Reply To This Message]

Re: Long time no axes/document question

Subject: Re: Long time no axes/document question
From: Jeni Tennison <jeni@xxxxxxxxxxxxxxxx>
Date: Thu, 20 Jun 2002 17:01:57 +0100
xml concat apos
Hi Richard,

> Right then the scenario is that I want to find out if a preceding
> sibling of mine has an item in another document with a attribute
> comparison between the two. What I have so far is...
>
> <xsl:variable name="sitedefxsl" select="document('sitedef.xsl')"/>
> <xsl:when test='not(preceding-sibling::menu[(not(@system) or
> $sitedefxsl//xsl:when[xsl:call-template[@name="url_check" or
> @name="article_system"] and
> contains(@test,concat("&apos;",translate(./@system,$UCASE,$lcase),"&apos
> ;"))]) and not(@hidden) and not(menu)])'>default.asp</xsl:when>
>
> I hope this is understandable - the bit that is messing me up is the
> ./@system because the . context is in the document not the element
> in the axes where I want it. I've done a similar thing earlier in
> the same style sheet for something not in an axes by preserving the
> conext in a variable but I can't see there is way to preserve a
> (possible) location in an axis.

This (and readability!) is a problem when you have predicates nested
inside each other. A way of pulling this out is to use an xsl:for-each
to go through the preceding-sibling menu elements one by one. That has
the advantage of allowing you to use the current node or intermediate
variables within the tests, so you can do:

  <xsl:variable name="sitedefxsl" select="document('sitedef.xsl')" />
  <xsl:variable name="whens"
    select="$sitedefxsl//xsl:when
              [xsl:call-template
                [@name = 'url_check' or @name = 'article_system']]" />
  <xsl:variable name="test">
    <xsl:for-each select="preceding-sibling::menu">
      <xsl:variable name="system"
        select='concat("&apos;",
                       translate(@system, $UCASE, $lcase),
                       "&apos;")' />
      <xsl:if test="not(@hidden) and not(menu) and
                    (not(@system) or
                     $whens[contains(@test, $system)]">true</xsl:if>
    </xsl:for-each>
  </xsl:variable>
  ...
  <xsl:when test="$test != 'true'">
    ...
  </xsl:when>
  ...

It's been suggested that XPath 2.0 enable you to set variables within
expressions to make this kind of thing easier, in which case you would
be able to do something like:

  <xsl:when test='preceding-sibling::menu[
                    $system := concat("&apos;",
                                      lower-case(@system),
                                      "&apos;");
                    not(@hidden) and not(menu) and
                    (not(@system) or
                     $whens[contains(@test, $system)]]'>
    ...
  </xsl:when>

Cheers,

Jeni

---
Jeni Tennison
http://www.jenitennison.com/


 XSL-List info and archive:  http://www.mulberrytech.com/xsl/xsl-list


Current Thread

PURCHASE STYLUS STUDIO ONLINE TODAY!

Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced!

Buy Stylus Studio Now

Download The World's Best XML IDE!

Accelerate XML development with our award-winning XML IDE - Download a free trial today!

Don't miss another message! Subscribe to this list today.
Email
First Name
Last Name
Company
Subscribe in XML format
RSS 2.0
Atom 0.3
Site Map | Privacy Policy | Terms of Use | Trademarks
Free Stylus Studio XML Training:
W3C Member
Stylus Studio® and DataDirect XQuery ™are products from DataDirect Technologies, is a registered trademark of Progress Software Corporation, in the U.S. and other countries. © 2004-2013 All Rights Reserved.