n2words 1.24.0 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (349) hide show
  1. package/README.md +285 -156
  2. package/dist/ArabicConverter.js +3 -0
  3. package/dist/ArabicConverter.js.map +1 -0
  4. package/dist/AzerbaijaniConverter.js +3 -0
  5. package/dist/AzerbaijaniConverter.js.map +1 -0
  6. package/dist/BanglaConverter.js +3 -0
  7. package/dist/BanglaConverter.js.map +1 -0
  8. package/dist/BiblicalHebrewConverter.js +3 -0
  9. package/dist/BiblicalHebrewConverter.js.map +1 -0
  10. package/dist/CroatianConverter.js +3 -0
  11. package/dist/CroatianConverter.js.map +1 -0
  12. package/dist/CzechConverter.js +3 -0
  13. package/dist/CzechConverter.js.map +1 -0
  14. package/dist/DanishConverter.js +3 -0
  15. package/dist/DanishConverter.js.map +1 -0
  16. package/dist/DutchConverter.js +3 -0
  17. package/dist/DutchConverter.js.map +1 -0
  18. package/dist/EnglishConverter.js +3 -0
  19. package/dist/EnglishConverter.js.map +1 -0
  20. package/dist/FilipinoConverter.js +3 -0
  21. package/dist/FilipinoConverter.js.map +1 -0
  22. package/dist/FrenchBelgiumConverter.js +3 -0
  23. package/dist/FrenchBelgiumConverter.js.map +1 -0
  24. package/dist/FrenchConverter.js +3 -0
  25. package/dist/FrenchConverter.js.map +1 -0
  26. package/dist/GermanConverter.js +3 -0
  27. package/dist/GermanConverter.js.map +1 -0
  28. package/dist/GreekConverter.js +3 -0
  29. package/dist/GreekConverter.js.map +1 -0
  30. package/dist/GujaratiConverter.js +3 -0
  31. package/dist/GujaratiConverter.js.map +1 -0
  32. package/dist/HebrewConverter.js +3 -0
  33. package/dist/HebrewConverter.js.map +1 -0
  34. package/dist/HindiConverter.js +3 -0
  35. package/dist/HindiConverter.js.map +1 -0
  36. package/dist/HungarianConverter.js +3 -0
  37. package/dist/HungarianConverter.js.map +1 -0
  38. package/dist/IndonesianConverter.js +3 -0
  39. package/dist/IndonesianConverter.js.map +1 -0
  40. package/dist/ItalianConverter.js +3 -0
  41. package/dist/ItalianConverter.js.map +1 -0
  42. package/dist/JapaneseConverter.js +3 -0
  43. package/dist/JapaneseConverter.js.map +1 -0
  44. package/dist/KannadaConverter.js +3 -0
  45. package/dist/KannadaConverter.js.map +1 -0
  46. package/dist/KoreanConverter.js +3 -0
  47. package/dist/KoreanConverter.js.map +1 -0
  48. package/dist/LatvianConverter.js +3 -0
  49. package/dist/LatvianConverter.js.map +1 -0
  50. package/dist/LithuanianConverter.js +3 -0
  51. package/dist/LithuanianConverter.js.map +1 -0
  52. package/dist/MalayConverter.js +3 -0
  53. package/dist/MalayConverter.js.map +1 -0
  54. package/dist/MarathiConverter.js +3 -0
  55. package/dist/MarathiConverter.js.map +1 -0
  56. package/dist/NorwegianBokmalConverter.js +3 -0
  57. package/dist/NorwegianBokmalConverter.js.map +1 -0
  58. package/dist/PersianConverter.js +3 -0
  59. package/dist/PersianConverter.js.map +1 -0
  60. package/dist/PolishConverter.js +3 -0
  61. package/dist/PolishConverter.js.map +1 -0
  62. package/dist/PortugueseConverter.js +3 -0
  63. package/dist/PortugueseConverter.js.map +1 -0
  64. package/dist/PunjabiConverter.js +3 -0
  65. package/dist/PunjabiConverter.js.map +1 -0
  66. package/dist/RomanianConverter.js +3 -0
  67. package/dist/RomanianConverter.js.map +1 -0
  68. package/dist/RussianConverter.js +3 -0
  69. package/dist/RussianConverter.js.map +1 -0
  70. package/dist/SerbianCyrillicConverter.js +3 -0
  71. package/dist/SerbianCyrillicConverter.js.map +1 -0
  72. package/dist/SerbianLatinConverter.js +3 -0
  73. package/dist/SerbianLatinConverter.js.map +1 -0
  74. package/dist/SimplifiedChineseConverter.js +3 -0
  75. package/dist/SimplifiedChineseConverter.js.map +1 -0
  76. package/dist/SpanishConverter.js +3 -0
  77. package/dist/SpanishConverter.js.map +1 -0
  78. package/dist/SwahiliConverter.js +3 -0
  79. package/dist/SwahiliConverter.js.map +1 -0
  80. package/dist/SwedishConverter.js +3 -0
  81. package/dist/SwedishConverter.js.map +1 -0
  82. package/dist/TamilConverter.js +3 -0
  83. package/dist/TamilConverter.js.map +1 -0
  84. package/dist/TeluguConverter.js +3 -0
  85. package/dist/TeluguConverter.js.map +1 -0
  86. package/dist/ThaiConverter.js +3 -0
  87. package/dist/ThaiConverter.js.map +1 -0
  88. package/dist/TraditionalChineseConverter.js +3 -0
  89. package/dist/TraditionalChineseConverter.js.map +1 -0
  90. package/dist/TurkishConverter.js +3 -0
  91. package/dist/TurkishConverter.js.map +1 -0
  92. package/dist/UkrainianConverter.js +3 -0
  93. package/dist/UkrainianConverter.js.map +1 -0
  94. package/dist/UrduConverter.js +3 -0
  95. package/dist/UrduConverter.js.map +1 -0
  96. package/dist/VietnameseConverter.js +3 -0
  97. package/dist/VietnameseConverter.js.map +1 -0
  98. package/dist/n2words.js +3 -2
  99. package/dist/n2words.js.map +1 -1
  100. package/lib/classes/abstract-language.d.ts +178 -0
  101. package/lib/classes/abstract-language.js +192 -185
  102. package/lib/classes/greedy-scale-language.d.ts +109 -0
  103. package/lib/classes/greedy-scale-language.js +96 -90
  104. package/lib/classes/slavic-language.d.ts +148 -0
  105. package/lib/classes/slavic-language.js +136 -106
  106. package/lib/classes/south-asian-language.d.ts +70 -0
  107. package/lib/classes/south-asian-language.js +58 -65
  108. package/lib/classes/turkic-language.d.ts +26 -0
  109. package/lib/classes/turkic-language.js +22 -26
  110. package/lib/languages/ar.d.ts +30 -0
  111. package/lib/languages/ar.js +49 -133
  112. package/lib/languages/az.d.ts +12 -0
  113. package/lib/languages/az.js +7 -23
  114. package/lib/languages/bn.d.ts +11 -0
  115. package/lib/languages/bn.js +12 -7
  116. package/lib/languages/cs.d.ts +88 -0
  117. package/lib/languages/cs.js +44 -113
  118. package/lib/languages/da.d.ts +15 -0
  119. package/lib/languages/da.js +40 -87
  120. package/lib/languages/de.d.ts +14 -0
  121. package/lib/languages/de.js +34 -68
  122. package/lib/languages/el.d.ts +14 -0
  123. package/lib/languages/el.js +22 -48
  124. package/lib/languages/en.d.ts +16 -0
  125. package/lib/languages/en.js +22 -59
  126. package/lib/languages/es.d.ts +15 -0
  127. package/lib/languages/es.js +49 -81
  128. package/lib/languages/fa.d.ts +47 -0
  129. package/lib/languages/fa.js +90 -73
  130. package/lib/languages/fil.d.ts +16 -0
  131. package/lib/languages/fil.js +35 -76
  132. package/lib/languages/fr-BE.d.ts +11 -0
  133. package/lib/languages/fr-BE.js +15 -51
  134. package/lib/languages/fr.d.ts +15 -0
  135. package/lib/languages/fr.js +33 -72
  136. package/lib/languages/gu.d.ts +11 -0
  137. package/lib/languages/gu.js +10 -34
  138. package/lib/languages/hbo.d.ts +113 -0
  139. package/lib/languages/hbo.js +251 -0
  140. package/lib/languages/he.d.ts +80 -0
  141. package/lib/languages/he.js +41 -164
  142. package/lib/languages/hi.d.ts +11 -0
  143. package/lib/languages/hi.js +12 -7
  144. package/lib/languages/hr.d.ts +80 -0
  145. package/lib/languages/hr.js +51 -95
  146. package/lib/languages/hu.d.ts +22 -0
  147. package/lib/languages/hu.js +35 -53
  148. package/lib/languages/id.d.ts +37 -0
  149. package/lib/languages/id.js +29 -44
  150. package/lib/languages/it.d.ts +37 -0
  151. package/lib/languages/it.js +36 -52
  152. package/lib/languages/ja.d.ts +17 -0
  153. package/lib/languages/ja.js +22 -75
  154. package/lib/languages/kn.d.ts +11 -0
  155. package/lib/languages/kn.js +10 -39
  156. package/lib/languages/ko.d.ts +14 -0
  157. package/lib/languages/ko.js +17 -45
  158. package/lib/languages/lt.d.ts +70 -0
  159. package/lib/languages/lt.js +28 -63
  160. package/lib/languages/lv.d.ts +70 -0
  161. package/lib/languages/lv.js +35 -58
  162. package/lib/languages/mr.d.ts +11 -0
  163. package/lib/languages/mr.js +10 -34
  164. package/lib/languages/ms.d.ts +31 -0
  165. package/lib/languages/ms.js +24 -20
  166. package/lib/languages/nb.d.ts +12 -0
  167. package/lib/languages/nb.js +36 -56
  168. package/lib/languages/nl.d.ts +16 -0
  169. package/lib/languages/nl.js +58 -109
  170. package/lib/languages/pa.d.ts +11 -0
  171. package/lib/languages/{pa-Guru.js → pa.js} +12 -7
  172. package/lib/languages/pl.d.ts +80 -0
  173. package/lib/languages/pl.js +26 -105
  174. package/lib/languages/pt.d.ts +29 -0
  175. package/lib/languages/pt.js +29 -64
  176. package/lib/languages/ro.d.ts +158 -0
  177. package/lib/languages/ro.js +60 -167
  178. package/lib/languages/ru.d.ts +85 -0
  179. package/lib/languages/ru.js +17 -37
  180. package/lib/languages/sr-Cyrl.d.ts +80 -0
  181. package/lib/languages/sr-Cyrl.js +113 -0
  182. package/lib/languages/sr-Latn.d.ts +80 -0
  183. package/lib/languages/sr-Latn.js +54 -98
  184. package/lib/languages/sv.d.ts +14 -0
  185. package/lib/languages/sv.js +26 -63
  186. package/lib/languages/sw.d.ts +39 -0
  187. package/lib/languages/sw.js +26 -21
  188. package/lib/languages/ta.d.ts +20 -0
  189. package/lib/languages/ta.js +26 -26
  190. package/lib/languages/te.d.ts +22 -0
  191. package/lib/languages/te.js +28 -38
  192. package/lib/languages/th.d.ts +17 -0
  193. package/lib/languages/th.js +25 -31
  194. package/lib/languages/tr.d.ts +12 -0
  195. package/lib/languages/tr.js +11 -38
  196. package/lib/languages/uk.d.ts +85 -0
  197. package/lib/languages/uk.js +18 -44
  198. package/lib/languages/ur.d.ts +11 -0
  199. package/lib/languages/ur.js +12 -7
  200. package/lib/languages/vi.d.ts +72 -0
  201. package/lib/languages/vi.js +25 -71
  202. package/lib/languages/zh-Hans.d.ts +21 -0
  203. package/lib/languages/zh-Hans.js +33 -87
  204. package/lib/languages/zh-Hant.d.ts +21 -0
  205. package/lib/languages/zh-Hant.js +111 -0
  206. package/lib/n2words.d.ts +209 -0
  207. package/lib/n2words.js +474 -191
  208. package/package.json +106 -67
  209. package/dist/languages/ar.js +0 -2
  210. package/dist/languages/ar.js.map +0 -1
  211. package/dist/languages/az.js +0 -2
  212. package/dist/languages/az.js.map +0 -1
  213. package/dist/languages/bn.js +0 -2
  214. package/dist/languages/bn.js.map +0 -1
  215. package/dist/languages/cs.js +0 -2
  216. package/dist/languages/cs.js.map +0 -1
  217. package/dist/languages/da.js +0 -2
  218. package/dist/languages/da.js.map +0 -1
  219. package/dist/languages/de.js +0 -2
  220. package/dist/languages/de.js.map +0 -1
  221. package/dist/languages/el.js +0 -2
  222. package/dist/languages/el.js.map +0 -1
  223. package/dist/languages/en.js +0 -2
  224. package/dist/languages/en.js.map +0 -1
  225. package/dist/languages/es.js +0 -2
  226. package/dist/languages/es.js.map +0 -1
  227. package/dist/languages/fa.js +0 -2
  228. package/dist/languages/fa.js.map +0 -1
  229. package/dist/languages/fil.js +0 -2
  230. package/dist/languages/fil.js.map +0 -1
  231. package/dist/languages/fr-BE.js +0 -2
  232. package/dist/languages/fr-BE.js.map +0 -1
  233. package/dist/languages/fr.js +0 -2
  234. package/dist/languages/fr.js.map +0 -1
  235. package/dist/languages/gu.js +0 -2
  236. package/dist/languages/gu.js.map +0 -1
  237. package/dist/languages/he.js +0 -2
  238. package/dist/languages/he.js.map +0 -1
  239. package/dist/languages/hi.js +0 -2
  240. package/dist/languages/hi.js.map +0 -1
  241. package/dist/languages/hr.js +0 -2
  242. package/dist/languages/hr.js.map +0 -1
  243. package/dist/languages/hu.js +0 -2
  244. package/dist/languages/hu.js.map +0 -1
  245. package/dist/languages/id.js +0 -2
  246. package/dist/languages/id.js.map +0 -1
  247. package/dist/languages/it.js +0 -2
  248. package/dist/languages/it.js.map +0 -1
  249. package/dist/languages/ja.js +0 -2
  250. package/dist/languages/ja.js.map +0 -1
  251. package/dist/languages/kn.js +0 -2
  252. package/dist/languages/kn.js.map +0 -1
  253. package/dist/languages/ko.js +0 -2
  254. package/dist/languages/ko.js.map +0 -1
  255. package/dist/languages/lt.js +0 -2
  256. package/dist/languages/lt.js.map +0 -1
  257. package/dist/languages/lv.js +0 -2
  258. package/dist/languages/lv.js.map +0 -1
  259. package/dist/languages/mr.js +0 -2
  260. package/dist/languages/mr.js.map +0 -1
  261. package/dist/languages/ms.js +0 -2
  262. package/dist/languages/ms.js.map +0 -1
  263. package/dist/languages/nb.js +0 -2
  264. package/dist/languages/nb.js.map +0 -1
  265. package/dist/languages/nl.js +0 -2
  266. package/dist/languages/nl.js.map +0 -1
  267. package/dist/languages/pa-Guru.js +0 -2
  268. package/dist/languages/pa-Guru.js.map +0 -1
  269. package/dist/languages/pl.js +0 -2
  270. package/dist/languages/pl.js.map +0 -1
  271. package/dist/languages/pt.js +0 -2
  272. package/dist/languages/pt.js.map +0 -1
  273. package/dist/languages/ro.js +0 -2
  274. package/dist/languages/ro.js.map +0 -1
  275. package/dist/languages/ru.js +0 -2
  276. package/dist/languages/ru.js.map +0 -1
  277. package/dist/languages/sr-Latn.js +0 -2
  278. package/dist/languages/sr-Latn.js.map +0 -1
  279. package/dist/languages/sv.js +0 -2
  280. package/dist/languages/sv.js.map +0 -1
  281. package/dist/languages/sw.js +0 -2
  282. package/dist/languages/sw.js.map +0 -1
  283. package/dist/languages/ta.js +0 -2
  284. package/dist/languages/ta.js.map +0 -1
  285. package/dist/languages/te.js +0 -2
  286. package/dist/languages/te.js.map +0 -1
  287. package/dist/languages/th.js +0 -2
  288. package/dist/languages/th.js.map +0 -1
  289. package/dist/languages/tr.js +0 -2
  290. package/dist/languages/tr.js.map +0 -1
  291. package/dist/languages/uk.js +0 -2
  292. package/dist/languages/uk.js.map +0 -1
  293. package/dist/languages/ur.js +0 -2
  294. package/dist/languages/ur.js.map +0 -1
  295. package/dist/languages/vi.js +0 -2
  296. package/dist/languages/vi.js.map +0 -1
  297. package/dist/languages/zh-Hans.js +0 -2
  298. package/dist/languages/zh-Hans.js.map +0 -1
  299. package/typings/classes/abstract-language.d.ts +0 -144
  300. package/typings/classes/greedy-scale-language.d.ts +0 -148
  301. package/typings/classes/slavic-language.d.ts +0 -145
  302. package/typings/classes/south-asian-language.d.ts +0 -101
  303. package/typings/classes/turkic-language.d.ts +0 -42
  304. package/typings/languages/ar.d.ts +0 -93
  305. package/typings/languages/az.d.ts +0 -25
  306. package/typings/languages/bn.d.ts +0 -1
  307. package/typings/languages/cs.d.ts +0 -120
  308. package/typings/languages/da.d.ts +0 -53
  309. package/typings/languages/de.d.ts +0 -26
  310. package/typings/languages/el.d.ts +0 -11
  311. package/typings/languages/en.d.ts +0 -30
  312. package/typings/languages/es.d.ts +0 -43
  313. package/typings/languages/fa.d.ts +0 -81
  314. package/typings/languages/fil.d.ts +0 -12
  315. package/typings/languages/fr-BE.d.ts +0 -41
  316. package/typings/languages/fr.d.ts +0 -43
  317. package/typings/languages/gu.d.ts +0 -12
  318. package/typings/languages/he.d.ts +0 -197
  319. package/typings/languages/hi.d.ts +0 -1
  320. package/typings/languages/hr.d.ts +0 -110
  321. package/typings/languages/hu.d.ts +0 -37
  322. package/typings/languages/id.d.ts +0 -69
  323. package/typings/languages/it.d.ts +0 -51
  324. package/typings/languages/ja.d.ts +0 -58
  325. package/typings/languages/kn.d.ts +0 -11
  326. package/typings/languages/ko.d.ts +0 -25
  327. package/typings/languages/lt.d.ts +0 -110
  328. package/typings/languages/lv.d.ts +0 -99
  329. package/typings/languages/mr.d.ts +0 -12
  330. package/typings/languages/ms.d.ts +0 -37
  331. package/typings/languages/nb.d.ts +0 -27
  332. package/typings/languages/nl.d.ts +0 -65
  333. package/typings/languages/pa-Guru.d.ts +0 -1
  334. package/typings/languages/pl.d.ts +0 -116
  335. package/typings/languages/pt.d.ts +0 -39
  336. package/typings/languages/ro.d.ts +0 -229
  337. package/typings/languages/ru.d.ts +0 -108
  338. package/typings/languages/sr-Latn.d.ts +0 -98
  339. package/typings/languages/sv.d.ts +0 -30
  340. package/typings/languages/sw.d.ts +0 -1
  341. package/typings/languages/ta.d.ts +0 -1
  342. package/typings/languages/te.d.ts +0 -1
  343. package/typings/languages/th.d.ts +0 -1
  344. package/typings/languages/tr.d.ts +0 -46
  345. package/typings/languages/uk.d.ts +0 -117
  346. package/typings/languages/ur.d.ts +0 -1
  347. package/typings/languages/vi.d.ts +0 -116
  348. package/typings/languages/zh-Hans.d.ts +0 -57
  349. package/typings/n2words.d.ts +0 -177
@@ -1,40 +1,19 @@
1
- import SlavicLanguage from '../classes/slavic-language.js'
2
-
3
- /**
4
- * @typedef {Object} SlavicOptions
5
- * @property {boolean} [feminine=false] Use feminine forms for numbers.
6
- */
1
+ import { SlavicLanguage } from '../classes/slavic-language.js'
7
2
 
8
3
  /**
9
4
  * Latvian language converter.
10
5
  *
11
- * Implements Latvian number words using the Slavic language pattern:
12
- * - Latvian number words (viens, divi, trīs, četri, pieci...)
13
- * - Latvian-specific pluralization patterns
14
- * - Baltic grammatical structure
15
- * - Simplified gender handling compared to Lithuanian
16
- *
17
- * Key Features:
18
- * - Three-form pluralization system shared across Slavic/Baltic languages
19
- * * Form 1 (singular): 1 (e.g., "tūkstotis")
20
- * * Form 2 (few): 2-4, 22-24, 32-34... excluding teens (e.g., "tūkstoši")
21
- * * Form 3 (many): all other numbers (e.g., "tūkstošu")
22
- * - Chunk-based decomposition (splits into groups of 3 digits: ones, thousands, millions, etc.)
23
- * - Large number handling via thousands[] array with indexed [singular, few, many] forms
24
- *
25
- * Features:
26
- * - Latvian diacritical marks (ī, ā, ē, ū, etc.)
27
- * - Three-form pluralization (adapted for Latvian)
28
- * - Baltic number naming conventions
6
+ * Supports:
7
+ * - Three-form pluralization (one/few/many)
8
+ * - Latvian diacritical marks (ī, ā, ē, ū)
29
9
  * - Compound number formation (divdesmit, trīsdesmit)
30
- *
31
- * Inherits from SlavicLanguage for pluralization algorithms.
32
10
  */
33
11
  export class Latvian extends SlavicLanguage {
34
12
  negativeWord = 'mīnus'
35
13
  decimalSeparatorWord = 'komats'
36
14
  zeroWord = 'nulle'
37
- ones = {
15
+
16
+ onesWords = {
38
17
  1: 'viens',
39
18
  2: 'divi',
40
19
  3: 'trīs',
@@ -46,7 +25,19 @@ export class Latvian extends SlavicLanguage {
46
25
  9: 'deviņi'
47
26
  }
48
27
 
49
- tens = {
28
+ onesFeminineWords = {
29
+ 1: 'viena',
30
+ 2: 'divas',
31
+ 3: 'trīs',
32
+ 4: 'četras',
33
+ 5: 'piecas',
34
+ 6: 'sešas',
35
+ 7: 'septiņas',
36
+ 8: 'astoņas',
37
+ 9: 'deviņas'
38
+ }
39
+
40
+ teensWords = {
50
41
  0: 'desmit',
51
42
  1: 'vienpadsmit',
52
43
  2: 'divpadsmit',
@@ -59,7 +50,7 @@ export class Latvian extends SlavicLanguage {
59
50
  9: 'deviņpadsmit'
60
51
  }
61
52
 
62
- twenties = {
53
+ twentiesWords = {
63
54
  2: 'divdesmit',
64
55
  3: 'trīsdesmit',
65
56
  4: 'četrdesmit',
@@ -70,9 +61,9 @@ export class Latvian extends SlavicLanguage {
70
61
  9: 'deviņdesmit'
71
62
  }
72
63
 
73
- hundreds = ['simts', 'simti', 'simtu']
64
+ hundredsWords = ['simts', 'simti', 'simtu']
74
65
 
75
- thousands = {
66
+ pluralForms = {
76
67
  1: ['tūkstotis', 'tūkstoši', 'tūkstošu'],
77
68
  2: ['miljons', 'miljoni', 'miljonu'],
78
69
  3: ['miljards', 'miljardi', 'miljardu'],
@@ -100,54 +91,40 @@ export class Latvian extends SlavicLanguage {
100
91
  return forms[1]
101
92
  }
102
93
 
103
- convertWholePart (number) {
104
- if (number === 0n) {
94
+ integerToWords (integerPart) {
95
+ if (integerPart === 0n) {
105
96
  return this.zeroWord
106
97
  }
107
98
  const words = []
108
- const chunks = this.splitByX(number.toString(), 3)
109
- let index = chunks.length
110
- for (const x of chunks) {
99
+ const segments = this.splitToSegments(integerPart.toString(), 3)
100
+ let index = segments.length
101
+ for (const x of segments) {
111
102
  index = index - 1
112
103
  if (x === 0n) {
113
104
  continue
114
105
  }
115
- const [n1, n2, n3] = this.getDigits(x)
106
+ const [n1, n2, n3] = this.extractDigits(x)
116
107
  if (n3 > 0n) {
117
108
  if (n3 === 1n && n2 === 0n && n1 > 0n) {
118
- words.push(this.hundreds[2])
109
+ words.push(this.hundredsWords[2])
119
110
  } else if (n3 > 1n) {
120
- words.push(this.ones[n3], this.hundreds[1])
111
+ words.push(this.onesWords[n3], this.hundredsWords[1])
121
112
  } else {
122
- words.push(this.hundreds[0])
113
+ words.push(this.hundredsWords[0])
123
114
  }
124
115
  }
125
116
  if (n2 > 1n) {
126
- words.push(this.twenties[n2])
117
+ words.push(this.twentiesWords[n2])
127
118
  }
128
119
  if (n2 === 1n) {
129
- words.push(this.tens[n1])
120
+ words.push(this.teensWords[n1])
130
121
  } else if (n1 > 0n && !(index > 0 && x === 1n)) {
131
- words.push(this.ones[n1])
122
+ words.push(this.onesWords[n1])
132
123
  }
133
124
  if (index > 0) {
134
- words.push(this.pluralize(x, this.thousands[index]))
125
+ words.push(this.pluralize(x, this.pluralForms[index]))
135
126
  }
136
127
  }
137
128
  return words.join(' ')
138
129
  }
139
130
  }
140
-
141
- /**
142
- * Converts a number to Latvian cardinal (written) form.
143
- *
144
- * @param {number|string|bigint} value The number to convert.
145
- * @param {Object} [options={}] Configuration options.
146
- * @param {boolean} [options.feminine=false] Use feminine forms for numbers.
147
- * @returns {string} The number expressed in Latvian words.
148
- * @throws {TypeError} If value is NaN or invalid type.
149
- * @throws {Error} If value is an invalid number string.
150
- */
151
- export default function convertToWords (value, options = {}) {
152
- return new Latvian(options).convertToWords(value)
153
- }
@@ -0,0 +1,11 @@
1
+ /**
2
+ * Marathi language converter.
3
+ *
4
+ * Supports:
5
+ * - Indian numbering system (हजार, लाख, कोटी)
6
+ * - Devanagari script
7
+ * - Complete word forms for 0-99
8
+ */
9
+ export class Marathi extends SouthAsianLanguage {
10
+ }
11
+ import { SouthAsianLanguage } from '../classes/south-asian-language.js';
@@ -1,30 +1,21 @@
1
- /**
2
- * Marathi language implementation for n2words
3
- *
4
- * Marathi uses Indian-style number grouping (3 digits, then 2-2 from right).
5
- * Numbers: शून्य (0), एक (1), दोन (2), तीन (3), चार (4), पाच (5)...
6
- *
7
- * @module lib/languages/mr
8
- * @example
9
- * import mr from './lib/languages/mr.js'
10
- * mr(42) // 'बेचाळीस'
11
- * mr(1000) // 'एक हजार'
12
- */
13
-
14
- import SouthAsianLanguage from '../classes/south-asian-language.js'
1
+ import { SouthAsianLanguage } from '../classes/south-asian-language.js'
15
2
 
16
3
  /**
17
- * Marathi language implementation
18
- * Extends SouthAsianLanguage for Indian-style grouping
4
+ * Marathi language converter.
5
+ *
6
+ * Supports:
7
+ * - Indian numbering system (हजार, लाख, कोटी)
8
+ * - Devanagari script
9
+ * - Complete word forms for 0-99
19
10
  */
20
- class MarathiLanguage extends SouthAsianLanguage {
11
+ export class Marathi extends SouthAsianLanguage {
21
12
  negativeWord = 'उणे'
22
13
  decimalSeparatorWord = 'दशांश'
23
14
  zeroWord = 'शून्य'
24
15
  hundredWord = 'शंभर'
25
- convertDecimalsPerDigit = true
16
+ usePerDigitDecimals = true
26
17
 
27
- belowHundred = [
18
+ belowHundredWords = [
28
19
  'शून्य',
29
20
  'एक',
30
21
  'दोन',
@@ -139,18 +130,3 @@ class MarathiLanguage extends SouthAsianLanguage {
139
130
  'शंकू'
140
131
  ]
141
132
  }
142
-
143
- /**
144
- * Convert a number to Marathi words
145
- *
146
- * @param {number|string|bigint} value - The number to convert
147
- * @param {Object} [options={}] - Conversion options
148
- * @returns {string} The Marathi word representation
149
- * @example
150
- * convertToWords(42) // 'बेचाळीस'
151
- * convertToWords(1000) // 'एक हजार'
152
- * convertToWords(100000) // 'एक लाख'
153
- */
154
- export default function convertToWords (value, options = {}) {
155
- return new MarathiLanguage(options).convertToWords(value)
156
- }
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Malay (Bahasa Melayu) language converter.
3
+ *
4
+ * Supports:
5
+ * - "Se-" prefix for singular units (seratus, seribu, sejuta)
6
+ * - Regular patterns (puluh for tens, ratus for hundreds)
7
+ * - Space-separated number components
8
+ */
9
+ export class Malay extends AbstractLanguage {
10
+ /**
11
+ * Word forms for digits 0-9.
12
+ * @type {Object.<number, string[]>}
13
+ */
14
+ digitWords: {
15
+ [x: number]: string[];
16
+ };
17
+ /**
18
+ * Scale magnitude words keyed by exponent (10^n).
19
+ * @type {Object.<number, string>}
20
+ */
21
+ scaleWords: {
22
+ [x: number]: string;
23
+ };
24
+ splitBy3(number: any): any[][];
25
+ spell(blocks: any): any[];
26
+ getHundreds(number: any): string[];
27
+ getTens(number: any): string[];
28
+ join(wordBlocks: any): string;
29
+ integerToWords(integerPart: any): string;
30
+ }
31
+ import { AbstractLanguage } from '../classes/abstract-language.js';
@@ -1,19 +1,23 @@
1
- import AbstractLanguage from '../classes/abstract-language.js'
1
+ import { AbstractLanguage } from '../classes/abstract-language.js'
2
2
 
3
3
  /**
4
4
  * Malay (Bahasa Melayu) language converter.
5
5
  *
6
- * Conventions:
7
- * - Base-10 structure
8
- * - "Se-" prefix for singular units (seratus, seribu, sejuta, sebilion, setrilion)
9
- * - Space-separated components (no conjunction like "dan" for tens/ones)
10
- * - Grouping by thousands (ribu, juta, bilion, trilion)
6
+ * Supports:
7
+ * - "Se-" prefix for singular units (seratus, seribu, sejuta)
8
+ * - Regular patterns (puluh for tens, ratus for hundreds)
9
+ * - Space-separated number components
11
10
  */
12
11
  export class Malay extends AbstractLanguage {
13
12
  negativeWord = 'minus'
14
13
  decimalSeparatorWord = 'perpuluhan'
15
14
  zeroWord = 'sifar'
16
- base = {
15
+
16
+ /**
17
+ * Word forms for digits 0-9.
18
+ * @type {Object.<number, string[]>}
19
+ */
20
+ digitWords = {
17
21
  0: [],
18
22
  1: ['satu'],
19
23
  2: ['dua'],
@@ -26,7 +30,11 @@ export class Malay extends AbstractLanguage {
26
30
  9: ['sembilan']
27
31
  }
28
32
 
29
- thousands = {
33
+ /**
34
+ * Scale magnitude words keyed by exponent (10^n).
35
+ * @type {Object.<number, string>}
36
+ */
37
+ scaleWords = {
30
38
  3: 'ribu',
31
39
  6: 'juta',
32
40
  9: 'bilion',
@@ -62,7 +70,7 @@ export class Malay extends AbstractLanguage {
62
70
  let spelling
63
71
  const firstBlock = blocks[0]
64
72
  if (firstBlock[0].length === 1) {
65
- spelling = firstBlock[0] === '0' ? ['sifar'] : this.base[Math.trunc(firstBlock[0])]
73
+ spelling = firstBlock[0] === '0' ? ['sifar'] : this.digitWords[Math.trunc(firstBlock[0])]
66
74
  } else if (firstBlock[0].length === 2) {
67
75
  spelling = this.getTens(firstBlock[0])
68
76
  } else {
@@ -84,7 +92,7 @@ export class Malay extends AbstractLanguage {
84
92
  } else if (number === '0') {
85
93
  return []
86
94
  } else {
87
- return [...this.base[Math.trunc(number)], 'ratus']
95
+ return [...this.digitWords[Math.trunc(number)], 'ratus']
88
96
  }
89
97
  }
90
98
 
@@ -95,14 +103,14 @@ export class Malay extends AbstractLanguage {
95
103
  } else if (number[1] === '1') {
96
104
  return ['sebelas']
97
105
  }
98
- return [...this.base[Math.trunc(number[1])], 'belas']
106
+ return [...this.digitWords[Math.trunc(number[1])], 'belas']
99
107
  }
100
108
 
101
109
  if (number[0] === '0') {
102
- return this.base[Math.trunc(number[1])]
110
+ return this.digitWords[Math.trunc(number[1])]
103
111
  }
104
112
 
105
- return [...this.base[Math.trunc(number[0])], 'puluh', ...this.base[Math.trunc(number[1])]]
113
+ return [...this.digitWords[Math.trunc(number[0])], 'puluh', ...this.digitWords[Math.trunc(number[1])]]
106
114
  }
107
115
 
108
116
  join (wordBlocks) {
@@ -112,7 +120,7 @@ export class Malay extends AbstractLanguage {
112
120
  for (let index = 0; index <= length; index++) {
113
121
  const words = wordBlocks[index][1]
114
122
  const isLast = index === length
115
- const scaleWord = isLast ? null : this.thousands[(length - index) * 3]
123
+ const scaleWord = isLast ? null : this.scaleWords[(length - index) * 3]
116
124
 
117
125
  if (!isLast && words.length === 1 && words[0] === 'satu') {
118
126
  // Use se- prefix for singular scale units: seribu, sejuta, sebilion, setrilion
@@ -132,15 +140,11 @@ export class Malay extends AbstractLanguage {
132
140
  return wordList.join(' ')
133
141
  }
134
142
 
135
- convertWholePart (number) {
143
+ integerToWords (integerPart) {
136
144
  return this.join(
137
145
  this.spell(
138
- this.splitBy3(number)
146
+ this.splitBy3(integerPart)
139
147
  )
140
148
  ).trim()
141
149
  }
142
150
  }
143
-
144
- export default function convertToWords (value, options = {}) {
145
- return new Malay(options).convertToWords(value)
146
- }
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Norwegian Bokmål language converter.
3
+ *
4
+ * Supports:
5
+ * - Hyphenation for compound numbers (tjue-en)
6
+ * - "og" (and) for hundreds combinations
7
+ * - Implicit '1' omission before tens and magnitudes
8
+ */
9
+ export class NorwegianBokmal extends GreedyScaleLanguage {
10
+ scaleWords: (string | bigint)[][];
11
+ }
12
+ import { GreedyScaleLanguage } from '../classes/greedy-scale-language.js';
@@ -1,29 +1,26 @@
1
- import GreedyScaleLanguage from '../classes/greedy-scale-language.js'
1
+ import { GreedyScaleLanguage } from '../classes/greedy-scale-language.js'
2
2
 
3
3
  /**
4
- * Norwegian language converter.
4
+ * Norwegian Bokmål language converter.
5
5
  *
6
- * GreedyScaleLanguage with inline Norwegian merge rules:
7
- * - Hyphenation for compound numbers (e.g., "tjueen")
6
+ * Supports:
7
+ * - Hyphenation for compound numbers (tjue-en)
8
8
  * - "og" (and) for hundreds combinations
9
- * - Comma separation for non-magnitude additions
10
- * - Implicit '1' before tens and magnitudes
11
- * - Space separators for large numbers
9
+ * - Implicit '1' omission before tens and magnitudes
12
10
  */
13
- export class Norwegian extends GreedyScaleLanguage {
11
+ export class NorwegianBokmal extends GreedyScaleLanguage {
14
12
  negativeWord = 'minus'
15
13
  decimalSeparatorWord = 'komma'
16
14
  zeroWord = 'null'
17
- scaleWordPairs = [
18
- [1_000_000_000_000_000_000_000_000_000_000_000n, 'quintillard'],
19
- [1_000_000_000_000_000_000_000_000_000_000n, 'quintillion'],
20
- [1_000_000_000_000_000_000_000_000_000n, 'quadrillard'],
21
- [1_000_000_000_000_000_000_000_000n, 'quadrillion'],
22
- [1_000_000_000_000_000_000_000n, 'trillard'],
23
- [1_000_000_000_000_000_000n, 'trillion'],
24
- [1_000_000_000_000_000n, 'billard'],
15
+
16
+ scaleWords = [
17
+ [1_000_000_000_000_000_000_000_000_000n, 'oktillion'],
18
+ [1_000_000_000_000_000_000_000_000n, 'septillion'],
19
+ [1_000_000_000_000_000_000_000n, 'sekstillion'],
20
+ [1_000_000_000_000_000_000n, 'kvintillion'],
21
+ [1_000_000_000_000_000n, 'kvadrillion'],
25
22
  [1_000_000_000_000n, 'billion'],
26
- [1_000_000_000n, 'millard'],
23
+ [1_000_000_000n, 'milliard'],
27
24
  [1_000_000n, 'million'],
28
25
  [1000n, 'tusen'],
29
26
  [100n, 'hundre'],
@@ -58,63 +55,46 @@ export class Norwegian extends GreedyScaleLanguage {
58
55
  ]
59
56
 
60
57
  /**
61
- * Merges two adjacent word-number pairs according to Norwegian grammar rules.
58
+ * Merges two adjacent word-sets according to Norwegian grammar rules.
62
59
  *
63
60
  * Norwegian-specific rules:
64
- * - Implicit \"en\": `mergeScales({ 'en': 1n }, { 'hundre': 100n })` → `{ 'hundre': 100n }`
65
- * - Hyphenation for compound tens: `mergeScales({ 'tjue': 20n }, { 'en': 1n })` → `{ 'tjue-en': 21n }`
66
- * - \"og\" (and) after hundreds: `mergeScales({ 'hundre': 100n }, { 'en': 1n })` → `{ 'hundre og en': 101n }`
61
+ * - Implicit "en": `combineWordSets({ 'en': 1n }, { 'hundre': 100n })` → `{ 'hundre': 100n }`
62
+ * - Hyphenation for compound tens: `combineWordSets({ 'tjue': 20n }, { 'en': 1n })` → `{ 'tjue-en': 21n }`
63
+ * - "og" (and) after hundreds: `combineWordSets({ 'hundre': 100n }, { 'en': 1n })` → `{ 'hundre og en': 101n }`
67
64
  * - Space-separated for large numbers (thousands+)
68
65
  * - Comma separator for non-magnitude additions (e.g., \"tusen, en\")
69
66
  *
70
- * @param {Object} leftPair The left operand as `{ word: BigInt }`.
71
- * @param {Object} rightPair The right operand as `{ word: BigInt }`.
67
+ * @param {Object} preceding The preceding word-set as `{ word: BigInt }`.
68
+ * @param {Object} following The following word-set as `{ word: BigInt }`.
72
69
  * @returns {Object} Merged pair with combined word and resulting numeric value.
73
70
  *
74
71
  * @example
75
- * mergeScales({ 'en': 1n }, { 'hundre': 100n }); // { 'hundre': 100n }
76
- * mergeScales({ 'tjue': 20n }, { 'tre': 3n }); // { 'tjue-tre': 23n }
72
+ * combineWordSets({ 'en': 1n }, { 'hundre': 100n }); // { 'hundre': 100n }
73
+ * combineWordSets({ 'tjue': 20n }, { 'tre': 3n }); // { 'tjue-tre': 23n }
77
74
  */
78
75
  // Norwegian merge rules mirror the former Scandinavian base logic
79
- mergeScales (leftPair, rightPair) {
80
- const leftWord = Object.keys(leftPair)[0]
81
- const rightWord = Object.keys(rightPair)[0]
82
- const leftNumber = Object.values(leftPair)[0]
83
- const rightNumber = Object.values(rightPair)[0]
76
+ combineWordSets (preceding, following) {
77
+ const precedingWord = Object.keys(preceding)[0]
78
+ const followingWord = Object.keys(following)[0]
79
+ const precedingValue = Object.values(preceding)[0]
80
+ const followingValue = Object.values(following)[0]
84
81
 
85
- if (leftNumber === 1n && rightNumber < 100n) {
86
- return rightPair
82
+ if (precedingValue === 1n && followingValue < 100n) {
83
+ return following
87
84
  }
88
85
 
89
- if (leftNumber < 100n && leftNumber > rightNumber) {
90
- return { [`${leftWord}-${rightWord}`]: leftNumber + rightNumber }
86
+ if (precedingValue < 100n && precedingValue > followingValue) {
87
+ return { [`${precedingWord}-${followingWord}`]: precedingValue + followingValue }
91
88
  }
92
89
 
93
- if (leftNumber >= 100n && rightNumber < 100n) {
94
- return { [`${leftWord} og ${rightWord}`]: leftNumber + rightNumber }
90
+ if (precedingValue >= 100n && followingValue < 100n) {
91
+ return { [`${precedingWord} og ${followingWord}`]: precedingValue + followingValue }
95
92
  }
96
93
 
97
- if (rightNumber > leftNumber) {
98
- return { [`${leftWord} ${rightWord}`]: leftNumber * rightNumber }
94
+ if (followingValue > precedingValue) {
95
+ return { [`${precedingWord} ${followingWord}`]: precedingValue * followingValue }
99
96
  }
100
97
 
101
- return { [`${leftWord}, ${rightWord}`]: leftNumber + rightNumber }
98
+ return { [`${precedingWord}, ${followingWord}`]: precedingValue + followingValue }
102
99
  }
103
100
  }
104
-
105
- /**
106
- * Converts a number to Norwegian cardinal (written) form.
107
- *
108
- * @param {number|string|bigint} value The number to convert.
109
- * @param {Object} [options] Conversion options (see Norwegian class options).
110
- * @returns {string} The number expressed in Norwegian words.
111
- * @throws {TypeError} If value is NaN or invalid type.
112
- * @throws {Error} If value is an invalid number string.
113
- *
114
- * @example
115
- * convertToWords(42); // 'førti-to'
116
- * convertToWords('1.5'); // 'en komma fem'
117
- */
118
- export default function convertToWords (value, options = {}) {
119
- return new Norwegian(options).convertToWords(value)
120
- }
@@ -0,0 +1,16 @@
1
+ /**
2
+ * Dutch language converter.
3
+ *
4
+ * Supports:
5
+ * - Optional "en" (and) separator for tens
6
+ * - Optional comma before hundreds
7
+ * - Compound word formation without hyphenation
8
+ */
9
+ export class Dutch extends GreedyScaleLanguage {
10
+ constructor(options?: {});
11
+ scaleWords: (string | bigint)[][];
12
+ /** Combines two word-sets according to Dutch grammar rules. */
13
+ combineWordSets(preceding: any, following: any): any;
14
+ integerToWords(integerPart: any): string;
15
+ }
16
+ import { GreedyScaleLanguage } from '../classes/greedy-scale-language.js';