Re: [xsl] Selective output of half a tag?

Subject: Re: [xsl] Selective output of half a tag?
From: Antonio Fiol <fiol@xxxxxxxxxx>
Date: Tue, 11 Jun 2002 15:04:29 +0200
Oh, I see what your issue is.

I imagine you are using something like:

<xsl:for-each select="foo">
<!-- ... -->
<xsl:apply-templates/>
<!-- ... -->
</xsl:for-each>


You can use then: <mytag> <xsl:for-each select="foo"> <!-- ... --> <xsl:apply-templates/> <!-- ... --> </xsl:for-each> </mytag>

Graham Ashton wrote:

On Tue, 2002-06-11 at 12:20, Peter Davis wrote:


On Tuesday 11 June 2002 03:50, Graham Ashton wrote:


<xsl:if test="self::foo">
<mytag>
</xsl:if>
<xsl:apply-templates/>
<xsl:if test="count(following-sibling::foo)=0">
</mytag>
</xsl:if>


Yes, that doesn't work because it is not well-formed.



Thanks very much for the reply.




If all you need to do is dynamically change the name of the tag, then <xsl:element> can help you out...



I don't think that will do it, because what I'm trying to do (but failed to explain properly) above is to take a series of <foo/> tags in the source, convert them all to <bar/> in the output, and then wrap the group of <bar/> up in <mytag/>.

So,

 <foo/>
 <foo/>

becomes

 <mytag>
   <bar/>
   <bar/>
 </mytag>

Hence the need to determine if a <foo/> is the last in the group of
<foo/>'s, so it can append a </mytag>.

To complicate things, each <foo/> tag will contain quite a few tags that
will themselves be converted into other types of tag, which is why I
need to call <xsl:apply-templates/>.



If you need to selectively output or not output the entire tag, then you need something like this:

<xsl:choose>
 <xsl:when test="something">
   <mytag>
     <xsl:apply-templates/>
   </mytag>
 </xsl:when>
 <xsl:otherwise>
   <xsl:apply-templates/>
 </xsl:otherwise>
</xsl:choose>

As you might notice, the above basically has two possible outputs, and each choice has its own copy of <xsl:apply-templates/>. You've already done the hard part of putting the common code in (an)other template(s). If what you had was more than a single command inside of <mytag/>, then you would probably want to move the common code to a named template and only copy the <xsl:call-template/> inside <mytag/> and <xsl:otherwise/>.



To pursue that path suggests to me that I would need to come up with a single template that (when called for the first <foo/> tag) would output all the <foo/> tags at once. I'm not sure how to do that.

I've got Michael Kay's "XSLT Ref, 2nd Ed.", and it talks about the
disable-output-escaping option (thanks for putting me onto it).



The final and most despised option is disable-output-escaping. This is the lazy way out, but it follows your idea of telling the processor to treat "<mytag>" as text.



From XSLT Ref (pg 327):

With a bit of thought you can usually find a way to achieve the output you want without resorting to such devices.

I'd really like to do it the right way, but haven't managed to work out
what that is yet.... so I'm going to go with disable-output-escaping in
the mean time, much as I hate the cheap way out.

Thanks again.







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


Current Thread