Dynamic formatting numbers and inputs

Working with numbers often can be inconvenient if the number is big. 100000000 - what’s that? 10 million or 100 million? Or maybe 1 billion? Admit that 100,000,000 is much more visually friendly and understandable. Even working with ‘thousands’ we often want to format it for better readability. 100,000 is better than 100000.

This article aims to help developers how to format numbers and, in particular, numbers in inputs

Formatting numbers
There are 3 cool ways to format numbers:

  1. Number.prototype.toLocaleString()

  2. Intl.NumberFormat.prototype.format()

  3. Regular Expressions (RegExp)

1. Number.prototype.toLocaleString()

 const number = 400000000000;
 $w('#num').text = number.toLocaleString();

The result is 400,000,000,000

  1. Intl.NumberFormat.prototype.format()
    This method provides greater opportunities than the toLocaleString() method. It can format number in different ways

Example 1:

const num = 1000000000;
$w('#num').text = new Intl.NumberFormat().format(num);

The result is 1,000,000,000

Example 2:

const num = 746376433;
const body = {
      style: 'currency',
      currency: 'USD',
      maximumSignificantDigits: num2.toFixed().length // deletes decimals.
}
$w('#num').text = new Intl.NumberFormat('en-US', body).format(num);

The result is $746,376,433

Example 3:

const num = 299792458;
const options = {
      style: 'unit',
      unit: 'meter-per-second',
}
$w('#num').text = new Intl.NumberFormat('en-US', options).format(num);

The result is 299,792,458 m/s

  1. RegExp
    RegExp is a flexible way to format any number or text.
const num = 10000000;
$w('#num').text = String(num).replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,');

The result is 10,000,000

Now you know how to easily format numbers.

Formatting inputs
But what about inputs? Input type ‘number’ prohibits using commas. The right way is to set input type to ‘text’ and to add a RegExp to permit only numbers and certain symbols.
In our case we should allow only numbers, commas, minus (for negative numbers) and dots (for decimals).

You can use these RegExp examples (or set another on your way)

/[^0-9,.-]+/g  // allows numbers, comma, dot, minus.
/[^0-9]+/g -  // allows only numbers
/\D+/g -  // allows only numbers (another way)

Now combine character prohibition in inputs and number formatting:
Example 1:

const input = $w('#input');
input.onInput( () => {
       input.value = input.value.replace(/[^0-9,.-]+/g, '');
       input.value = input.value.split(',').join('').replace(/(\d)(?=(\d{3})+(?!\d))/g, '$1,')
})

Example 2:

const input = $w('#input');
input.onInput( () => {
     input.value = input.value.replace(/[^0-9,.-]+/g, '');
     input.value = new Intl.NumberFormat().format(+input.value.split(',').join(''));
})

Catch this

RegExp is more flexible because you can easily change the delimiter. Just change ‘$1,’ to ‘$1 ’ in the replace() method and don’t forget to change the delimiter in split(’,‘) to split(’ '). And the ‘comma’ delimiter turns to ‘space’.

Finally learn more by reading documentation about these API on MDN or any other websites.
Good luck, guys :slight_smile:

1 Like

Nice post Vlad. But Regex? Seriously? You’re just trying to show off. :beers:

Not at all :slight_smile:
This is the good way to provide any delimiter to a number you want, I guess.
For example, need to replace 10000 to 10_000 or 10’000 ? RegExp is the simplest way.

@vladkl I know - I also use regex. It’s just that it gives me a headache.
Again - really nice post. This will help a lot of people.

@vladkl

The following code works great for me. Is there a way to add a “$” (Ex. $100,000)

Also, is there a way to add a decimal point . (ex. $100,000.00 and $100.00)

const input = $w ( ‘#input195’ );
input . onInput ( () => {
input . value = input . value . replace ( /[^0-9,.-]+/ g , ‘’ );
input . value = new Intl . NumberFormat (). format (+ input . value . split ( ‘,’ ). join ( ‘’ ));
})

Thanks for any ideas and help.

Hello Miguel.
For this simple task you can use new Intl constructor. No necessity to dive deep into regExp

let number = 123456789 ;
let formatted = new Intl . NumberFormat ( ‘en’ , {
style : ‘currency’ ,
currency : ‘USD’ ,
maximumFractionDigits : ‘0’
}). format ( number );

console . log ( formatted ) // $123,456,789

If you want to get $123,456,789.00 - just delete or change maximumFractionDigits property (it stands for fraction digits)

@vladkl

Thanks. I’ll try this out. Appreciate your response.