1 | <?xml version="1.0"?>
|
---|
2 | <xsl:stylesheet version="1.0"
|
---|
3 | xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
|
---|
4 | xmlns:doc="http://xsltsl.org/xsl/documentation/1.0"
|
---|
5 | xmlns:math="http://xsltsl.org/math"
|
---|
6 | exclude-result-prefixes="doc math">
|
---|
7 |
|
---|
8 | <doc:reference xmlns="">
|
---|
9 | <referenceinfo>
|
---|
10 | <releaseinfo role="meta">
|
---|
11 | $Id: math.xsl,v 1.1 2004/11/10 06:51:55 balls Exp $
|
---|
12 | </releaseinfo>
|
---|
13 | <author>
|
---|
14 | <surname>Ball</surname>
|
---|
15 | <firstname>Steve</firstname>
|
---|
16 | </author>
|
---|
17 | <copyright>
|
---|
18 | <year>2004</year>
|
---|
19 | <year>2002</year>
|
---|
20 | <holder>Steve Ball</holder>
|
---|
21 | </copyright>
|
---|
22 | </referenceinfo>
|
---|
23 |
|
---|
24 | <title>Math Module</title>
|
---|
25 |
|
---|
26 | <partintro>
|
---|
27 | <section>
|
---|
28 | <title>Introduction</title>
|
---|
29 |
|
---|
30 | <para>This module provides mathematical functions.</para>
|
---|
31 | </section>
|
---|
32 | </partintro>
|
---|
33 |
|
---|
34 | </doc:reference>
|
---|
35 |
|
---|
36 | <doc:template name="math:power" xmlns="">
|
---|
37 | <refpurpose>Power</refpurpose>
|
---|
38 |
|
---|
39 | <refdescription>
|
---|
40 | <para>Raises a number to a power.</para>
|
---|
41 | </refdescription>
|
---|
42 |
|
---|
43 | <refparameter>
|
---|
44 | <variablelist>
|
---|
45 | <varlistentry>
|
---|
46 | <term>base</term>
|
---|
47 | <listitem>
|
---|
48 | <para>The base number. Must be a number.</para>
|
---|
49 | </listitem>
|
---|
50 | </varlistentry>
|
---|
51 | <varlistentry>
|
---|
52 | <term>power</term>
|
---|
53 | <listitem>
|
---|
54 | <para>The power to raise the number to. Must be an integer.</para>
|
---|
55 | </listitem>
|
---|
56 | </varlistentry>
|
---|
57 | </variablelist>
|
---|
58 | </refparameter>
|
---|
59 |
|
---|
60 | <refreturn>
|
---|
61 | <para>Returns base multiplied by itself power times. If the base or power are not numbers or if the power is fractional then an empty string is returned.</para>
|
---|
62 | </refreturn>
|
---|
63 | </doc:template>
|
---|
64 |
|
---|
65 | <xsl:template name="math:power">
|
---|
66 | <xsl:param name="base"/>
|
---|
67 | <xsl:param name="power"/>
|
---|
68 |
|
---|
69 | <xsl:choose>
|
---|
70 | <xsl:when test='$power = "0" and $base = "0"'>
|
---|
71 | <xsl:text>1</xsl:text>
|
---|
72 | </xsl:when>
|
---|
73 | <xsl:when test='$power = "0" and number($base)'>
|
---|
74 | <xsl:text>1</xsl:text>
|
---|
75 | </xsl:when>
|
---|
76 | <xsl:when test='$power = "0" and not(number($base))'/>
|
---|
77 | <xsl:when test='$base = "0" and number($power)'>
|
---|
78 | <xsl:text>0</xsl:text>
|
---|
79 | </xsl:when>
|
---|
80 |
|
---|
81 | <xsl:when test='not(number($base)) or not(number($power))'/>
|
---|
82 |
|
---|
83 | <xsl:when test='floor(number($power)) != number($power)'/>
|
---|
84 |
|
---|
85 | <xsl:when test='number($power) < 0'>
|
---|
86 | <xsl:variable name='x'>
|
---|
87 | <xsl:call-template name='math:power'>
|
---|
88 | <xsl:with-param name='base' select='$base'/>
|
---|
89 | <xsl:with-param name='power' select='-1 * $power'/>
|
---|
90 | </xsl:call-template>
|
---|
91 | </xsl:variable>
|
---|
92 | <xsl:value-of select='1 div $x'/>
|
---|
93 | </xsl:when>
|
---|
94 |
|
---|
95 | <xsl:when test='number($power) = 1'>
|
---|
96 | <xsl:value-of select='$base'/>
|
---|
97 | </xsl:when>
|
---|
98 |
|
---|
99 | <xsl:when test='number($power) > 0'>
|
---|
100 | <xsl:variable name='x'>
|
---|
101 | <xsl:call-template name='math:power'>
|
---|
102 | <xsl:with-param name='base' select='$base'/>
|
---|
103 | <xsl:with-param name='power' select='$power - 1'/>
|
---|
104 | </xsl:call-template>
|
---|
105 | </xsl:variable>
|
---|
106 | <xsl:value-of select='$base * $x'/>
|
---|
107 | </xsl:when>
|
---|
108 | <xsl:otherwise/>
|
---|
109 | </xsl:choose>
|
---|
110 | </xsl:template>
|
---|
111 |
|
---|
112 | <doc:template name="math:abs" xmlns="">
|
---|
113 | <refpurpose>Absolute Value</refpurpose>
|
---|
114 |
|
---|
115 | <refdescription>
|
---|
116 | <para>Absolute value of a number.</para>
|
---|
117 | </refdescription>
|
---|
118 |
|
---|
119 | <refparameter>
|
---|
120 | <variablelist>
|
---|
121 | <varlistentry>
|
---|
122 | <term>number</term>
|
---|
123 | <listitem>
|
---|
124 | <para>The number. Must be a number.</para>
|
---|
125 | </listitem>
|
---|
126 | </varlistentry>
|
---|
127 | </variablelist>
|
---|
128 | </refparameter>
|
---|
129 |
|
---|
130 | <refreturn>
|
---|
131 | <para>Returns the absolute value of the number.</para>
|
---|
132 | </refreturn>
|
---|
133 | </doc:template>
|
---|
134 |
|
---|
135 | <xsl:template name="math:abs">
|
---|
136 | <xsl:param name="number"/>
|
---|
137 |
|
---|
138 | <xsl:choose>
|
---|
139 | <xsl:when test='$number < 0'>
|
---|
140 | <xsl:value-of select='$number * -1'/>
|
---|
141 | </xsl:when>
|
---|
142 | <xsl:when test='$number >= 0'>
|
---|
143 | <xsl:value-of select='$number'/>
|
---|
144 | </xsl:when>
|
---|
145 | </xsl:choose>
|
---|
146 | </xsl:template>
|
---|
147 |
|
---|
148 | <doc:template name="math:cvt-hex-decimal" xmlns="">
|
---|
149 | <refpurpose>Conversion</refpurpose>
|
---|
150 |
|
---|
151 | <refdescription>
|
---|
152 | <para>Converts a hexidecimal value to a decimal value.</para>
|
---|
153 | </refdescription>
|
---|
154 |
|
---|
155 | <refparameter>
|
---|
156 | <variablelist>
|
---|
157 | <varlistentry>
|
---|
158 | <term>value</term>
|
---|
159 | <listitem>
|
---|
160 | <para>The hexidecimal number. Must be a number in hexidecimal format.</para>
|
---|
161 | </listitem>
|
---|
162 | </varlistentry>
|
---|
163 | </variablelist>
|
---|
164 | </refparameter>
|
---|
165 |
|
---|
166 | <refreturn>
|
---|
167 | <para>Returns the value as a decimal string. If the value is not a number then a NaN value is returned.</para>
|
---|
168 | </refreturn>
|
---|
169 | </doc:template>
|
---|
170 |
|
---|
171 | <xsl:template name="math:cvt-hex-decimal">
|
---|
172 | <xsl:param name="value"/>
|
---|
173 |
|
---|
174 | <xsl:choose>
|
---|
175 | <xsl:when test='$value = ""'/>
|
---|
176 |
|
---|
177 | <xsl:when test='string-length($value) = 1'>
|
---|
178 | <xsl:call-template name='math:cvt-hex-decimal-digit'>
|
---|
179 | <xsl:with-param name='digit' select='$value'/>
|
---|
180 | </xsl:call-template>
|
---|
181 | </xsl:when>
|
---|
182 | <xsl:otherwise>
|
---|
183 | <xsl:variable name='first-digit'>
|
---|
184 | <xsl:call-template name='math:cvt-hex-decimal-digit'>
|
---|
185 | <xsl:with-param name='digit' select='substring($value, 1, 1)'/>
|
---|
186 | </xsl:call-template>
|
---|
187 | </xsl:variable>
|
---|
188 | <xsl:variable name='remainder'>
|
---|
189 | <xsl:call-template name='math:cvt-hex-decimal'>
|
---|
190 | <xsl:with-param name='value' select='substring($value, 2)'/>
|
---|
191 | </xsl:call-template>
|
---|
192 | </xsl:variable>
|
---|
193 |
|
---|
194 | <xsl:value-of select='$first-digit * 16 + $remainder'/>
|
---|
195 | </xsl:otherwise>
|
---|
196 | </xsl:choose>
|
---|
197 | </xsl:template>
|
---|
198 |
|
---|
199 | <xsl:template name='math:cvt-hex-decimal-digit'>
|
---|
200 | <xsl:param name='digit' select='0'/>
|
---|
201 | <xsl:choose>
|
---|
202 | <xsl:when test='$digit <= 9'>
|
---|
203 | <xsl:value-of select='$digit'/>
|
---|
204 | </xsl:when>
|
---|
205 | <xsl:when test='$digit = "a" or $digit = "A"'>10</xsl:when>
|
---|
206 | <xsl:when test='$digit = "b" or $digit = "B"'>11</xsl:when>
|
---|
207 | <xsl:when test='$digit = "c" or $digit = "C"'>12</xsl:when>
|
---|
208 | <xsl:when test='$digit = "d" or $digit = "D"'>13</xsl:when>
|
---|
209 | <xsl:when test='$digit = "e" or $digit = "E"'>14</xsl:when>
|
---|
210 | <xsl:when test='$digit = "f" or $digit = "F"'>15</xsl:when>
|
---|
211 | </xsl:choose>
|
---|
212 | </xsl:template>
|
---|
213 |
|
---|
214 | <doc:template name="math:cvt-decimal-hex" xmlns="">
|
---|
215 | <refpurpose>Conversion</refpurpose>
|
---|
216 |
|
---|
217 | <refdescription>
|
---|
218 | <para>Converts a decimal value to a hexidecimal value.</para>
|
---|
219 | </refdescription>
|
---|
220 |
|
---|
221 | <refparameter>
|
---|
222 | <variablelist>
|
---|
223 | <varlistentry>
|
---|
224 | <term>value</term>
|
---|
225 | <listitem>
|
---|
226 | <para>The decimal number.</para>
|
---|
227 | </listitem>
|
---|
228 | </varlistentry>
|
---|
229 | </variablelist>
|
---|
230 | </refparameter>
|
---|
231 |
|
---|
232 | <refreturn>
|
---|
233 | <para>Returns the value as a hexidecimal string (lowercase). If the value is not a number then a NaN value is returned.</para>
|
---|
234 | </refreturn>
|
---|
235 | </doc:template>
|
---|
236 |
|
---|
237 | <xsl:template name="math:cvt-decimal-hex">
|
---|
238 | <xsl:param name="value"/>
|
---|
239 |
|
---|
240 | <xsl:choose>
|
---|
241 | <xsl:when test='$value = "0"'>0</xsl:when>
|
---|
242 | <xsl:when test='not(number($value))'>NaN</xsl:when>
|
---|
243 |
|
---|
244 | <xsl:when test='$value div 16 >= 1'>
|
---|
245 | <xsl:call-template name='math:cvt-decimal-hex'>
|
---|
246 | <xsl:with-param name='value' select='floor($value div 16)'/>
|
---|
247 | </xsl:call-template>
|
---|
248 | <xsl:call-template name='math:cvt-decimal-hex'>
|
---|
249 | <xsl:with-param name='value' select='$value mod 16'/>
|
---|
250 | </xsl:call-template>
|
---|
251 | </xsl:when>
|
---|
252 | <xsl:when test='$value = 10'>a</xsl:when>
|
---|
253 | <xsl:when test='$value = 11'>b</xsl:when>
|
---|
254 | <xsl:when test='$value = 12'>c</xsl:when>
|
---|
255 | <xsl:when test='$value = 13'>d</xsl:when>
|
---|
256 | <xsl:when test='$value = 14'>e</xsl:when>
|
---|
257 | <xsl:when test='$value = 15'>f</xsl:when>
|
---|
258 | <xsl:otherwise>
|
---|
259 | <xsl:value-of select='$value'/>
|
---|
260 | </xsl:otherwise>
|
---|
261 | </xsl:choose>
|
---|
262 | </xsl:template>
|
---|
263 |
|
---|
264 | <doc:template name="math:ordinal" xmlns="">
|
---|
265 | <refpurpose>Ordinal number</refpurpose>
|
---|
266 |
|
---|
267 | <refdescription>
|
---|
268 | <para>Gives the ordinal number of a given counting number. For example, 1 becomes "1st".</para>
|
---|
269 | </refdescription>
|
---|
270 |
|
---|
271 | <refparameter>
|
---|
272 | <variablelist>
|
---|
273 | <varlistentry>
|
---|
274 | <term>number</term>
|
---|
275 | <listitem>
|
---|
276 | <para>An integer number.</para>
|
---|
277 | </listitem>
|
---|
278 | </varlistentry>
|
---|
279 | </variablelist>
|
---|
280 | </refparameter>
|
---|
281 |
|
---|
282 | <refreturn>
|
---|
283 | <para>Returns the number with an ordinal suffix.</para>
|
---|
284 | </refreturn>
|
---|
285 | </doc:template>
|
---|
286 |
|
---|
287 | <xsl:template name="math:ordinal">
|
---|
288 | <xsl:param name="number"/>
|
---|
289 |
|
---|
290 | <xsl:choose>
|
---|
291 | <xsl:when test='$number < 0'/>
|
---|
292 | <xsl:otherwise>
|
---|
293 | <xsl:value-of select='$number'/>
|
---|
294 | <xsl:choose>
|
---|
295 | <xsl:when test='$number = 11 or $number = 12 or $number = 13'>th</xsl:when>
|
---|
296 | <xsl:when test='$number mod 10 = 1'>st</xsl:when>
|
---|
297 | <xsl:when test='$number mod 10 = 2'>nd</xsl:when>
|
---|
298 | <xsl:when test='$number mod 10 = 3'>rd</xsl:when>
|
---|
299 | <xsl:otherwise>th</xsl:otherwise>
|
---|
300 | </xsl:choose>
|
---|
301 | </xsl:otherwise>
|
---|
302 | </xsl:choose>
|
---|
303 | </xsl:template>
|
---|
304 |
|
---|
305 |
|
---|
306 | <doc:template name="math:ordinal-as-word" xmlns="">
|
---|
307 | <refpurpose>Returns an ordinal number</refpurpose>
|
---|
308 |
|
---|
309 | <refdescription>
|
---|
310 | <para>This template returns the ordinal number for a given counting number as a word. For example "first" for 1.</para>
|
---|
311 | <para>Only handles numbers less than 10000000 (ten million).</para>
|
---|
312 | </refdescription>
|
---|
313 |
|
---|
314 | <refparameter>
|
---|
315 | <variablelist>
|
---|
316 | <varlistentry>
|
---|
317 | <term>number</term>
|
---|
318 | <listitem>
|
---|
319 | <para>The counting number.</para>
|
---|
320 | </listitem>
|
---|
321 | </varlistentry>
|
---|
322 | <varlistentry>
|
---|
323 | <term>conjunctive</term>
|
---|
324 | <listitem>
|
---|
325 | <para>Whether to add the word "and" to the result, for example "one hundred and first" rather than "one hundred first". Default is "yes".</para>
|
---|
326 | </listitem>
|
---|
327 | </varlistentry>
|
---|
328 | </variablelist>
|
---|
329 | </refparameter>
|
---|
330 |
|
---|
331 | <refreturn>
|
---|
332 | <para>Returns the ordinal number as a string.</para>
|
---|
333 | </refreturn>
|
---|
334 | </doc:template>
|
---|
335 |
|
---|
336 | <xsl:template name="math:ordinal-as-word">
|
---|
337 | <xsl:param name="number" select="0"/>
|
---|
338 | <xsl:param name='conjunctive' select='"yes"'/>
|
---|
339 | <xsl:param name='preceding' select='0'/>
|
---|
340 |
|
---|
341 | <xsl:choose>
|
---|
342 | <xsl:when test='$preceding = 1 and $number = 0'/>
|
---|
343 | <xsl:when test='$number = 0'>zeroth</xsl:when>
|
---|
344 |
|
---|
345 | <xsl:when test="$number < 1 or $number != floor($number)"/>
|
---|
346 |
|
---|
347 | <xsl:when test='$number = 1'>
|
---|
348 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
349 | <xsl:text>first</xsl:text>
|
---|
350 | </xsl:when>
|
---|
351 | <xsl:when test='$number = 2'>
|
---|
352 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
353 | <xsl:text>second</xsl:text>
|
---|
354 | </xsl:when>
|
---|
355 | <xsl:when test='$number = 3'>
|
---|
356 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
357 | <xsl:text>third</xsl:text>
|
---|
358 | </xsl:when>
|
---|
359 | <xsl:when test='$number = 4'>
|
---|
360 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
361 | <xsl:text>fourth</xsl:text>
|
---|
362 | </xsl:when>
|
---|
363 | <xsl:when test='$number = 5'>
|
---|
364 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
365 | <xsl:text>fifth</xsl:text>
|
---|
366 | </xsl:when>
|
---|
367 | <xsl:when test='$number = 6'>
|
---|
368 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
369 | <xsl:text>sixth</xsl:text>
|
---|
370 | </xsl:when>
|
---|
371 | <xsl:when test='$number = 7'>
|
---|
372 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
373 | <xsl:text>seventh</xsl:text>
|
---|
374 | </xsl:when>
|
---|
375 | <xsl:when test='$number = 8'>
|
---|
376 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
377 | <xsl:text>eighth</xsl:text>
|
---|
378 | </xsl:when>
|
---|
379 | <xsl:when test='$number = 9'>
|
---|
380 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
381 | <xsl:text>ninth</xsl:text>
|
---|
382 | </xsl:when>
|
---|
383 | <xsl:when test='$number = 10'>
|
---|
384 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
385 | <xsl:text>tenth</xsl:text>
|
---|
386 | </xsl:when>
|
---|
387 | <xsl:when test='$number = 11'>
|
---|
388 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
389 | <xsl:text>eleventh</xsl:text>
|
---|
390 | </xsl:when>
|
---|
391 | <xsl:when test='$number = 12'>
|
---|
392 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
393 | <xsl:text>twelveth</xsl:text>
|
---|
394 | </xsl:when>
|
---|
395 | <xsl:when test='$number = 13'>
|
---|
396 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
397 | <xsl:text>thirteenth</xsl:text>
|
---|
398 | </xsl:when>
|
---|
399 | <xsl:when test='$number = 14'>
|
---|
400 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
401 | <xsl:text>fourteenth</xsl:text>
|
---|
402 | </xsl:when>
|
---|
403 | <xsl:when test='$number = 15'>
|
---|
404 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
405 | <xsl:text>fifteenth</xsl:text>
|
---|
406 | </xsl:when>
|
---|
407 | <xsl:when test='$number = 16'>
|
---|
408 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
409 | <xsl:text>sixteenth</xsl:text>
|
---|
410 | </xsl:when>
|
---|
411 | <xsl:when test='$number = 17'>
|
---|
412 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
413 | <xsl:text>seventeenth</xsl:text>
|
---|
414 | </xsl:when>
|
---|
415 | <xsl:when test='$number = 18'>
|
---|
416 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
417 | <xsl:text>eighteenth</xsl:text>
|
---|
418 | </xsl:when>
|
---|
419 | <xsl:when test='$number = 19'>
|
---|
420 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
421 | <xsl:text>nineteenth</xsl:text>
|
---|
422 | </xsl:when>
|
---|
423 | <xsl:when test='$number = 20'>
|
---|
424 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
425 | <xsl:text>twentieth</xsl:text>
|
---|
426 | </xsl:when>
|
---|
427 | <xsl:when test='$number = 30'>
|
---|
428 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
429 | <xsl:text>thirtieth</xsl:text>
|
---|
430 | </xsl:when>
|
---|
431 | <xsl:when test='$number = 40'>
|
---|
432 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
433 | <xsl:text>fortieth</xsl:text>
|
---|
434 | </xsl:when>
|
---|
435 | <xsl:when test='$number = 50'>
|
---|
436 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
437 | <xsl:text>fiftieth</xsl:text>
|
---|
438 | </xsl:when>
|
---|
439 | <xsl:when test='$number = 60'>
|
---|
440 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
441 | <xsl:text>sixtieth</xsl:text>
|
---|
442 | </xsl:when>
|
---|
443 | <xsl:when test='$number = 70'>
|
---|
444 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
445 | <xsl:text>seventieth</xsl:text>
|
---|
446 | </xsl:when>
|
---|
447 | <xsl:when test='$number = 80'>
|
---|
448 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
449 | <xsl:text>eightieth</xsl:text>
|
---|
450 | </xsl:when>
|
---|
451 | <xsl:when test='$number = 90'>
|
---|
452 | <xsl:if test='$preceding = 1'> and </xsl:if>
|
---|
453 | <xsl:text>ninetieth</xsl:text>
|
---|
454 | </xsl:when>
|
---|
455 |
|
---|
456 | <xsl:when test='$number mod 1000000 = 0'>
|
---|
457 | <xsl:call-template name='math:number-as-word'>
|
---|
458 | <xsl:with-param name='number' select='floor($number div 1000000)'/>
|
---|
459 | </xsl:call-template>
|
---|
460 | <xsl:text> millionth</xsl:text>
|
---|
461 | </xsl:when>
|
---|
462 | <xsl:when test='$number < 1000000 and $number mod 1000 = 0'>
|
---|
463 | <xsl:if test='$preceding = 1 and $conjunctive'> and </xsl:if>
|
---|
464 | <xsl:call-template name='math:number-as-word'>
|
---|
465 | <xsl:with-param name='number' select='floor($number div 1000)'/>
|
---|
466 | </xsl:call-template>
|
---|
467 | <xsl:text> thousandth</xsl:text>
|
---|
468 | </xsl:when>
|
---|
469 | <xsl:when test='$number < 1000 and $number mod 100 = 0'>
|
---|
470 | <xsl:if test='$preceding = 1 and $conjunctive'> and </xsl:if>
|
---|
471 | <xsl:call-template name='math:number-as-word'>
|
---|
472 | <xsl:with-param name='number' select='floor($number div 100)'/>
|
---|
473 | </xsl:call-template>
|
---|
474 | <xsl:text> hundredth</xsl:text>
|
---|
475 | </xsl:when>
|
---|
476 |
|
---|
477 | <xsl:when test='$number > 1000000'>
|
---|
478 | <xsl:if test='$preceding = 1'>
|
---|
479 | <xsl:text> </xsl:text>
|
---|
480 | <xsl:if test='$conjunctive'>and </xsl:if>
|
---|
481 | </xsl:if>
|
---|
482 | <xsl:call-template name='math:number-as-word'>
|
---|
483 | <xsl:with-param name='number' select='floor($number div 1000000) * 1000000'/>
|
---|
484 | </xsl:call-template>
|
---|
485 | <xsl:choose>
|
---|
486 | <xsl:when
|
---|
487 | test='(floor(floor(($number mod 1000000) + 0.1) div 100000) > 0 and $number mod 100000 > 0) or
|
---|
488 | (floor(floor(($number mod 100000) + 0.1) div 10000) > 0 and $number mod 10000 > 0) or
|
---|
489 | (floor(floor(($number mod 10000) + 0.1) div 1000) > 0 and $number mod 1000 > 0) or
|
---|
490 | (floor(floor(($number mod 1000) + 0.1) div 100) > 0 and $number mod 100 > 0) or
|
---|
491 | (floor(floor(($number mod 100) + 0.1) div 10) > 0 and $number mod 10 > 0 and $number mod 100 > 20)'>
|
---|
492 | <xsl:text> </xsl:text>
|
---|
493 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
494 | <xsl:with-param name='number' select='floor(($number mod 1000000) + 0.1)'/>
|
---|
495 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
496 | <xsl:with-param name='preceding' select='0'/>
|
---|
497 | </xsl:call-template>
|
---|
498 | </xsl:when>
|
---|
499 | <xsl:otherwise>
|
---|
500 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
501 | <xsl:with-param name='number' select='floor(($number mod 1000000) + 0.1)'/>
|
---|
502 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
503 | <xsl:with-param name='preceding' select='1'/>
|
---|
504 | </xsl:call-template>
|
---|
505 | </xsl:otherwise>
|
---|
506 | </xsl:choose>
|
---|
507 | </xsl:when>
|
---|
508 | <xsl:when test='$number > 1000'>
|
---|
509 | <xsl:if test='$preceding = 1'>
|
---|
510 | <xsl:text> </xsl:text>
|
---|
511 | <xsl:if test='$conjunctive'>and </xsl:if>
|
---|
512 | </xsl:if>
|
---|
513 | <xsl:call-template name='math:number-as-word'>
|
---|
514 | <xsl:with-param name='number' select='floor($number div 1000) * 1000'/>
|
---|
515 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
516 | </xsl:call-template>
|
---|
517 | <xsl:choose>
|
---|
518 | <xsl:when test='floor(floor(($number mod 1000) + 0.1) div 100) > 0'>
|
---|
519 | <xsl:text> </xsl:text>
|
---|
520 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
521 | <xsl:with-param name='number' select='floor(($number mod 1000) + 0.1)'/>
|
---|
522 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
523 | <xsl:with-param name='preceding' select='0'/>
|
---|
524 | </xsl:call-template>
|
---|
525 | </xsl:when>
|
---|
526 | <xsl:otherwise>
|
---|
527 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
528 | <xsl:with-param name='number' select='floor(($number mod 1000) + 0.1)'/>
|
---|
529 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
530 | <xsl:with-param name='preceding' select='1'/>
|
---|
531 | </xsl:call-template>
|
---|
532 | </xsl:otherwise>
|
---|
533 | </xsl:choose>
|
---|
534 | </xsl:when>
|
---|
535 | <xsl:when test='$number > 100'>
|
---|
536 | <xsl:if test='$preceding = 1'>
|
---|
537 | <xsl:text> </xsl:text>
|
---|
538 | <xsl:if test='$conjunctive'>and </xsl:if>
|
---|
539 | </xsl:if>
|
---|
540 | <xsl:call-template name='math:number-as-word'>
|
---|
541 | <xsl:with-param name='number' select='floor($number div 100) * 100'/>
|
---|
542 | </xsl:call-template>
|
---|
543 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
544 | <xsl:with-param name='number' select='floor(($number mod 100) + 0.1)'/>
|
---|
545 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
546 | <xsl:with-param name='preceding' select='1'/>
|
---|
547 | </xsl:call-template>
|
---|
548 | </xsl:when>
|
---|
549 |
|
---|
550 | <xsl:when test='$number > 20'>
|
---|
551 | <xsl:if test='$preceding = 1'>
|
---|
552 | <xsl:text> </xsl:text>
|
---|
553 | <xsl:if test='$conjunctive'>and </xsl:if>
|
---|
554 | </xsl:if>
|
---|
555 | <xsl:call-template name='math:number-as-word'>
|
---|
556 | <xsl:with-param name='number' select='floor($number div 10) * 10'/>
|
---|
557 | </xsl:call-template>
|
---|
558 | <xsl:text> </xsl:text>
|
---|
559 | <xsl:call-template name='math:ordinal-as-word'>
|
---|
560 | <xsl:with-param name='number' select='floor(($number mod 10) + 0.1)'/>
|
---|
561 | <xsl:with-param name='conjunctive' select='$conjunctive'/>
|
---|
562 | </xsl:call-template>
|
---|
563 | </xsl:when>
|
---|
564 |
|
---|
565 | <xsl:otherwise/>
|
---|
566 | </xsl:choose>
|
---|
567 | </xsl:template>
|
---|
568 |
|
---|
569 | <doc:template name="math:number-as-word" xmlns="">
|
---|
570 | <refpurpose>Returns a number as a word</refpurpose>
|
---|
571 |
|
---|
572 | <refdescription>
|
---|
573 | <para>This template returns the word for a given integer number, for example "one" for 1.</para>
|
---|
574 | <para>Only handles numbers less than 10000000 (ten million).</para>
|
---|
575 | </refdescription>
|
---|
576 |
|
---|
577 | <refparameter>
|
---|
578 | <variablelist>
|
---|
579 | <varlistentry>
|
---|
580 | <term>number</term>
|
---|
581 | <listitem>
|
---|
582 | <para>The counting number.</para>
|
---|
583 | </listitem>
|
---|
584 | </varlistentry>
|
---|
585 | <varlistentry>
|
---|
586 | <term>conjunctive</term>
|
---|
587 | <listitem>
|
---|
588 | <para>Adds the word "and" where appropriate, for example.</para>
|
---|
589 | </listitem>
|
---|
590 | </varlistentry>
|
---|
591 | </variablelist>
|
---|
592 | </refparameter>
|
---|
593 |
|
---|
594 | <refreturn>
|
---|
595 | <para>Returns the number as a string.</para>
|
---|
596 | </refreturn>
|
---|
597 | </doc:template>
|
---|
598 |
|
---|
599 | <xsl:template name="math:number-as-word">
|
---|
600 | <xsl:param name="number" select="0"/>
|
---|
601 | <xsl:param name='conjunctive' select='true()'/>
|
---|
602 |
|
---|
603 | <xsl:choose>
|
---|
604 |
|
---|
605 | <xsl:when test='$number = 0'>zero</xsl:when>
|
---|
606 |
|
---|
607 | <xsl:when test='$number < 0'>
|
---|
608 | <xsl:text>minus </xsl:text>
|
---|
609 | <xsl:call-template name='math:number-as-word'>
|
---|
610 | <xsl:with-param name='number' select='-1 * $number'/>
|
---|
611 | </xsl:call-template>
|
---|
612 | </xsl:when>
|
---|
613 |
|
---|
614 | <xsl:when test="$number != floor($number)"/>
|
---|
615 |
|
---|
616 | <xsl:when test='$number mod 1000000 = 0'>
|
---|
617 | <xsl:call-template name='math:number-as-word'>
|
---|
618 | <xsl:with-param name='number' select='floor($number div 1000000)'/>
|
---|
619 | </xsl:call-template>
|
---|
620 | <xsl:text> million</xsl:text>
|
---|
621 | </xsl:when>
|
---|
622 | <xsl:when test='$number >= 1000000'>
|
---|
623 | <xsl:call-template name='math:number-as-word'>
|
---|
624 | <xsl:with-param name='number' select='floor($number div 1000000)'/>
|
---|
625 | </xsl:call-template>
|
---|
626 | <xsl:text> million </xsl:text>
|
---|
627 | <xsl:call-template name='math:number-as-word'>
|
---|
628 | <xsl:with-param name='number' select='floor(($number mod 1000000) + 0.1)'/>
|
---|
629 | </xsl:call-template>
|
---|
630 | </xsl:when>
|
---|
631 | <xsl:when test='$number mod 1000 = 0'>
|
---|
632 | <xsl:call-template name='math:number-as-word'>
|
---|
633 | <xsl:with-param name='number' select='floor($number div 1000)'/>
|
---|
634 | </xsl:call-template>
|
---|
635 | <xsl:text> thousand</xsl:text>
|
---|
636 | </xsl:when>
|
---|
637 | <xsl:when test='$number >= 1000'>
|
---|
638 | <xsl:call-template name='math:number-as-word'>
|
---|
639 | <xsl:with-param name='number' select='floor($number div 1000)'/>
|
---|
640 | </xsl:call-template>
|
---|
641 | <xsl:text> thousand </xsl:text>
|
---|
642 | <xsl:if test='$conjunctive and floor(floor(($number mod 1000) + 0.1) div 100) = 0'>and </xsl:if>
|
---|
643 | <xsl:call-template name='math:number-as-word'>
|
---|
644 | <xsl:with-param name='number' select='floor(($number mod 1000) + 0.1)'/>
|
---|
645 | </xsl:call-template>
|
---|
646 | </xsl:when>
|
---|
647 | <xsl:when test='$number mod 100 = 0'>
|
---|
648 | <xsl:call-template name='math:number-as-word'>
|
---|
649 | <xsl:with-param name='number' select='floor($number div 100)'/>
|
---|
650 | </xsl:call-template>
|
---|
651 | <xsl:text> hundred</xsl:text>
|
---|
652 | </xsl:when>
|
---|
653 | <xsl:when test='$number >= 100'>
|
---|
654 | <xsl:call-template name='math:number-as-word'>
|
---|
655 | <xsl:with-param name='number' select='floor($number div 100)'/>
|
---|
656 | </xsl:call-template>
|
---|
657 | <xsl:text> hundred </xsl:text>
|
---|
658 | <xsl:if test='$conjunctive'>and </xsl:if>
|
---|
659 | <xsl:call-template name='math:number-as-word'>
|
---|
660 | <xsl:with-param name='number' select='floor(($number mod 100) + 0.1)'/>
|
---|
661 | </xsl:call-template>
|
---|
662 | </xsl:when>
|
---|
663 |
|
---|
664 | <xsl:when test='$number = 1'>one</xsl:when>
|
---|
665 | <xsl:when test='$number = 2'>two</xsl:when>
|
---|
666 | <xsl:when test='$number = 3'>three</xsl:when>
|
---|
667 | <xsl:when test='$number = 4'>four</xsl:when>
|
---|
668 | <xsl:when test='$number = 5'>five</xsl:when>
|
---|
669 | <xsl:when test='$number = 6'>six</xsl:when>
|
---|
670 | <xsl:when test='$number = 7'>seven</xsl:when>
|
---|
671 | <xsl:when test='$number = 8'>eight</xsl:when>
|
---|
672 | <xsl:when test='$number = 9'>nine</xsl:when>
|
---|
673 | <xsl:when test='$number = 10'>ten</xsl:when>
|
---|
674 | <xsl:when test='$number = 11'>eleven</xsl:when>
|
---|
675 | <xsl:when test='$number = 12'>twelve</xsl:when>
|
---|
676 | <xsl:when test='$number = 13'>thirteen</xsl:when>
|
---|
677 | <xsl:when test='$number = 14'>fourteen</xsl:when>
|
---|
678 | <xsl:when test='$number = 15'>fifteen</xsl:when>
|
---|
679 | <xsl:when test='$number = 16'>sixteen</xsl:when>
|
---|
680 | <xsl:when test='$number = 17'>seventeen</xsl:when>
|
---|
681 | <xsl:when test='$number = 18'>eighteen</xsl:when>
|
---|
682 | <xsl:when test='$number = 19'>nineteen</xsl:when>
|
---|
683 | <xsl:when test='$number = 20'>twenty</xsl:when>
|
---|
684 | <xsl:when test='$number = 30'>thirty</xsl:when>
|
---|
685 | <xsl:when test='$number = 40'>forty</xsl:when>
|
---|
686 | <xsl:when test='$number = 50'>fifty</xsl:when>
|
---|
687 | <xsl:when test='$number = 60'>sixty</xsl:when>
|
---|
688 | <xsl:when test='$number = 70'>seventy</xsl:when>
|
---|
689 | <xsl:when test='$number = 80'>eighty</xsl:when>
|
---|
690 | <xsl:when test='$number = 90'>ninety</xsl:when>
|
---|
691 |
|
---|
692 | <xsl:when test='$number < 100'>
|
---|
693 | <xsl:call-template name='math:number-as-word'>
|
---|
694 | <xsl:with-param name='number' select='floor($number div 10) * 10'/>
|
---|
695 | </xsl:call-template>
|
---|
696 | <xsl:text> </xsl:text>
|
---|
697 | <xsl:call-template name='math:number-as-word'>
|
---|
698 | <xsl:with-param name='number' select='floor(($number mod 10) + 0.1)'/>
|
---|
699 | </xsl:call-template>
|
---|
700 | </xsl:when>
|
---|
701 | </xsl:choose>
|
---|
702 | </xsl:template>
|
---|
703 | </xsl:stylesheet>
|
---|
704 |
|
---|