Formatando números e moedas com toLocaleString()

vanribeiro

Van Ribeiro

Posted on March 21, 2022

Formatando números e moedas com toLocaleString()

O método Number.prototype.toLocaleString() permite formatar um número de acordo com a nacionalidade desejada. A partir de uma entrada do tipo number, ele devolve uma string com a formatação padrão ou a que foi definida através das opções disponíveis.

Conteúdo:

  1. Números
    1. Estilo decimal
      1. Separadores de milhar
        1. Desabilitando separadores de milhar
      2. Inteiros e dígitos fracionados (casas decimais)
        1. minimumIntegerDigits
        2. minimumFractionDigits
        3. maximumFractionDigits
        4. minimumSignificantDigits
        5. maximumSignificantDigits
    2. Estilo percent
      1. Exibir valores entre 0% e 100%, onde 100% não está incluso
      2. Exibir valores maiores ou iguais a 100%
    3. Estilo currency
      1. A opção currencyDisplay
  2. Limitações
  3. Conclusão
  4. Links para consulta

Números

Para o método Number.prototype.toLocaleString() são aceitos três estilos de formatação:

  • decimal (default): para números simples
  • percent: para porcentagem
  • currency: para valores monetários

Estilo decimal

É o valor padrão e está definido de forma implícita.

Separadores de milhar

Podemos definir os separadores de milhar de acordo com a localidade do ambiente atual de hospedagem:

const brazilPopulation = 213317639; 
brazilPopulation.toLocaleString();
// Output: "213.317.639"
Enter fullscreen mode Exit fullscreen mode

Mas, se quisermos especificar de qual país queremos a formatação, basta passar uma string com a tag da linguagem de acordo com a BCP 47 para qual desejamos formatar.

Geralmente, essa tag é composta de uma ou mais subtags, sendo a primeira da linguagem principal e a segunda com o código do país, de acordo com a ISO 3166-1 alpha-2. Exemplo: pt-BR ou en-us.

const brazilPopulation = 213317639; 
brazilPopulation.toLocaleString('ja-JP');
// Output: "213,317,639"
Enter fullscreen mode Exit fullscreen mode
Desabilitando separadores de milhar

Também podemos definir se queremos ou não usar separadores de milhares, definindo um valor booleano para a propriedade useGrouping, o valor default é true

const brazilPopulation = 213317639;
brazilPopulation.toLocaleString('pt-BR', {useGrouping: false})
// Output "213317639"
Enter fullscreen mode Exit fullscreen mode

Inteiros e Dígitos Fracionados (Casas Decimais):

O estilo padrão para formatação de Number.prototype.toLocaleString() é decimal, porém podemos definir algumas opções:

minimumIntegerDigits:
  • Define a quantidade mínima de dígitos inteiros
  • Intervalo de Valores: 1 ~ 21
  • Valor Default: 1
const number = 10.175;
number.toLocaleString('pt-br', {style: 'decimal', minimumIntegerDigits: 5});
// Output: "00.010,175"
Enter fullscreen mode Exit fullscreen mode

Repare que ele adiciona a quantidade de zeros à esquerda necessárias para compensar os dígitos faltantes.

minimumFractionDigits:
  • Define a quantidade mínima de dígitos fracionados
  • Intervalo de Valores: 1 ~ 20
  • Valor Default: 0
const number = 10.175;
number.toLocaleString('pt-br', {style: 'decimal', minimumFractionDigits: 10});
// Output: "10,17500000"
Enter fullscreen mode Exit fullscreen mode

Semelhante a minimumIntegerDigits, adiciona zeros à direita para compensar os dígitos faltantes.

maximumFractionDigits:
  • Define o número máximo de dígitos fracionados
  • Intervalo de Valores: 0 ~ 20
  • Valor Default: 3
const number = 10.175;
number.toLocaleString('pt-br', {style: 'decimal', maximumFractionDigits: 1});
// Output: "10,2"
Enter fullscreen mode Exit fullscreen mode

Aqui, ele arredonda os números de acordo com a regras de arredondamento.

minimumSignificantDigits:
  • Define a quantidade mínima de dígitos significantes
  • Intervalo de Valores: 1 ~ 21.
  • Valor Default: 1
const number = 10.175;
number.toLocaleString('pt-br', {style: 'decimal', minimumSignificantDigits: 10});
// Output: "10,17500000"
Enter fullscreen mode Exit fullscreen mode

Diferente de minimumIntegerDigits, ele não adiciona zeros à esquerda para compensar os dígitos faltantes e sim à direita.

maximumSignificantDigits:
  • Define a quantidade máxima de dígitos significantes
  • Intervalo de Valores: 0 ~ 20.
  • Valor Default: minimumSignificantDigits
const number = 10.175;
number.toLocaleString('pt-br', {style: 'decimal', maximumSignificantDigits: 2});
// Output: "10"
number.toLocaleString('pt-br', {style: 'decimal', maximumSignificantDigits: 10});
// Output: "10,155"
Enter fullscreen mode Exit fullscreen mode

Estilo percent

Para estilizar números no formato percentual, precisamos definir a propriedade style como percent. Aqui vale lembrar que porcentagem é a divisão de um número qualquer por 100. Então, para:

Exibir valores entre 0% e 100%, onde 100% não está incluso

O valor a ser exibido deve estar entre 0 e 1, onde 1 não está incluso:

const discount = 0.08179;
off.toLocaleString('pt-br', {style: 'percent'});
// Output: 8%
Enter fullscreen mode Exit fullscreen mode

Exibir valores maiores ou iguais a 100%

O valor a ser exibido deve ser maior ou igual a 1:

const discount = 8.179;
discount.toLocaleString('pt-br', {style: 'percent'});
// Output: "818%"
Enter fullscreen mode Exit fullscreen mode

Estilo currency

Para formatar valores monetários, precisamos definir a propriedade style como currency. Além disso, também é preciso usar a propriedade currency definindo seu valor com o código da moeda necessária de acordo com a ISO 4217:

const price = 2865.79;

price.toLocaleString('pt-BR', {style: 'currency', currency: 'BRL'});
// Output "R$ 2.865,79"

price.toLocaleString('ja-JP', {style: 'currency', currency: 'JPY'});
// Output "¥2,866"

price.toLocaleString('en-US', {style: 'currency', currency: 'USD'});
// Output "$2,865.79"
Enter fullscreen mode Exit fullscreen mode

A opção currencyDisplay

Podemos, ainda, definir como este valor será exibido. Valores aceitos:

  • name: exibe nome da moeda
  • code: exibe o código de acordo com a ISO 4217
  • symbol(default): exibe o símbolo da moeda
const price = 2865.79;

price.toLocaleString('pt-BR', {
    style: 'currency', 
    currency: 'BRL',
    currencyDisplay: 'name'
});
// Output "2.865,79 Reais brasileiros"

price.toLocaleString('pt-BR', {
    style: 'currency', 
    currency: 'BRL',
    currencyDisplay: 'code'
});
// Output "BRL 2.865,79"
Enter fullscreen mode Exit fullscreen mode

Limitações

A MDN recomenda que, caso exista um volume muito grande de números a serem formatados, é melhor criar um objeto Intl.NumberFormat e usar o método Intl.NumberFormat.prototype.format() para ter um ganho de performance.

Conclusão

Considere o HTML a seguir:

<span class="price"></span>
Enter fullscreen mode Exit fullscreen mode

Sem Number.prototype.toLocaleString(), precisaríamos fazer algo assim para obtermos uma apresentação minimamente aceitável de um valor monetário:

const value = 25.978;
const priceContainer = document.querySelector('.price');
priceValueContainer.innerHTML = `R$ ${value.toFixed(2)}`;
Enter fullscreen mode Exit fullscreen mode

Porém, usando Number.prototype.toLocaleString(), podemos delegar a responsabilidade para o formatador:

priceContainer.innerHTML = value.toLocaleString('pt-BR', {style: 'currency', currency: 'BRL'});
Enter fullscreen mode Exit fullscreen mode

Ok, mas, no final das contas, ambos os códigos geram o mesmo resultado visual. Por que eu deveria usar Number.prototype.toLocaleString() então?

Uma resposta possível seria para o seguinte caso:

Suponha que o nome da moeda do Brasil mude de Reais para Nárnia Reais e que o símbolo deixará de ser R$ para se tornar NR$. A gente teria que sair atualizando tudo manualmente em nossa aplicação. Então, delegar essa responsabilidade para um método Number.prototype.toLocaleString() pode agilizar essas modificações, pois ele usará as atualizações mais recentes dos códigos dos países.

E isso não é apenas para moedas, mas também para outros números. Imagine ter que formatar números grandes como a população ou o PBI de um país, por exemplo?

Então, conhecer esse tipo de método torna-se interessante e um facilitador quando precisamos trabalhar com internacionalização.

Links para Consulta:

💖 💪 🙅 🚩
vanribeiro
Van Ribeiro

Posted on March 21, 2022

Join Our Newsletter. No Spam, Only the good stuff.

Sign up to receive the latest update from our blog.

Related