summaryrefslogtreecommitdiff
path: root/LedgerSMB/Num2text.pm
blob: bd66bcfa1cfeaf919732ffc0c9998187a9d14731 (plain)
  1. #=====================================================================
  2. # LedgerSMB
  3. # Small Medium Business Accounting software
  4. # http://www.ledgersmb.org/
  5. #
  6. # Copyright (C) 2006
  7. # This work contains copyrighted information from a number of sources all used
  8. # with permission.
  9. #
  10. # This file contains source code included with or based on SQL-Ledger which
  11. # is Copyright Dieter Simader and DWS Systems Inc. 2000-2005 and licensed
  12. # under the GNU General Public License version 2 or, at your option, any later
  13. # version. For a full list including contact information of contributors,
  14. # maintainers, and copyright holders, see the CONTRIBUTORS file.
  15. #
  16. # Original Copyright Notice from SQL-Ledger 2.6.17 (before the fork):
  17. # Copyright (C) 2002
  18. #
  19. # Author: DWS Systems Inc.
  20. # Web: http://www.sql-ledger.org
  21. #
  22. # Contributors:
  23. #
  24. #======================================================================
  25. #
  26. # This file has NOT undergone whitespace cleanup.
  27. #
  28. #======================================================================
  29. #
  30. # this is the default code for the Check package
  31. #
  32. #=====================================================================
  33. sub init {
  34. my $self = shift;
  35. my $locale = $self->{'locale'};
  36. my $langtag = substr($locale->language_tag, 0, 2);
  37. $self->{'numrules'} = 'en';
  38. $self->{'numrules'} = $langtag if
  39. grep {/$langtag/} (qw/ca de es et fr hu it nl ru/);
  40. $self->{'numrules'} = 'es' if $self->{'numrules'} eq 'ca';
  41. $self->{'numrules'} = 'de' if $self->{'numrules'} eq 'ru';
  42. %{ $self->{numbername} } =
  43. (0 => $locale->text('Zero'),
  44. 1 => $locale->text('One'),
  45. '1o' => $locale->text('One-o'),
  46. 2 => $locale->text('Two'),
  47. 3 => $locale->text('Three'),
  48. 4 => $locale->text('Four'),
  49. 5 => $locale->text('Five'),
  50. 6 => $locale->text('Six'),
  51. 7 => $locale->text('Seven'),
  52. 8 => $locale->text('Eight'),
  53. 9 => $locale->text('Nine'),
  54. 10 => $locale->text('Ten'),
  55. 11 => $locale->text('Eleven'),
  56. '11o' => $locale->text('Eleven-o'),
  57. 12 => $locale->text('Twelve'),
  58. 13 => $locale->text('Thirteen'),
  59. 14 => $locale->text('Fourteen'),
  60. 15 => $locale->text('Fifteen'),
  61. 16 => $locale->text('Sixteen'),
  62. 17 => $locale->text('Seventeen'),
  63. 18 => $locale->text('Eighteen'),
  64. 19 => $locale->text('Nineteen'),
  65. 20 => $locale->text('Twenty'),
  66. 21 => $locale->text('Twenty One'),
  67. '21o' => $locale->text('Twenty One-o'),
  68. 22 => $locale->text('Twenty Two'),
  69. 23 => $locale->text('Twenty Three'),
  70. 24 => $locale->text('Twenty Four'),
  71. 25 => $locale->text('Twenty Five'),
  72. 26 => $locale->text('Twenty Six'),
  73. 27 => $locale->text('Twenty Seven'),
  74. 28 => $locale->text('Twenty Eight'),
  75. 29 => $locale->text('Twenty Nine'),
  76. 30 => $locale->text('Thirty'),
  77. 40 => $locale->text('Forty'),
  78. 50 => $locale->text('Fifty'),
  79. 60 => $locale->text('Sixty'),
  80. 70 => $locale->text('Seventy'),
  81. 80 => $locale->text('Eighty'),
  82. 90 => $locale->text('Ninety'),
  83. 10**2 => $locale->text('Hundred'),
  84. 500 => $locale->text('Five Hundred'),
  85. 700 => $locale->text('Seven Hundred'),
  86. 900 => $locale->text('Nine Hundred'),
  87. 10**3 => $locale->text('Thousand'),
  88. 10**6 => $locale->text('Million'),
  89. 10**9 => $locale->text('Billion'),
  90. 10**12 => $locale->text('Trillion'),
  91. );
  92. }
  93. sub num2text {
  94. my ($self, $amount) = @_;
  95. return $self->num2text_de($amount) if $self->{'numrules'} eq 'de';
  96. return $self->num2text_es($amount) if $self->{'numrules'} eq 'es';
  97. return $self->num2text_nl($amount) if $self->{'numrules'} eq 'nl';
  98. return $self->num2text_hu($amount) if $self->{'numrules'} eq 'hu';
  99. return $self->num2text_et($amount) if $self->{'numrules'} eq 'et';
  100. return $self->num2text_fr($amount) if $self->{'numrules'} eq 'fr';
  101. return $self->num2text_it($amount) if $self->{'numrules'} eq 'it';
  102. return $self->num2text_en($amount);
  103. }
  104. sub num2text_en {
  105. my ($self, $amount) = @_;
  106. return $self->{numbername}{0} unless $amount;
  107. my @textnumber = ();
  108. # split amount into chunks of 3
  109. my @num = reverse split //, abs($amount);
  110. my @numblock = ();
  111. my @a;
  112. my $i;
  113. while (@num) {
  114. @a = ();
  115. for (1 .. 3) {
  116. push @a, shift @num;
  117. }
  118. push @numblock, join / /, reverse @a;
  119. }
  120. while (@numblock) {
  121. $i = $#numblock;
  122. @num = split //, $numblock[$i];
  123. if ($numblock[$i] == 0) {
  124. pop @numblock;
  125. next;
  126. }
  127. if ($numblock[$i] > 99) {
  128. # the one from hundreds
  129. push @textnumber, $self->{numbername}{$num[0]};
  130. # add hundred designation
  131. push @textnumber, $self->{numbername}{10**2};
  132. # reduce numblock
  133. $numblock[$i] -= $num[0] * 100;
  134. }
  135. $numblock[$i] *= 1;
  136. if ($numblock[$i] > 9) {
  137. # tens
  138. push @textnumber, $self->format_ten_en($numblock[$i]);
  139. } elsif ($numblock[$i] > 0) {
  140. # ones
  141. push @textnumber, $self->{numbername}{$numblock[$i]};
  142. }
  143. # add thousand, million
  144. if ($i) {
  145. $num = 10**($i * 3);
  146. push @textnumber, $self->{numbername}{$num};
  147. }
  148. pop @numblock;
  149. }
  150. join ' ', @textnumber;
  151. }
  152. sub format_ten_en {
  153. my ($self, $amount) = @_;
  154. my $textnumber = "";
  155. my @num = split //, $amount;
  156. if ($amount > 20) {
  157. $textnumber = $self->{numbername}{$num[0]*10};
  158. $amount = $num[1];
  159. } else {
  160. $textnumber = $self->{numbername}{$amount};
  161. $amount = 0;
  162. }
  163. $textnumber .= " ".$self->{numbername}{$amount} if $amount;
  164. $textnumber;
  165. }
  166. sub num2text_de {
  167. my ($self, $amount) = @_;
  168. return $self->{numbername}{0} unless $amount;
  169. my @textnumber = ();
  170. # split amount into chunks of 3
  171. my @num = reverse split //, abs($amount);
  172. my @numblock = ();
  173. my ($i, $appendn);
  174. my @a = ();
  175. while (@num) {
  176. @a = ();
  177. for (1 .. 3) {
  178. push @a, shift @num;
  179. }
  180. push @numblock, join / /, reverse @a;
  181. }
  182. my $belowhundred = !$#numblock;
  183. while (@numblock) {
  184. $i = $#numblock;
  185. @num = split //, $numblock[$i];
  186. $appendn = "";
  187. $numblock[$i] *= 1;
  188. if ($numblock[$i] == 0) {
  189. pop @numblock;
  190. next;
  191. }
  192. if ($numblock[$i] > 99) {
  193. # the one from hundreds
  194. push @textnumber, $self->{numbername}{$num[0]};
  195. # add hundred designation
  196. push @textnumber, $self->{numbername}{10**2};
  197. # reduce numblock
  198. $numblock[$i] -= $num[0] * 100;
  199. }
  200. $appendn = 'en' if ($i == 2);
  201. $appendn = 'n' if ($i > 2);
  202. if ($numblock[$i] > 9) {
  203. # tens
  204. push @textnumber, $self->format_ten_de($numblock[$i], $belowhundred);
  205. } elsif ($numblock[$i] > 1) {
  206. # ones
  207. push @textnumber, $self->{numbername}{$numblock[$i]};
  208. } elsif ($numblock[$i] == 1) {
  209. if ($i == 0) {
  210. push @textnumber, $self->{numbername}{$numblock[$i]}.'s';
  211. } else {
  212. if ($i >= 2) {
  213. push @textnumber, $self->{numbername}{$numblock[$i]}.'e';
  214. } else {
  215. push @textnumber, $self->{numbername}{$numblock[$i]};
  216. }
  217. }
  218. $appendn = "";
  219. }
  220. # add thousand, million
  221. if ($i) {
  222. $amount = 10**($i * 3);
  223. push @textnumber, $self->{numbername}{$amount}.$appendn;
  224. }
  225. pop @numblock;
  226. }
  227. join '', @textnumber;
  228. }
  229. sub format_ten_de {
  230. my ($self, $amount, $belowhundred) = @_;
  231. my $textnumber = "";
  232. my @num = split //, $amount;
  233. if ($amount > 20) {
  234. if ($num[1] == 0) {
  235. $textnumber = $self->{numbername}{$amount};
  236. } else {
  237. if ($belowhundred) {
  238. $amount = $num[0] * 10;
  239. $textnumber = $self->{numbername}{$num[1]}.'und'.$self->{numbername}{$amount};
  240. } else {
  241. $amount = $num[0] * 10;
  242. $textnumber = $self->{numbername}{$amount}.$self->{numbername}{$num[1]};
  243. $textnumber .= 's' if ($num[1] == 1);
  244. }
  245. }
  246. } else {
  247. $textnumber = $self->{numbername}{$amount};
  248. }
  249. $textnumber;
  250. }
  251. sub num2text_et {
  252. my ($self, $amount) = @_;
  253. return $self->{numbername}{0} unless $amount;
  254. my @textnumber = ();
  255. # split amount into chunks of 3
  256. my @num = reverse split //, abs($amount);
  257. my @numblock = ();
  258. my ($i, $appendit);
  259. my @a = ();
  260. while (@num) {
  261. @a = ();
  262. for (1 .. 3) {
  263. push @a, shift @num;
  264. }
  265. push @numblock, join / /, reverse @a;
  266. }
  267. while (@numblock) {
  268. $i = $#numblock;
  269. $numblock[$i] *= 1;
  270. @num = split //, $numblock[$i];
  271. $appendit = "it";
  272. $hundred = 0;
  273. if ($numblock[$i] == 0) {
  274. pop @numblock;
  275. next;
  276. }
  277. if ($numblock[$i] > 99) {
  278. # the one from hundreds
  279. push @textnumber, "$self->{numbername}{$num[0]}$self->{numbername}{10**2}";
  280. # reduce numblock
  281. $numblock[$i] -= $num[0] * 100;
  282. @num = split //, $numblock[$i];
  283. $hundred = 1;
  284. }
  285. if ($numblock[$i] > 19) {
  286. # 20 - 99
  287. push @textnumber, "$self->{numbername}{$num[0]}kümmend";
  288. @num = split //, $numblock[$i];
  289. push @textnumber, $self->{numbername}{$num[1]} if $num[1] > 0;
  290. } elsif ($numblock[$i] > 10) {
  291. # 11 - 19
  292. if ($hundred) {
  293. @num = split //, $numblock[$i];
  294. }
  295. $num = $num[1];
  296. push @textnumber, "$self->{numbername}{$num}teist";
  297. } elsif ($numblock[$i] > 1) {
  298. # ones
  299. push @textnumber, $self->{numbername}{$numblock[$i]};
  300. } elsif ($numblock[$i] == 1) {
  301. push @textnumber, $self->{numbername}{$num[0]};
  302. $appendit = "";
  303. }
  304. # add thousand, million
  305. if ($i) {
  306. $amount = 10**($i * 3);
  307. $appendit = ($i == 1) ? "" : $appendit;
  308. push @textnumber, "$self->{numbername}{$amount}$appendit";
  309. }
  310. pop @numblock;
  311. }
  312. join ' ', @textnumber;
  313. }
  314. sub num2text_es {
  315. my ($self, $amount) = @_;
  316. return $self->{numbername}{0} unless $amount;
  317. my @textnumber = ();
  318. # split amount into chunks of 3
  319. my @num = reverse split //, abs($amount);
  320. my @numblock = ();
  321. my $stripun = 0;
  322. my @a = ();
  323. my $i;
  324. while (@num) {
  325. @a = ();
  326. for (1 .. 3) {
  327. push @a, shift @num;
  328. }
  329. push @numblock, join / /, reverse @a;
  330. }
  331. # special case for 1000
  332. if ($numblock[1] eq '1' && $numblock[0] gt '000') {
  333. # remove first array element from textnumber
  334. $stripun = 1;
  335. }
  336. while (@numblock) {
  337. $i = $#numblock;
  338. @num = split //, $numblock[$i];
  339. $numblock[$i] *= 1;
  340. if ($numblock[$i] == 0) {
  341. pop @numblock;
  342. next;
  343. }
  344. if ($numblock[$i] > 99) {
  345. if ($num[0] == 1) {
  346. push @textnumber, $self->{numbername}{10**2};
  347. } else {
  348. # special case for 500, 700, 900
  349. if (grep /$num[0]/, (5,7,9)) {
  350. push @textnumber, $self->{numbername}{"${num[0]}00"};
  351. } else {
  352. # the one from hundreds, append cientos
  353. push @textnumber, $self->{numbername}{$num[0]}.$self->{numbername}{10**2}.'s';
  354. }
  355. }
  356. # reduce numblock
  357. $numblock[$i] -= $num[0] * 100;
  358. }
  359. if ($numblock[$i] > 9) {
  360. # tens
  361. push @textnumber, $self->format_ten_es($numblock[$i], $i);
  362. } elsif ($numblock[$i] > 0) {
  363. # ones
  364. $num = $numblock[$i];
  365. $num .= 'o' if ($num == 1 && $i == 0);
  366. push @textnumber, $self->{numbername}{$num};
  367. }
  368. # add thousand, million
  369. if ($i) {
  370. $num = 10**($i * 3);
  371. if ($numblock[$i] > 1) {
  372. if ($i == 2 || $i == 4) {
  373. $a = $self->{numbername}{$num}."es";
  374. $a =~ s/ó/o/;
  375. push @textnumber, $a;
  376. } elsif ($i == 3) {
  377. $num = 10**($i * 2);
  378. $a = "$self->{10**3} $self->{numbername}{$num}"."es";
  379. $a =~ s/ó/o/;
  380. push @textnumber, $a;
  381. } else {
  382. if ($i == 1) {
  383. push @textnumber, $self->{numbername}{$num};
  384. } else {
  385. push @textnumber, $self->{numbername}{$num}.'s';
  386. }
  387. }
  388. } else {
  389. push @textnumber, $self->{numbername}{$num};
  390. }
  391. }
  392. pop @numblock;
  393. }
  394. shift @textnumber if $stripun;
  395. join ' ', @textnumber;
  396. }
  397. sub format_ten_es {
  398. my ($self, $amount, $i) = @_;
  399. my $textnumber = "";
  400. my @num = split //, $amount;
  401. if ($amount > 30) {
  402. $textnumber = $self->{numbername}{$num[0]*10};
  403. $amount = $num[1];
  404. } else {
  405. $amount .= 'o' if ($num[1] == 1 && $i == 0);
  406. $textnumber = $self->{numbername}{$amount};
  407. $amount = 0;
  408. }
  409. $textnumber .= " y ".$self->{numbername}{$amount} if $amount;
  410. $textnumber;
  411. }
  412. sub num2text_fr {
  413. my ($self, $amount) = @_;
  414. return $self->{numbername}{0} unless $amount;
  415. my @textnumber = ();
  416. # split amount into chunks of 3
  417. my @num = reverse split //, abs($amount);
  418. my @numblock = ();
  419. my @a;
  420. my $i;
  421. while (@num) {
  422. @a = ();
  423. for (1 .. 3) {
  424. push @a, shift @num;
  425. }
  426. push @numblock, join / /, reverse @a;
  427. }
  428. my $cent=0;
  429. while (@numblock) {
  430. $i = $#numblock;
  431. @num = split //, $numblock[$i];
  432. if ($numblock[$i] == 0) {
  433. pop @numblock;
  434. next;
  435. }
  436. if ($numblock[$i] > 99) {
  437. $cent=1;
  438. # the one from hundreds
  439. if ($num[0] > 1) {
  440. push @textnumber, $self->{numbername}{$num[0]};
  441. }
  442. # reduce numblock
  443. $numblock[$i] -= $num[0] * 100;
  444. # add hundred designation
  445. if ($num[0] > 1) {
  446. if($numblock[$i] > 0) {
  447. push @textnumber, $self->{numbername}{10**2};
  448. } else {
  449. push @textnumber, "$self->{numbername}{10**2}s";
  450. }
  451. } else {
  452. push @textnumber, $self->{numbername}{10**2};
  453. }
  454. }
  455. $numblock[$i] *= 1;
  456. if ($numblock[$i] > 9) {
  457. # tens
  458. push @textnumber, $self->format_ten_fr($numblock[$i]);
  459. } elsif ($numblock[$i] > 0) {
  460. # ones
  461. if ($i == 1) {
  462. if ($cent == 1) {
  463. push @textnumber, $self->{numbername}{$numblock[$i]};
  464. }
  465. $cent = 0;
  466. } else {
  467. push @textnumber, $self->{numbername}{$numblock[$i]};
  468. }
  469. }
  470. # add thousand, million
  471. if ($i) {
  472. $num = 10**($i * 3);
  473. if ($i == 1) {
  474. push @textnumber, $self->{numbername}{$num};
  475. } elsif ($numblock[$i] > 1) {
  476. push @textnumber, "$self->{numbername}{$num}s";
  477. } else {
  478. push @textnumber, "$self->{numbername}{$num}";
  479. }
  480. }
  481. pop @numblock;
  482. }
  483. join ' ', @textnumber;
  484. }
  485. sub format_ten_fr {
  486. my ($self, $amount) = @_;
  487. my $textnumber = "";
  488. my @num = split //, $amount;
  489. if ($amount > 20) {
  490. if ($num[0] == 8) {
  491. if ($num[1] > 0) {
  492. $textnumber = $self->{numbername}{$num[0]*10};
  493. } else {
  494. $textnumber = "$self->{numbername}{$num[0]*10}s";
  495. }
  496. $amount = $num[1];
  497. } elsif ($num[0] == 7 || $num[0] == 9) {
  498. if ($num[1] > 0) {
  499. $textnumber = $self->{numbername}{($num[0]-1)*10};
  500. $textnumber .= " et" if ($num[1] == 1 && $num[0] == 7);
  501. $amount -= ($num[0]-1)*10;
  502. } else {
  503. $textnumber = $self->{numbername}{$num[0]*10};
  504. $amount = $num[1];
  505. }
  506. } else {
  507. $textnumber = $self->{numbername}{$num[0]*10};
  508. $textnumber .= " et" if ($num[1] == 1);
  509. $amount = $num[1];
  510. }
  511. } else {
  512. $textnumber = "$self->{numbername}{$amount}";
  513. $amount = 0;
  514. }
  515. $textnumber .= " ".$self->{numbername}{$amount} if $amount;
  516. $textnumber;
  517. }
  518. sub num2text_hu {
  519. my ($self, $amount) = @_;
  520. return $self->{numbername}{0} unless $amount;
  521. my @textnumber = ();
  522. # split amount into chunks of 3
  523. my @num = reverse split //, abs($amount);
  524. my @numblock = ();
  525. my @a;
  526. my $i;
  527. my $res;
  528. while (@num) {
  529. @a = ();
  530. for (1 .. 3) {
  531. push @a, shift @num;
  532. }
  533. push @numblock, join / /, reverse @a;
  534. }
  535. while (@numblock) {
  536. $i = $#numblock;
  537. @num = split //, $numblock[$i];
  538. if ($numblock[$i] == 0) {
  539. pop @numblock;
  540. next;
  541. }
  542. if ($numblock[$i] > 99) {
  543. push @textnumber, $self->{numbername}{$num[0]};
  544. # add hundred designation
  545. push @textnumber, $self->{numbername}{10**2};
  546. # reduce numblock
  547. $numblock[$i] -= $num[0] * 100;
  548. }
  549. $numblock[$i] *= 1;
  550. if ($numblock[$i] > 9) {
  551. # tens
  552. push @textnumber, $self->format_ten_hu($numblock[$i]);
  553. } elsif ($numblock[$i] > 0) {
  554. # ones
  555. push @textnumber, $self->{numbername}{$numblock[$i]};
  556. }
  557. # add thousand, million
  558. if ($i) {
  559. if ($i==1 && $amount < 2000){
  560. $num = 10**($i * 3);
  561. push @textnumber, $self->{numbername}{$num};
  562. } else {
  563. $num = 10**($i * 3);
  564. push @textnumber, $self->{numbername}{$num}."-";
  565. }
  566. }
  567. pop @numblock;
  568. }
  569. $res=ucfirst join '', @textnumber;
  570. $res=~s/(\-)$//;
  571. return $res;
  572. }
  573. sub format_ten_hu {
  574. my ($self, $amount) = @_;
  575. my $textnumber = "";
  576. my @num = split //, $amount;
  577. if ($amount > 30) {
  578. $textnumber = $self->{numbername}{$num[0]*10};
  579. $amount = $num[1];
  580. } else {
  581. $textnumber = $self->{numbername}{$amount};
  582. $amount = 0;
  583. }
  584. $textnumber .= "".$self->{numbername}{$amount} if $amount;
  585. $textnumber;
  586. }
  587. sub num2text_nl {
  588. my ($self, $amount) = @_;
  589. return $self->{numbername}{0} unless $amount;
  590. my @textnumber = ('**');
  591. # split amount into chunks of 3
  592. my @num = reverse split //, abs($amount);
  593. my @numblock = ();
  594. my ($i, $appendn);
  595. my @a = ();
  596. while (@num) {
  597. @a = ();
  598. for (1 .. 3) {
  599. push @a, shift @num;
  600. }
  601. push @numblock, join / /, reverse @a;
  602. }
  603. while (@numblock) {
  604. $i = $#numblock;
  605. @num = split //, $numblock[$i];
  606. $numblock[$i] *= 1;
  607. if ($numblock[$i] == 0) {
  608. pop @numblock;
  609. next;
  610. }
  611. if ($numblock[$i] > 99) {
  612. # the one from hundreds
  613. push @textnumber, $self->{numbername}{$num[0]};
  614. # add hundred designation
  615. push @textnumber, $self->{numbername}{10**2};
  616. # reduce numblock
  617. $numblock[$i] -= $num[0] * 100;
  618. }
  619. if ($numblock[$i] > 9) {
  620. # tens
  621. push @textnumber, $self->format_ten_nl($numblock[$i]);
  622. } else {
  623. # ones
  624. push @textnumber, $self->{numbername}{$numblock[$i]};
  625. }
  626. # add thousand, million
  627. if ($i) {
  628. $amount = 10**($i * 3);
  629. push @textnumber, $self->{numbername}{$amount};
  630. }
  631. pop @numblock;
  632. }
  633. push @textnumber, '**';
  634. join '', @textnumber;
  635. }
  636. sub format_ten_nl {
  637. my ($self, $amount) = @_;
  638. my $textnumber = "";
  639. my @num = split //, $amount;
  640. if ($amount > 20) {
  641. # reverse one and ten and glue together with 'en'
  642. $amount = $num[0] * 10;
  643. $textnumber = $self->{numbername}{$num[1]}.'en'.$self->{numbername}{$amount};
  644. } else {
  645. $textnumber = $self->{numbername}{$amount};
  646. }
  647. $textnumber;
  648. }
  649. sub num2text_it {
  650. my ($self, $amount) = @_;
  651. return $self->{numbername}{0} unless $amount;
  652. my @textnumber = ();
  653. # split amount into chunks of 3
  654. my @num = reverse split //, abs($amount);
  655. my @numblock = ();
  656. my ($i, $appendn);
  657. my @a = ();
  658. while (@num) {
  659. @a = ();
  660. for (1 .. 3) {
  661. push @a, shift @num;
  662. }
  663. push @numblock, join / /, reverse @a;
  664. }
  665. while (@numblock) {
  666. $i = $#numblock;
  667. @num = split //, $numblock[$i];
  668. $numblock[$i] *= 1;
  669. if ($numblock[$i] == 0) {
  670. pop @numblock;
  671. next;
  672. }
  673. if ($numblock[$i] > 99) {
  674. # the one from hundreds
  675. push @textnumber, $self->{numbername}{$num[0]};
  676. # add hundred designation
  677. push @textnumber, $self->{numbername}{10**2};
  678. # reduce numblock
  679. $numblock[$i] -= $num[0] * 100;
  680. }
  681. if ($numblock[$i] > 9) {
  682. # tens
  683. push @textnumber, $self->format_ten_it($numblock[$i]);
  684. } elsif ($numblock[$i] > 1) {
  685. # ones
  686. push @textnumber, $self->{numbername}{$numblock[$i]};
  687. }
  688. # add thousand, million
  689. if ($i) {
  690. $amount = 10**($i * 3);
  691. push @textnumber, $self->{numbername}{$amount};
  692. }
  693. pop @numblock;
  694. }
  695. join '', @textnumber;
  696. }
  697. sub format_ten_it {
  698. my ($self, $amount) = @_;
  699. my $textnumber = "";
  700. my @num = split //, $amount;
  701. if ($amount > 20) {
  702. if ($num[1] == 0) {
  703. $textnumber = $self->{numbername}{$amount};
  704. } else {
  705. $amount = $num[0] * 10;
  706. $textnumber = $self->{numbername}{$amount}.$self->{numbername}{$num[1]};
  707. }
  708. } else {
  709. $textnumber = $self->{numbername}{$amount};
  710. }
  711. $textnumber;
  712. }
  713. 1;