[xsl] Creating Fixed-Width Text Data

Subject: [xsl] Creating Fixed-Width Text Data
From: "Michael Peet" <mjpeet@xxxxxxxxxxx>
Date: Tue, 14 Jan 2003 09:02:16 -0500
Hi All,

I have the need to create a fixed-width text record. Fields within the record can be either numeric or character. Numeric fields are zero-padded, right justified. Character fields are space-padded, left justified. A simplified example would look something like:

000123hello 00

I've developed a stylesheet with recursive templates for padding the field data, but was wondering if anyone knows of a slicker way to do it. Code follows, sorry for the long post!

XML:

<fields>
 <field>
   <name>foo</name>
   <type>N</type>
   <length>6</length>
   <value>123</value>
 </field>
 <field>
   <name>bar</name>
   <type>C</type>
   <length>12</length>
   <value>hello</value>
 </field>
 <field>
   <name>baz</name>
   <type>N</type>
   <length>2</length>
   <value/>
 </field>
</fields>

XSL:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"; version="1.0">

<xsl:output method="text"/>

 <xsl:template match="/">
   <xsl:apply-templates select="fields"/>
 </xsl:template>

 <xsl:template match="fields">
   <xsl:apply-templates select="field"/>
 </xsl:template>

 <xsl:template match="field[type = 'N']">
   <xsl:call-template name="pad-number">
     <xsl:with-param name="length" select="length"/>
     <xsl:with-param name="value" select="value"/>
   </xsl:call-template>
 </xsl:template>

 <xsl:template match="field[type = 'C']">
   <xsl:call-template name="pad-string">
     <xsl:with-param name="length" select="length"/>
     <xsl:with-param name="value" select="value"/>
   </xsl:call-template>
 </xsl:template>

 <xsl:template name="pad-string">
   <xsl:param name="length"/>
   <xsl:param name="value"/>
   <xsl:param name="pos" select="string-length($value)"/>
   <xsl:choose>
     <xsl:when test="$pos &lt; $length">
       <xsl:call-template name="pad-string">
         <xsl:with-param name="length" select="$length"/>
         <xsl:with-param name="value" select="concat($value, ' ')"/>
         <xsl:with-param name="pos" select="$pos + 1"/>
       </xsl:call-template>
     </xsl:when>
     <xsl:otherwise>
       <xsl:value-of select="$value"/>
     </xsl:otherwise>
   </xsl:choose>
 </xsl:template>

 <xsl:template name="pad-number">
   <xsl:param name="length"/>
   <xsl:param name="value"/>
   <xsl:param name="pos" select="string-length($value)"/>
   <xsl:choose>
     <xsl:when test="$pos &lt; $length">
       <xsl:call-template name="pad-number">
         <xsl:with-param name="length" select="$length"/>
         <xsl:with-param name="value" select="concat('0', $value)"/>
         <xsl:with-param name="pos" select="$pos + 1"/>
       </xsl:call-template>
     </xsl:when>
     <xsl:otherwise>
       <xsl:value-of select="$value"/>
     </xsl:otherwise>
   </xsl:choose>
 </xsl:template>

</xsl:stylesheet>

OUTPUT:

000123hello 00

Best Regards,

Mike


_________________________________________________________________
Help STOP SPAM: Try the new MSN 8 and get 2 months FREE* http://join.msn.com/?page=features/junkmail



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



Current Thread