UNPKG

@canutin/svelte-currency-input

Version:

A fully-featured currency input component for Svelte 5 that handles formatting, localization, and validation

33 lines (32 loc) 1.57 kB
import { escapeRegExp } from './escapeRegExp'; export const abbrValue = (value, decimalSeparator = '.', _decimalPlaces = 10) => { if (value > 999) { let valueLength = ('' + value).length; const p = Math.pow; const d = p(10, _decimalPlaces); valueLength -= valueLength % 3; const abbrValue = Math.round((value * d) / p(10, valueLength)) / d + ' kMGTPE'[valueLength / 3]; return abbrValue.replace('.', decimalSeparator); } return String(value); }; const abbrMap = { k: 1000, m: 1000000, b: 1000000000 }; export const parseAbbrValue = (value, decimalSeparator = '.') => { const reg = new RegExp(`(\\d+(${escapeRegExp(decimalSeparator)}\\d*)?)([kmb])$`, 'i'); const match = value.match(reg); if (match) { const [, digits, , abbr] = match; const multiplier = abbrMap[abbr.toLowerCase()]; const result = Number(digits.replace(decimalSeparator, '.')) * multiplier; // Round based on input precision to avoid floating-point errors // e.g. 4.1 * 1000000 = 4099999.9999999995 should become 4100000 // but 1.12345678 * 1000 = 1123.45678 should preserve all decimals const decimalPart = digits.split(decimalSeparator)[1] || ''; const inputDecimals = decimalPart.length; const multiplierZeros = Math.log10(multiplier); const resultDecimals = Math.max(0, inputDecimals - multiplierZeros); const precision = Math.pow(10, resultDecimals); return Math.round(result * precision) / precision; } return undefined; };