Subject: RE: [xsl] determine the number of payment methods and specify order depending on page type being viewed From: "Michael Kay" <mike@xxxxxxxxxxxx> Date: Tue, 4 Nov 2008 15:57:08 -0000 |
> Now it happens that the fact that you're generating the > results in a fixed order actually simplifies things for you. > Your 'class' > attributes can each be one of three values, "doubleLine > completed", "doubleLine current" and "doubleLine". But > because the elements will come in order, these do not map > arbitrarily. Actually it's something like this: Good work Wendell, and congratulations on your patience. I spent a few minutes on this and gave it up: somehow it the ratio of complexity and tedium didn't inspire me to work on it. But you've broken the back of it. Now it just needs a way to generify it a bit more. How about a two-pass solution? <xsl:template match="paymentMethods"> <xsl:variable name="temp"> <xsl:apply-templates select="directDebit"/> <xsl:apply-templates select="creditCard"/> <xsl:apply-templates select="invoice"/> </xsl:variable> <xsl:apply-templates select="$temp/*" mode="add-class" </xsl:template> <xsl:template match="directDebit"> <directDebit>Payment by <br/>Direct Debit</directDebit> </xsl:template> <xsl:template match="creditCard"> <creditCard>Payment by <br/>Credit Card</creditCard> </xsl:template> <xsl:template match="invoice"> <invoice>Payment by <br/>Invoice</invoice> </xsl:template> <xsl:template match="*" mode="add-class"> <xsl:variable name="status"> <xsl:choose> <xsl:when test="$label = local-name()">current</xsl:when> <xsl:when test="preceding-sibling::*[local-name() = $label]">completed</xsl:when> <xsl:otherwise/> </xsl:choose> </xsl:variable> <li class="doubleLine {$status}"><xsl:copy-of select="node()"/></li> </xsl:template> Probably doesn't save many lines of code, and it runs into the 1.0 node-set() restriction, but it strikes me as capturing the logic of the problem a bit better: if a fourth and fifth kind of payment were added, fewer changes would be needed, as the final template has no knowledge of the different kinds of payment. Michael Kay http://www.saxonica.com/ > > ... I won't try to explain the logic of the assignment of > values to $status in each case. You should examine and test > it to be sure I'm right. (The logic assumes that only three > values are possible.) > > But it's worth noticing I use XSLT "attribute value syntax" (the { } > syntax) to get this value into the li/@class attribute. > > Cosmetically, if you don't like the extra space you get on > the @class when $status has no value, you can write around > that like this: > > <xsl:variable name="status"> > <xsl:if test="$label = 'directDebit'"> current</xsl:if> > </xsl:variable> > <li class="doubleLine{$status}">Payment by <br/>Direct Debit</li> > > The other concern here is to make sure that $label is > available as a global parameter or variable; you said it was > set at run time, so I assume it is. > > I think this handles your problem, except for one exception. > What happens if $label is set to 'creditCard', say, but you > have no 'creditCard' element? Currently, the stylesheet will generate: > > <ul> > <li class="doubleLine completed">Payment by <br/>Direct Debit</li> > <li class="doubleLine">Payment by <br/>Invoice</li> </ul> > > If your system does not have a way of preventing this from > happening, you need to think about what you want the > stylesheet to do if (when) it does. > > Finally -- notice that you don't need to test to see how many > and which element children of 'paymentMethod' are present. > Instead, this work is simply done by processing the input > data: elements not present are not processed. :-) This is far > more robust, and reflects the way XSLT is intended to work. > > If you need to dive in and learn how to apply and match > templates in order to get this going -- so much the better. > You'll never understand XSLT without this capability. > Template matching and the idea of "tree traversal" (context > nodes, child elements, etc. etc.) are at the heart of the language. > > Finally -- I have used XSLT 1.0 methods and idioms > throughout. In XSLT 2.0, there are ways of making this more > concise (and possibly opaque). But there's little point in > doing this in XSLT 2.0 unless you can do it in XSLT 1.0 > (which is arguably not true of all XSLT problems). > > Please ask any followup questions for clarification. > > Cheers, > Wendell > > > > ====================================================================== > Wendell Piez mailto:wapiez@xxxxxxxxxxxxxxxx > Mulberry Technologies, Inc. http://www.mulberrytech.com > 17 West Jefferson Street Direct Phone: 301/315-9635 > Suite 207 Phone: 301/315-9631 > Rockville, MD 20850 Fax: 301/315-8285 > ---------------------------------------------------------------------- > Mulberry Technologies: A Consultancy Specializing in SGML > and XML > ======================================================================
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
Re: [xsl] determine the number of p, Wendell Piez | Thread | RE: [xsl] determine the number of p, Wendell Piez |
Re: [xsl] determine the number of p, Wendell Piez | Date | Re: [xsl] typing the input from wit, Owen Rees |
Month |