Skip to content
← 1001 Widgets
N° 029 · ●○○

Bill splitter

The bill amount, a tip, the number of guests: everyone knows what they owe, rounded to 50 cents. The right exercise to compute money without rounding errors.

HTMLJS
What you'll learn
  • Compute in cents to avoid errors
  • Round up with Math.ceil
  • Read an amount written with a comma
Why this language

Pourquoi un partage d'addition ? Fin de repas à six, une addition de 86,40 euros, dix pour cent de pourboire : qui sort sa calculatrice ? Cet outil répond en une seconde, et arrondit pour que personne ne cherche ses pièces.

Le secret, c'est de compter en centimes. En JavaScript, 0,1 + 0,2 ne vaut pas exactement 0,3. Avec des nombres entiers de centimes, ce problème disparaît. On arrondit chaque part vers le haut : la salle touche un petit bonus plutôt qu'un manque.

Pourquoi en JavaScript simple ? Trois entrées, quatre lignes de calcul, et Intl.NumberFormat pour afficher des euros à la belge.

How it works
  1. LIRE LE MONTANT

    « 86,40 » doit devenir 86.4, et un champ vide ne doit pas devenir 0.

    function lire(texte) {
      const t = texte.replace(/\s/g, '').replace(',', '.');
      return t === '' ? NaN : Number(t);
    }
  2. PASSER EN CENTIMES

    Les centimes sont des entiers : plus d'erreur du type 0,1 + 0,2.

    const centimes = Math.round(lire(champ.value) * 100);
  3. AJOUTER LE POURBOIRE

    const total = Math.round(centimes * (1 + pourboire / 100));
  4. DIVISER ET ARRONDIR

    Math.ceil arrondit vers le haut : le total n'est jamais trop court.

    let part = Math.ceil(total / personnes);
    if (arrondir) part = Math.ceil(part / 50) * 50;   // aux 50 centimes
  5. AFFICHER

    const eur = new Intl.NumberFormat('fr-BE', { style: 'currency', currency: 'EUR' });
    document.getElementById('part').textContent = eur.format(part / 100);
    document.getElementById('bonus').textContent = eur.format((part * personnes - total) / 100);
Pitfalls

PIÈGE 1 : Calculer en euros à virgule

Pitfall

Mauvais : 86.4 * 1.1 / 4. On obtient 23.760000000000005, et les arrondis se décalent.

Fix

Correct : convertir en centimes entiers au départ, et ne diviser par 100 qu'à l'affichage.

PIÈGE 2 : Arrondir au plus proche

Pitfall

Mauvais : Math.round sur chaque part. À six convives, il peut manquer quelques centimes au total.

Fix

Correct : Math.ceil, puis afficher ce qui dépasse comme un petit bonus.

PIÈGE 3 : Diviser par zéro personne

Pitfall

Mauvais : laisser descendre le nombre de convives à 0. La part devient Infinity.

Fix

Correct : un minimum de 1, et le bouton moins désactivé à cette limite.

PERSONNALISER
  • Des parts inégales : un convive qui n'a pris qu'une entrée paie moins.
  • Le pourboire en montant fixe plutôt qu'en pourcentage.
  • Un bouton Partager qui copie le détail des parts dans le presse-papiers.
OPTIMISATION
  • Gardez le dernier pourboire choisi dans localStorage : on garde souvent ses habitudes.
  • Ajoutez inputmode="decimal" au champ : sur téléphone, le clavier numérique s'ouvre directement.
VERS REACT

Le montant, le pourboire et le nombre de convives vivent dans trois useState.

La part et le bonus se calculent pendant le rendu : ce sont des valeurs dérivées.

Le formateur Intl se crée une fois, en dehors du composant.

Comments
0/1000

Loading comments…

Audience measurement

With your consent, this site measures its traffic with Google Analytics and the Meta pixel, via Google Tag Manager. Nothing is loaded until you choose, and you can change your mind at any time with the "Cookies" link at the bottom of the page.