diff --git a/README.md b/README.md index cbf8652..641adc0 100644 --- a/README.md +++ b/README.md @@ -2,106 +2,148 @@ Написание числительных на русском языке с учётом пола и падежа. -# Установка +## Использование в NodeJS ``` npm install --save numeralize-ru ``` -# API +```javascript +import {numeralize, Case, Gender} from "numeralize-ru"; -### `numeralize(number, [gender, [kase, [animate]]])` - -Возвращает числительное, соответствующее числу - -+ `number` — число, для которого надо записать числительное; -+ `gender` — пол: - + `Gender.Masculine` — мужской (по умолчанию); - + `Gender.Feminine` — женский; - + `Gender.Neuter` — средний; -+ `kase` — падеж (`case` является ключевым словом, поэтому не может быть использован в качестве имени переменной): - + `Case.Nominative` — именительный (по умолчанию); - + `Case.Genitive` — родительный; - + `Case.Dative` — дательный; - + `Case.Accusative` — винительный; - + `Case.Instrumental` — творительный; - + `Case.Prepositional` — предложный; -+ `animate` — являются ли перечисляемые предметы одушевлёнными (влияет на форму винительного падежа некоторых числительных) - -```typescript -import {Case, Gender, numeralize, pluralize} from 'numeralize-ru'; - -numeralize(5122981121); -// мужской род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' - -numeralize(5122981121, Gender.Feminine); -// женский род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одна' - -numeralize(5122981121, Gender.Neuter); -// средний род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одно' - -numeralize(5122981121, Gender.Masculine, Case.Nominative); -// мужской род, именительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' - -numeralize(5122981121, Gender.Masculine, Case.Genitive); -// мужской род, родительный падеж, 'пяти миллиардов ста двадцати двух миллионов девятисот восьмидесяти одной тысячи ста двадцати одного' - -numeralize(5122981121, Gender.Masculine, Case.Dative); -// мужской род, дательный падеж, 'пяти миллиардам ста двадцати двум миллионам девятистам восьмидесяти одной тысяче ста двадцати одному' - -numeralize(5122981121, Gender.Masculine, Case.Accusative); -// мужской род, винительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать один' - -numeralize(5122981121, Gender.Masculine, Case.Accusative, true); -// мужской род, винительный падеж, одушевлённые предметы, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать одного' - -numeralize(5122981121, Gender.Masculine, Case.Instrumental); -// мужской род, творительный падеж, 'пятью миллиардами ста двадцатью двумя миллионами девятьюстами восемьюдесятью одной тысячей ста двадцатью одним' - -numeralize(5122981121, Gender.Masculine, Case.Prepositional); -// мужской род, творительный падеж, 'пяти миллиардах ста двадцати двух миллионах девятистах восьмидесяти одной тысяче ста двадцати одном' +console.log(numeralize(5122981121, Gender.Masculine, Case.Nominative)); ``` -### `pluralize(count, one, two, five)` +## Использование с [дореволюционных](https://caniuse.com/?search=ESM) браузерах -Выбирает нужную форму существительного в зависимости от количества. - -+ `count` — количество -+ `one` — форма существительного для одного предмета, например, _рубль_; -+ `two` — форма существительного для двух предметов, например, _рубля_; -+ `five` — форма существительного для пяти предметов, например, _рублей_; - -```typescript -import {pluralize} from 'numeralize-ru'; - -pluralize(0, 'рубль', 'рубля', 'рублей'); -// 'рублей' - -pluralize(1, 'рубль', 'рубля', 'рублей'); -// 'рубль' - -pluralize(2, 'рубль', 'рубля', 'рублей'); -// 'рубля' - -pluralize(5, 'рубль', 'рубля', 'рублей'); -// 'рублей' - -pluralize(11, 'рубль', 'рубля', 'рублей'); -// 'рублей' - -pluralize(21, 'рубль', 'рубля', 'рублей'); -// 'рубль' - -pluralize(22, 'рубль', 'рубля', 'рублей'); -// 'рубля' +```html + + ``` -# Roadmap +## API -+ Порядковые числительные (ordinal numerals): _первый_, _вторым_, _третьими_ и т.д. -+ Собирательные числительные (collective numerals): _трое_, _четверых_, _пятерыми_ и т.д. -+ Особые формы единственного и множественного числа: _одни сутки_, _два дня_, _пять суток_ и т.д. +```typescript +/** + * Возвращает числительное, соответствующее числу + * + * @param {number} number Целое число, для которого надо записать числительное + * + * @param {Gender} [gender=Gender.Masculine] Пол: + * - {@link Gender.Masculine} – мужской (по умолчанию); + * - {@link Gender.Feminine} – женский; + * - {@link Gender.Neuter} – средний. + * + * @param {Case} [kase=Case.Nominative] Падеж + * (`case` является ключевым словом, поэтому не может быть использован в качестве имени переменной): + * - {@link Case.Nominative} — именительный (по умолчанию); + * - {@link Case.Genitive} — родительный; + * - {@link Case.Dative} — дательный; + * - {@link Case.Accusative} — винительный; + * - {@link Case.Instrumental} — творительный; + * - {@link Case.Prepositional} — предложный. + * + * @param {boolean} [animate=false] Являются ли перечисляемые предметы одушевлёнными + * (влияет на форму винительного падежа некоторых числительных) + * + * @example + * // мужской род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' + * numeralize(5122981121); + * + * @example + * // женский род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одна' + * numeralize(5122981121, Gender.Feminine); + * + * @example + * // средний род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одно' + * numeralize(5122981121, Gender.Neuter); + * + * @example + * // мужской род, именительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' + * numeralize(5122981121, Gender.Masculine, Case.Nominative); + * + * @example + * // мужской род, родительный падеж, 'пяти миллиардов ста двадцати двух миллионов девятисот восьмидесяти одной тысячи ста двадцати одного' + * numeralize(5122981121, Gender.Masculine, Case.Genitive); + * + * @example + * // мужской род, дательный падеж, 'пяти миллиардам ста двадцати двум миллионам девятистам восьмидесяти одной тысяче ста двадцати одному' + * numeralize(5122981121, Gender.Masculine, Case.Dative); + * + * @example + * // мужской род, винительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать один' + * numeralize(5122981121, Gender.Masculine, Case.Accusative); + * + * @example + * // мужской род, винительный падеж, одушевлённые предметы, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать одного' + * numeralize(5122981121, Gender.Masculine, Case.Accusative, true); + * + * @example + * // мужской род, творительный падеж, 'пятью миллиардами ста двадцатью двумя миллионами девятьюстами восемьюдесятью одной тысячей ста двадцатью одним' + * numeralize(5122981121, Gender.Masculine, Case.Instrumental); + * + * @example + * // мужской род, творительный падеж, 'пяти миллиардах ста двадцати двух миллионах девятистах восьмидесяти одной тысяче ста двадцати одном' + * numeralize(5122981121, Gender.Masculine, Case.Prepositional); + */ +declare function numeralize( + number: number, + gender: Gender = Gender.Masculine, + kase: Case = Case.Nominative, + animate: boolean = false +): string; -# См.также +/** + * Выбирает нужную форму существительного в зависимости от количества. + * + * @param {number} count Количество + * @param {string} one Форма существительного для одного предмета, например, «рубль»; + * @param {string} two Форма существительного для двух предметов, например, «рубля»; + * @param {string} five Форма существительного для пяти предмета, например, «рублей»; + * + * @example + * // 'рублей' + * pluralize(0, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубль' + * pluralize(1, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубля' + * pluralize(2, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рублей' + * pluralize(5, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рублей' + * pluralize(11, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубль' + * pluralize(21, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубля' + * pluralize(22, 'рубль', 'рубля', 'рублей'); + */ +declare function pluralize(count: number, one: string, two: string, five: string): string +``` + +## Спонсорство + +[Стать первым спонсором проекта](https://github.com/sponsors/anotherpit) + +## Roadmap + ++ [ ] Порядковые числительные (ordinal numerals): _первый_, _вторым_, _третьими_ и т.д. ++ [ ] Собирательные числительные (collective numerals): _трое_, _четверых_, _пятерыми_ и т.д. ++ [ ] Особые формы единственного и множественного числа: _одни сутки_, _два дня_, _пять суток_ и т.д. + +## См.также + Подробно о склонении числительных в русском языке с примерами: http://numeralonline.ru/ diff --git a/package-lock.json b/package-lock.json index cbd4bcf..092ef43 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,17 +1,18 @@ { "name": "numeralize-ru", - "version": "2.0.0", + "version": "2.0.0-alpha.1", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "numeralize-ru", - "version": "2.0.0", + "version": "2.0.0-alpha.1", "license": "MIT", "devDependencies": { "@types/mocha": "^10.0.2", "@typescript-eslint/eslint-plugin": "^6.8.0", "@typescript-eslint/parser": "^6.8.0", + "esbuild": "^0.19.5", "eslint": "^8.51.0", "mocha": "^10.2.0", "ts-mocha": "^10.0.0", @@ -40,6 +41,358 @@ "node": ">=12" } }, + "node_modules/@esbuild/android-arm": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm/-/android-arm-0.19.5.tgz", + "integrity": "sha512-bhvbzWFF3CwMs5tbjf3ObfGqbl/17ict2/uwOSfr3wmxDE6VdS2GqY/FuzIPe0q0bdhj65zQsvqfArI9MY6+AA==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/android-arm64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-arm64/-/android-arm64-0.19.5.tgz", + "integrity": "sha512-5d1OkoJxnYQfmC+Zd8NBFjkhyCNYwM4n9ODrycTFY6Jk1IGiZ+tjVJDDSwDt77nK+tfpGP4T50iMtVi4dEGzhQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/android-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/android-x64/-/android-x64-0.19.5.tgz", + "integrity": "sha512-9t+28jHGL7uBdkBjL90QFxe7DVA+KGqWlHCF8ChTKyaKO//VLuoBricQCgwhOjA1/qOczsw843Fy4cbs4H3DVA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "android" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/darwin-arm64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-arm64/-/darwin-arm64-0.19.5.tgz", + "integrity": "sha512-mvXGcKqqIqyKoxq26qEDPHJuBYUA5KizJncKOAf9eJQez+L9O+KfvNFu6nl7SCZ/gFb2QPaRqqmG0doSWlgkqw==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/darwin-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/darwin-x64/-/darwin-x64-0.19.5.tgz", + "integrity": "sha512-Ly8cn6fGLNet19s0X4unjcniX24I0RqjPv+kurpXabZYSXGM4Pwpmf85WHJN3lAgB8GSth7s5A0r856S+4DyiA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/freebsd-arm64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-arm64/-/freebsd-arm64-0.19.5.tgz", + "integrity": "sha512-GGDNnPWTmWE+DMchq1W8Sd0mUkL+APvJg3b11klSGUDvRXh70JqLAO56tubmq1s2cgpVCSKYywEiKBfju8JztQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/freebsd-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/freebsd-x64/-/freebsd-x64-0.19.5.tgz", + "integrity": "sha512-1CCwDHnSSoA0HNwdfoNY0jLfJpd7ygaLAp5EHFos3VWJCRX9DMwWODf96s9TSse39Br7oOTLryRVmBoFwXbuuQ==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "freebsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-arm": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm/-/linux-arm-0.19.5.tgz", + "integrity": "sha512-lrWXLY/vJBzCPC51QN0HM71uWgIEpGSjSZZADQhq7DKhPcI6NH1IdzjfHkDQws2oNpJKpR13kv7/pFHBbDQDwQ==", + "cpu": [ + "arm" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-arm64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-arm64/-/linux-arm64-0.19.5.tgz", + "integrity": "sha512-o3vYippBmSrjjQUCEEiTZ2l+4yC0pVJD/Dl57WfPwwlvFkrxoSO7rmBZFii6kQB3Wrn/6GwJUPLU5t52eq2meA==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-ia32": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ia32/-/linux-ia32-0.19.5.tgz", + "integrity": "sha512-MkjHXS03AXAkNp1KKkhSKPOCYztRtK+KXDNkBa6P78F8Bw0ynknCSClO/ztGszILZtyO/lVKpa7MolbBZ6oJtQ==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-loong64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-loong64/-/linux-loong64-0.19.5.tgz", + "integrity": "sha512-42GwZMm5oYOD/JHqHska3Jg0r+XFb/fdZRX+WjADm3nLWLcIsN27YKtqxzQmGNJgu0AyXg4HtcSK9HuOk3v1Dw==", + "cpu": [ + "loong64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-mips64el": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-mips64el/-/linux-mips64el-0.19.5.tgz", + "integrity": "sha512-kcjndCSMitUuPJobWCnwQ9lLjiLZUR3QLQmlgaBfMX23UEa7ZOrtufnRds+6WZtIS9HdTXqND4yH8NLoVVIkcg==", + "cpu": [ + "mips64el" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-ppc64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-ppc64/-/linux-ppc64-0.19.5.tgz", + "integrity": "sha512-yJAxJfHVm0ZbsiljbtFFP1BQKLc8kUF6+17tjQ78QjqjAQDnhULWiTA6u0FCDmYT1oOKS9PzZ2z0aBI+Mcyj7Q==", + "cpu": [ + "ppc64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-riscv64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-riscv64/-/linux-riscv64-0.19.5.tgz", + "integrity": "sha512-5u8cIR/t3gaD6ad3wNt1MNRstAZO+aNyBxu2We8X31bA8XUNyamTVQwLDA1SLoPCUehNCymhBhK3Qim1433Zag==", + "cpu": [ + "riscv64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-s390x": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-s390x/-/linux-s390x-0.19.5.tgz", + "integrity": "sha512-Z6JrMyEw/EmZBD/OFEFpb+gao9xJ59ATsoTNlj39jVBbXqoZm4Xntu6wVmGPB/OATi1uk/DB+yeDPv2E8PqZGw==", + "cpu": [ + "s390x" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/linux-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/linux-x64/-/linux-x64-0.19.5.tgz", + "integrity": "sha512-psagl+2RlK1z8zWZOmVdImisMtrUxvwereIdyJTmtmHahJTKb64pAcqoPlx6CewPdvGvUKe2Jw+0Z/0qhSbG1A==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "linux" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/netbsd-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/netbsd-x64/-/netbsd-x64-0.19.5.tgz", + "integrity": "sha512-kL2l+xScnAy/E/3119OggX8SrWyBEcqAh8aOY1gr4gPvw76la2GlD4Ymf832UCVbmuWeTf2adkZDK+h0Z/fB4g==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "netbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/openbsd-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/openbsd-x64/-/openbsd-x64-0.19.5.tgz", + "integrity": "sha512-sPOfhtzFufQfTBgRnE1DIJjzsXukKSvZxloZbkJDG383q0awVAq600pc1nfqBcl0ice/WN9p4qLc39WhBShRTA==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "openbsd" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/sunos-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/sunos-x64/-/sunos-x64-0.19.5.tgz", + "integrity": "sha512-dGZkBXaafuKLpDSjKcB0ax0FL36YXCvJNnztjKV+6CO82tTYVDSH2lifitJ29jxRMoUhgkg9a+VA/B03WK5lcg==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "sunos" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-arm64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-arm64/-/win32-arm64-0.19.5.tgz", + "integrity": "sha512-dWVjD9y03ilhdRQ6Xig1NWNgfLtf2o/STKTS+eZuF90fI2BhbwD6WlaiCGKptlqXlURVB5AUOxUj09LuwKGDTg==", + "cpu": [ + "arm64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-ia32": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-ia32/-/win32-ia32-0.19.5.tgz", + "integrity": "sha512-4liggWIA4oDgUxqpZwrDhmEfAH4d0iljanDOK7AnVU89T6CzHon/ony8C5LeOdfgx60x5cnQJFZwEydVlYx4iw==", + "cpu": [ + "ia32" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, + "node_modules/@esbuild/win32-x64": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/@esbuild/win32-x64/-/win32-x64-0.19.5.tgz", + "integrity": "sha512-czTrygUsB/jlM8qEW5MD8bgYU2Xg14lo6kBDXW6HdxKjh8M5PzETGiSHaz9MtbXBYDloHNUAUW2tMiKW4KM9Mw==", + "cpu": [ + "x64" + ], + "dev": true, + "optional": true, + "os": [ + "win32" + ], + "engines": { + "node": ">=12" + } + }, "node_modules/@eslint-community/eslint-utils": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/@eslint-community/eslint-utils/-/eslint-utils-4.4.0.tgz", @@ -855,6 +1208,43 @@ "integrity": "sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==", "dev": true }, + "node_modules/esbuild": { + "version": "0.19.5", + "resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.19.5.tgz", + "integrity": "sha512-bUxalY7b1g8vNhQKdB24QDmHeY4V4tw/s6Ak5z+jJX9laP5MoQseTOMemAr0gxssjNcH0MCViG8ONI2kksvfFQ==", + "dev": true, + "hasInstallScript": true, + "bin": { + "esbuild": "bin/esbuild" + }, + "engines": { + "node": ">=12" + }, + "optionalDependencies": { + "@esbuild/android-arm": "0.19.5", + "@esbuild/android-arm64": "0.19.5", + "@esbuild/android-x64": "0.19.5", + "@esbuild/darwin-arm64": "0.19.5", + "@esbuild/darwin-x64": "0.19.5", + "@esbuild/freebsd-arm64": "0.19.5", + "@esbuild/freebsd-x64": "0.19.5", + "@esbuild/linux-arm": "0.19.5", + "@esbuild/linux-arm64": "0.19.5", + "@esbuild/linux-ia32": "0.19.5", + "@esbuild/linux-loong64": "0.19.5", + "@esbuild/linux-mips64el": "0.19.5", + "@esbuild/linux-ppc64": "0.19.5", + "@esbuild/linux-riscv64": "0.19.5", + "@esbuild/linux-s390x": "0.19.5", + "@esbuild/linux-x64": "0.19.5", + "@esbuild/netbsd-x64": "0.19.5", + "@esbuild/openbsd-x64": "0.19.5", + "@esbuild/sunos-x64": "0.19.5", + "@esbuild/win32-arm64": "0.19.5", + "@esbuild/win32-ia32": "0.19.5", + "@esbuild/win32-x64": "0.19.5" + } + }, "node_modules/escalade": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/escalade/-/escalade-3.1.1.tgz", diff --git a/package.json b/package.json index e1f3f02..d79228f 100644 --- a/package.json +++ b/package.json @@ -1,17 +1,18 @@ { "name": "numeralize-ru", - "version": "2.0.0-alpha.1", + "version": "2.0.0-alpha.2", "description": "Russian numerals", "type": "module", "exports": { ".": { - "types": "./lib/types/index.d.ts", - "require": "./lib/cjs/index.js", - "import": "./lib/esm/index.js", - "default": "./lib/esm/index.js" + "types": "./lib/index.d.ts", + "require": "./lib/index.js", + "import": "./lib/index.js", + "default": "./lib/index.js", + "browser": "./lib/index.browser.js" } }, - "main": "lib/cjs/index.js", + "main": "lib/index.js", "files": [ "lib/", "LICENSE.md", @@ -22,7 +23,7 @@ "dev": "ts-mocha src/**.spec.ts -w --watch-files 'src/**.ts'", "test": "ts-mocha src/**.spec.ts", "lint": "eslint src/*", - "build": "rm -rf ./lib && tsc --build ./tsconfig.amd.json ./tsconfig.cjs.json ./tsconfig.esm.json ./tsconfig.types.json ./tsconfig.umd.json", + "build": "rm -rf ./lib && tsc --build && esbuild ./lib/index.js --outfile=lib/index.browser.js --format=iife --global-name=numeralize", "prepublish": "npm run lint && npm run test && npm run build" }, "keywords": [ @@ -42,6 +43,7 @@ "@types/mocha": "^10.0.2", "@typescript-eslint/eslint-plugin": "^6.8.0", "@typescript-eslint/parser": "^6.8.0", + "esbuild": "^0.19.5", "eslint": "^8.51.0", "mocha": "^10.2.0", "ts-mocha": "^10.0.0", diff --git a/src/index.spec.ts b/src/index.spec.ts index cf4b32c..1f7010c 100644 --- a/src/index.spec.ts +++ b/src/index.spec.ts @@ -1,4 +1,4 @@ -import {Case, Gender, numeralize} from "./index"; +import {numeralize, Gender, Case} from "./index"; import * as assert from "assert"; describe(numeralize.name, () => { diff --git a/src/index.ts b/src/index.ts index 5dc8254..a1512b4 100644 --- a/src/index.ts +++ b/src/index.ts @@ -112,24 +112,6 @@ const LARGES = [ ) ] as const; -/** - * Pluralize noun according to count, e.g. `pluralize(42, 'рубль', 'рубля', 'рублей')` - */ -export function pluralize(count: number, one: string, two: string, five: string): string { - count = Math.floor(Math.abs(count)) % 100; - if (count > 10 && count < 20) { - return five; - } - count = count % 10; - if (1 === count) { - return one; - } - if (count >= 2 && count <= 4) { - return two; - } - return five; -} - function small(number: number, gender: Gender, kase: Case, animate: boolean): string { // Zero if (0 === number) { @@ -172,7 +154,117 @@ function small(number: number, gender: Gender, kase: Case, animate: boolean): st } /** - * Numeralize number + * Выбирает нужную форму существительного в зависимости от количества. + * + * @param {number} count Количество + * @param {string} one Форма существительного для одного предмета, например, «рубль»; + * @param {string} two Форма существительного для двух предметов, например, «рубля»; + * @param {string} five Форма существительного для пяти предмета, например, «рублей»; + * + * @example + * // 'рублей' + * pluralize(0, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубль' + * pluralize(1, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубля' + * pluralize(2, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рублей' + * pluralize(5, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рублей' + * pluralize(11, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубль' + * pluralize(21, 'рубль', 'рубля', 'рублей'); + * + * @example + * // 'рубля' + * pluralize(22, 'рубль', 'рубля', 'рублей'); + */ +export function pluralize(count: number, one: string, two: string, five: string): string { + count = Math.floor(Math.abs(count)) % 100; + if (count > 10 && count < 20) { + return five; + } + count = count % 10; + if (1 === count) { + return one; + } + if (count >= 2 && count <= 4) { + return two; + } + return five; +} + +/** + * Возвращает числительное, соответствующее числу + * + * @param {number} number Целое число, для которого надо записать числительное + * + * @param {Gender} [gender=Gender.Masculine] Пол: + * - {@link Gender.Masculine} – мужской (по умолчанию); + * - {@link Gender.Feminine} – женский; + * - {@link Gender.Neuter} – средний. + * + * @param {Case} [kase=Case.Nominative] Падеж + * (`case` является ключевым словом, поэтому не может быть использован в качестве имени переменной): + * - {@link Case.Nominative} — именительный (по умолчанию); + * - {@link Case.Genitive} — родительный; + * - {@link Case.Dative} — дательный; + * - {@link Case.Accusative} — винительный; + * - {@link Case.Instrumental} — творительный; + * - {@link Case.Prepositional} — предложный. + * + * @param {boolean} [animate=false] Являются ли перечисляемые предметы одушевлёнными + * (влияет на форму винительного падежа некоторых числительных) + * + * @example + * // мужской род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' + * numeralize(5122981121); + * + * @example + * // женский род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одна' + * numeralize(5122981121, Gender.Feminine); + * + * @example + * // средний род, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать одно' + * numeralize(5122981121, Gender.Neuter); + * + * @example + * // мужской род, именительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одна тысяча сто двадцать один' + * numeralize(5122981121, Gender.Masculine, Case.Nominative); + * + * @example + * // мужской род, родительный падеж, 'пяти миллиардов ста двадцати двух миллионов девятисот восьмидесяти одной тысячи ста двадцати одного' + * numeralize(5122981121, Gender.Masculine, Case.Genitive); + * + * @example + * // мужской род, дательный падеж, 'пяти миллиардам ста двадцати двум миллионам девятистам восьмидесяти одной тысяче ста двадцати одному' + * numeralize(5122981121, Gender.Masculine, Case.Dative); + * + * @example + * // мужской род, винительный падеж, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать один' + * numeralize(5122981121, Gender.Masculine, Case.Accusative); + * + * @example + * // мужской род, винительный падеж, одушевлённые предметы, 'пять миллиардов сто двадцать два миллиона девятьсот восемьдесят одну тысячу сто двадцать одного' + * numeralize(5122981121, Gender.Masculine, Case.Accusative, true); + * + * @example + * // мужской род, творительный падеж, 'пятью миллиардами ста двадцатью двумя миллионами девятьюстами восемьюдесятью одной тысячей ста двадцатью одним' + * numeralize(5122981121, Gender.Masculine, Case.Instrumental); + * + * @example + * // мужской род, творительный падеж, 'пяти миллиардах ста двадцати двух миллионах девятистах восьмидесяти одной тысяче ста двадцати одном' + * numeralize(5122981121, Gender.Masculine, Case.Prepositional); */ export function numeralize( number: number, @@ -214,3 +306,4 @@ export function numeralize( // Return return result.join(' '); } + diff --git a/tsconfig.amd.json b/tsconfig.amd.json deleted file mode 100644 index 3da5dc2..0000000 --- a/tsconfig.amd.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "module": "umd", - "outDir": "./lib/amd/" - } -} diff --git a/tsconfig.cjs.json b/tsconfig.cjs.json deleted file mode 100644 index 8e7e7ed..0000000 --- a/tsconfig.cjs.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "module": "commonjs", - "outDir": "./lib/cjs/" - } -} diff --git a/tsconfig.esm.json b/tsconfig.esm.json deleted file mode 100644 index e628341..0000000 --- a/tsconfig.esm.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "module": "es2020", - "outDir": "./lib/esm/" - } -} diff --git a/tsconfig.json b/tsconfig.json index 1abb26b..4e7a1e2 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -46,13 +46,13 @@ // "maxNodeModuleJsDepth": 1, /* Specify the maximum folder depth used for checking JavaScript files from 'node_modules'. Only applicable with 'allowJs'. */ /* Emit */ - "declaration": false, + "declaration": true, /* Generate .d.ts files from TypeScript and JavaScript files in your project. */ // "declarationMap": true, /* Create sourcemaps for d.ts files. */ // "emitDeclarationOnly": true, /* Only output d.ts files and not JavaScript files. */ // "sourceMap": true, /* Create source map files for emitted JavaScript files. */ // "outFile": "./", /* Specify a file that bundles all outputs into one JavaScript file. If 'declaration' is true, also designates a file that bundles all .d.ts output. */ - // "outDir": "./", /* Specify an output folder for all emitted files. */ + "outDir": "./lib", /* Specify an output folder for all emitted files. */ // "removeComments": true, /* Disable emitting comments. */ // "noEmit": true, /* Disable emitting files from a compilation. */ // "importHelpers": true, /* Allow importing helper functions from tslib once per project, instead of including them per-file. */ diff --git a/tsconfig.types.json b/tsconfig.types.json deleted file mode 100644 index 4cc6da9..0000000 --- a/tsconfig.types.json +++ /dev/null @@ -1,8 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "outDir": "./lib/types", - "declaration": true, - "emitDeclarationOnly": true - } -} diff --git a/tsconfig.umd.json b/tsconfig.umd.json deleted file mode 100644 index d4c3e72..0000000 --- a/tsconfig.umd.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "extends": "./tsconfig.json", - "compilerOptions": { - "module": "umd", - "outDir": "./lib/umd/" - } -}