Re: [xsl] toc with number with element selection

Subject: Re: [xsl] toc with number with element selection
From: Wendell Piez <wapiez@xxxxxxxxxxxxxxx>
Date: Thu, 27 Feb 2014 09:51:09 -0500
Jean-Francois,

You are hitting a wrinkle in the specification of how xsl:number
works. Your "2.2" node is not counted with the "2.1" node because they
are not siblings. (See the XSLT 2.0 Rec, section 12.2, under
level='multiple'.)

A couple of possible workarounds occur to me. One is to implement the
logic you need "by hand". A simpler and easier approach could be to
pipeline the data -- pass it through a set of templates that copies
everything except the elements that get in the way, i.e. the
group[@pdf='no'] (for them, apply templates to their children but
don't copy them), and then generate your numbering from the filtered
temporary result instead of the source.

Let us know if you need any more hints.

Cheers, Wendell

On Wed, Feb 26, 2014 at 11:18 AM, jfrm.maurel@xxxxxxxxx
<jfrm.maurel@xxxxxxxxx> wrote:
> Hi all,
>
> I would like to build a toc using xsl:number (version 2.0 with saxon)
> avoiding element with pdf="no" attributes.
> The first group element always has pdf="no" attribute. Other group elements
> can have this attribute or not.
>
> Data are as follows:
> ----------------------------
> <?xml version="1.0" encoding="UTF-8"?>
> <workshop>
>  <meta>
>   <title><line>t</line></title>
>   <image path="t.jpg"
>    author="p" />
>   <identification>t</identification>
>  </meta>
>  <body>
>   <base>f</base>
>   <group pdf="no">
>    <reference>a</reference>
>    <group>
>     <reference>a/b</reference>
>     <group>
>      <reference>a/b/c</reference>
>      <group>
>       <reference>a/b/c/d</reference>
>      </group>
>      <group>
>       <reference>a/b/c/e</reference>
>      </group>
>     </group>
>    </group>
>    <group>
>     <reference>a/f</reference>
>     <group>
>      <reference>a/f/g</reference>
>      <group>
>       <reference>a/f/g/h</reference>
>      </group>
>     </group>
>     <group pdf="no">
>      <reference>a/f/i</reference>
>      <group>
>       <reference>a/f/i/j</reference>
>      </group>
>     </group>
>    </group>
>   </group>
>  </body>
> </workshop>
>
> my attempt :
> -----------------
>
> <?xml version="1.0" encoding="UTF-8"?>
> <xsl:stylesheet version="2.0"
> xmlns:xsl="http://www.w3.org/1999/XSL/Transform";
>  xmlns:xs="http://www.w3.org/2001/XMLSchema";
> xmlns:pf="http://www.pimeca.com/pf";
> xmlns:fn="http://www.w3.org/2005/xpath-functions";>
>
>  <xsl:output encoding="UTF-8" method="xml" omit-xml-declaration="no"
> indent="yes" />
>
>  <xsl:template match="/workshop">
>   <r>
>    <xsl:apply-templates select="body" />
>   </r>
>  </xsl:template>
>
>  <xsl:template match="meta" />
>
>  <xsl:template match="body">
>   <xsl:apply-templates select="group" />
>  </xsl:template>
>
>  <xsl:template match="group[not(@pdf)]">
>   <xsl:variable name="p-number">
>    <xsl:number count="group[not(@pdf)]" level="multiple" format="1.1 "
> from="/workshop/body/group[@pdf='no']" />
>   </xsl:variable>
>   <g>
>   <p>
>    <xsl:value-of select="$p-number" />
>    <xsl:value-of select="./reference" />
>    </p>
>    <xsl:apply-templates />
>   </g>
>  </xsl:template>
>
>  <xsl:template match="group[@pdf='no']">
>   <xsl:apply-templates select="group" />
>  </xsl:template>
>
>  <xsl:template match="reference">
>  </xsl:template>
>
> </xsl:stylesheet>
>
> Incorrect result obtained:
> ---------------------------------
>
> ?xml version="1.0" encoding="UTF-8"?>
> <r>
>    <g>
>       <p>1 a/b</p>
>
>       <g>
>          <p>1.1 a/b/c</p>
>
>          <g>
>             <p>1.1.1 a/b/c/d</p>
>
>          </g>
>          <g>
>             <p>1.1.2 a/b/c/e</p>
>
>          </g>
>       </g>
>    </g>
>    <g>
>       <p>2 a/f</p>
>
>       <g>
>          <p>2.1 a/f/g</p>
>
>          <g>
>             <p>2.1.1 a/f/g/h</p>
>
>          </g>
>       </g>
>       <g>
> *<p>2.1 a/f/i/j</p>*
>
>      </g>
>    </g>
> </r>
>
> I would like to obtain 2.2 for a/f/i/j element instead of 2.1. I could not
> figure out how to do it.
>
> Could you please tell me how to do it with xsl:number or point me to
another
> solution ?
>
> Regards
>
> --
> Jean-FranC'ois MAUREL
> PIMECA
> http://www.pimeca.com
>



--
Wendell Piez | http://www.wendellpiez.com
XML | XSLT | electronic publishing
Eat Your Vegetables
_____oo_________o_o___ooooo____ooooooo_^

Current Thread