Subject: Re: [xsl] Format text within a XML tag... From: Peter Davis <pdavis152@xxxxxxxxx> Date: Tue, 18 Jun 2002 03:02:52 -0700 |
-----BEGIN PGP SIGNED MESSAGE----- Hash: SHA1 On Tuesday 18 June 2002 02:15, Anders Wasen wrote: > I have looked into solving it with a script and deviding the string into > peaces like rule/comment and then add text formating tags around the > comment part(s), but the problem is that I don't know how many comments > there is... this will only support one comment: First, you are not using XSLT, you are using WD-XSL. The <xsl:eval> tag doesn't exist in XSLT. Since I don't know WD-XSL, my attempted solution will be in pure XSLT. Please feel free to disregard my suggestions, since you will likely get better performance (but not portability) using an extension function; if you wish to continue to use VBScript, you may do so. The concept of the loop I describe can be adapted to any language, not just XSLT. What you need is a loop: search for the leading "/*", output the text before that "/*", output some formatting tags, search for the closing "*/", output the text between the previous "/*" and that "*/", output some formatting tags, and repeat. In XSLT, you can make such a loop with a recursive template (since XSLT has no actual loop constructs), and the contains(), substring-before(), and substring-after() functions will help. The loop will need to alternate between two different states: (1) search for the "/*", and (2) search for the "*/". When (1) is matched, the process will proceed using (2), and once (2) is matched, the process will repeat with (1). <!-- the 'xsl:' prefix has been removed from all elements for brevity --> <template name="format-comment"> <param name="text"/> <!-- state (1): search for the "/*" --> <choose> <when test="not(contains($text, '/*'))"> <!-- process complete; no more comments --> <value-of select="$data"/> </when> <otherwise> <!-- output text before the comment start --> <value-of select="substring-before($text, '/*')"/> <!-- ## output openning formatting tags ## --> <text>/*</text> <!-- search for closing '*/' --> <call-template name="format-comment-close"> <!-- search in the remaining text following the '/*' --> <with-param name="text" select="substring-after($text, '/*')"/> </call-template> </otherwise> </choose> </template> <template name="format-comment-close"> <param name="text"/> <!-- state (2) --> <choose> <when test="not(contains($text, '*/'))"> <!-- unclosed comment; it's up to you what to do here --> <value-of select="$text"/> </when> <otherwise> <!-- output text before the comment end --> <value-of select="substring-before($text, '*/')"/> <text>*/</text> <!-- ## output closing formatting tags ## --> <!-- repeat search for openning '/*' --> <call-template name="format-comment"> <!-- search in the remaining text following the '*/' --> <with-param name="text" select="substring-after($text, '*/')"/> </call-template> </otherwise> </choose> </template> <!-- NOTE: THIS IS COMPLETELY UNTESTED --> You may notice that the two templates share a lot of common structure; it should be possible to collapse the two into a single template by doing some tricks with <xsl:param/>, but I'll leave that up to you. For clarity (and to save me time), I left it as two templates. The biggest problem you will have with the above is with the HTML <div> tags you want to output surrounding the comment. The openning "<div>" needs to be output in the first template, but the closing "</div>" needs to be output in the second template. This is not easy with XSLT. I can think of two ways to work around this: (1) Output the openning and closing <div></div> with disable-output-escaping in order to avoid making the stylesheet well-formed XML: <xsl:text disable-output-escaping="yes"><div ...></xsl:text> <xsl:text disable-output-escaping="yes"></div></xsl:text> (2) Nest multiple <div> tags, switching back and forth between normal and "comment" formatting. I recommend this option solely because of the problems inherent with d-o-e, but it can make the resulting HTML fairly ugly if the text has a lot of comments (each comment and the text following the comment will be nested successively deeper; the end of the text would be followed by a series of "</div></div></div>...", one for each comment). To do this, where I say "output openning formatting tags" in the first template, you would surround the <call-template/> tag like this: <div style="font-weight: bold; color: #494B95"> <xsl:call-template name="format-comment-close"> <xsl:with-param .../> </xsl:call-template> </div> And you will surround the <call-template/> in the second template with another <div> with "inverse" CSS properties: <div style="font-weight: normal; color: #000000"> <xsl:call-template name="format-comment"> <xsl:with-param .../> </xsl:call-template> </div> Hopefully it is clear how this will work when it is all put together. Hope that helps! - -- Peter Davis -----BEGIN PGP SIGNATURE----- Version: GnuPG v1.0.7 (GNU/Linux) iD8DBQE9DwVONSZCJx7tYycRArZvAJ4yG5A3e4/K+xATGoQ7fYBQXOJqLACeKdvX PDJr7lq26qNgcdEyehv4deg= =DNED -----END PGP SIGNATURE----- XSL-List info and archive: http://www.mulberrytech.com/xsl/xsl-list
Current Thread |
---|
|
<- Previous | Index | Next -> |
---|---|---|
Re: [xsl] Format text within a XML , David Carlisle | Thread | Re: [xsl] Format text within a XML , Anders Wasen |
Re: [xsl] Format text within a XML , David Carlisle | Date | Re: [xsl] Writing a stylesheet to c, David Carlisle |
Month |