[XSL-LIST Mailing List Archive Home]
[By Thread]
[By Date]
Angela Williams wrote:
good evening for me ;)
I looked up an old template of myself where I faced a similar problem. The easy part is the number of sort statements. Just limit the amount to, say, 10, and create 10 sort statements. Then:
1. The 'order' and 'data-type' are AVT, so you can easily get them from any variable or data structure. Likely something like: $sortkeys/sort[1]/order etc. This will give you fine granularity control over descending/ascending, numeric/string. Keep in mind that it is an error when the order or data-type evaluates to empty, so make sure to use defaults in that case.
2. The select statements are a bit tricky. You can leave them simple if you only need to sort on one node with a given name (from your sortkey) and use local-name() or name() functions to match for it. You can evaluate an xpath (not sure saxon:evaluate is the way to go) or you can decide to create a simple function that takes the current node and resolves your (simplified) xpath if it is more then just a node name.
3. The order of the sortkeys is something you can resolve in several XSLT native ways. That shouldn't be that hard.
Combined, this looks something like this:
<xsl:apply-templates select="somenode">
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[1]/@order}" data-type="{$sortkey/key[1]/@type}"/>
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[2]/@order}" data-type="{$sortkey/key[2]/@type}"/>
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[3]/@order}" data-type="{$sortkey/key[3]/@type}"/>
.... etc (10x) ...
</xsl:apply-templates>
You can generalize this to some further extend, of course.
If you want even more control, you should consider making a two-pass transformation where in the first pass you create the XSLT that contains the correct sortkeys. FXSL has many examples of how to do multi-pass on XSLT alone.
HTH,
Re: [xsl] Dynamically define number of xsl:sort stmts using parameters
Subject: Re: [xsl] Dynamically define number of xsl:sort stmts using parameters From: Abel Braaksma <abel.online@xxxxxxxxx> Date: Tue, 27 Mar 2007 17:52:10 +0200 |
Angela Williams wrote:
Good morning, list -
good evening for me ;)
<sort order="1">name</sort> <sort order="2">city</sort> I can think of the following theoretical solutions, but I don't know if they are even possible:
1. (I know this doesn't work) Create multiple variables to evaluate the sort value and then hardcode the same number of <xsl:sort> statements that may be evaluating a null value for @select:
2. Use xsl to select the sort nodes and then dynamically write and output the template and for-each loop that uses the appropriate number of sort statements - then how would I call it in the same stylesheet?
3. Write multiple templates using 0 to n sort statements and then call the appropriate template based on the number of <sort/> nodes found? This doesn't sound very elegant or practical to me, but might be the simplest...
Any suggestions?
I looked up an old template of myself where I faced a similar problem. The easy part is the number of sort statements. Just limit the amount to, say, 10, and create 10 sort statements. Then:
1. The 'order' and 'data-type' are AVT, so you can easily get them from any variable or data structure. Likely something like: $sortkeys/sort[1]/order etc. This will give you fine granularity control over descending/ascending, numeric/string. Keep in mind that it is an error when the order or data-type evaluates to empty, so make sure to use defaults in that case.
2. The select statements are a bit tricky. You can leave them simple if you only need to sort on one node with a given name (from your sortkey) and use local-name() or name() functions to match for it. You can evaluate an xpath (not sure saxon:evaluate is the way to go) or you can decide to create a simple function that takes the current node and resolves your (simplified) xpath if it is more then just a node name.
3. The order of the sortkeys is something you can resolve in several XSLT native ways. That shouldn't be that hard.
Combined, this looks something like this:
<!-- order of these elements is the order for the sort-key --> <xsl:variable name="sortkey"> <key nodename='name' order='ascending' type='string' /> <key nodename='street' order='ascending' type='string' /> <key nodename='birth-year' order='ascending' type='numberic' /> </xsl:variable>
<xsl:apply-templates select="somenode">
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[1]/@order}" data-type="{$sortkey/key[1]/@type}"/>
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[2]/@order}" data-type="{$sortkey/key[2]/@type}"/>
<xsl:sort select="*[local-name() = $sortkey/key[1]/@nodename"
order="{$sortkey/key[3]/@order}" data-type="{$sortkey/key[3]/@type}"/>
.... etc (10x) ...
</xsl:apply-templates>
You can generalize this to some further extend, of course.
If you want even more control, you should consider making a two-pass transformation where in the first pass you create the XSLT that contains the correct sortkeys. FXSL has many examples of how to do multi-pass on XSLT alone.
HTH,
Cheers, -- Abel Braaksma http://www.nuntia.nl
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
[xsl] Dynamically define number of , Angela Williams | Thread | RE: [xsl] Dynamically define number, Angela Williams |
RE: [xsl] Need help with sorting., Austin, Darrel | Date | RE: [xsl] Dynamically define number, cknell |
Month |