Files
ki-fwi/docs/adr/0002-phaser-hors-budget-initial.md
T
OKIandClaude Opus 5 3c660c776b feat(session-4): module Pa touché et scène arcade Ranmasé en Phaser 4
Pa touché est une consultation, pas un mode de jeu : cinq plantes triées
par gravité, dépliables, sans chrono, sans score, sans épreuve. Le module
affiche lui-même qu'il n'a pas encore été relu par une personne compétente
et dit que cette relecture est la contribution la plus utile au projet.

Ranmasé : import dynamique, game.destroy(true) au démontage, communication
par événements — la scène ne touche aucun état Svelte et n'émet que sur
changement, jamais par frame. Miroir DOM sémantique, canvas aria-hidden,
jouable au clavier. Écran de chargement designé.

Game design guidé par la pédagogie : laisser passer une plante dangereuse
ne coûte rien (c'est le bon geste), ramasser le mauvais fruit coûte 2
points et pas une vie (il n'y a pas d'erreur à cueillir), une plante
dangereuse sur cinq.

Budgets mesurés et consignés dans l'ADR 0002
- shell hors Phaser : 78 Ko gzip (budget 170)
- Phaser seul : 348 Ko gzip, sous le seuil de réexamen de 450
- absent du chemin critique de l'accueil, vérifié sur le HTML prérendu
- build total 1,4 Mo

Une prescription de l'ADR 0002 était fausse : l'option `resolution`
n'existe pas dans Phaser 4 (pixelRatio y est en lecture seule). Le
plafonnement passe par un tampon de rendu fixe 480×640 étiré en CSS —
plafond dur plutôt que relatif. L'ADR est corrigé, pas contourné.

Reste non mesuré : les 30 fps sur Mali-G52, qui demandent un appareil réel.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-27 12:07:48 -04:00

3.7 KiB
Raw Blame History

ADR 0002 — Phaser 4 et l'écart au budget JS

  • Statut : accepté, avec mesure à compléter en session 4
  • Date : 2026-07-27
  • Session : 0 — cadre et données

Contexte

Le playbook OKI §2.7 fixe un budget non négociable de 170 Ko de JS initial compressé. Le mode arcade « Ranmasé » demande de la physique, des particules et du game feel : le faire en DOM coûterait plus cher en travail et en performance qu'un moteur éprouvé.

Le pack d'origine prescrivait « Phaser 5 ». Phaser 5 n'existe pas. Vérification faite au démarrage de la session :

$ npm view phaser version
4.2.1

La branche courante est Phaser 4 — 4.0 « Caladan » (avril 2026), 4.1 « Salusa », 4.2 « Giedi » — avec un moteur WebGL réécrit en render nodes. Partir de Phaser 3 aurait été partir d'une branche en fin de vie.

Décision

Utiliser phaser@^4 (4.2.1 au moment de la décision), et assumer un écart documenté au budget JS, borné par quatre conditions :

  1. Phaser n'est jamais dans le chemin critique. Import dynamique dans la route (jeu)/ranmase uniquement, jamais au layout racine.
  2. Le shell reste ≤ 170 Ko gzip, Phaser exclu. Le budget n'est pas relâché : il est mesuré à part.
  3. L'entrée dans la scène passe derrière un écran de chargement designé (playbook P5, en KA avec le tambour ka), pas derrière une page blanche.
  4. Rendu AUTO (WebGL avec repli canvas), DPR plafonné à 1,5, powerPreference: 'low-power', cible 30 fps stables sur Mali-G52.

Conséquences

  • Le budget d'entrée du site (≤ 2 Mo) et les Core Web Vitals (LCP < 2,5 s, INP < 200 ms, CLS < 0,05) restent mesurés sur l'accueil et sur une fiche, pages qui ne chargent jamais Phaser.
  • Un utilisateur qui ne joue jamais au mode arcade ne télécharge jamais Phaser. Les quatre autres modes sont en Svelte pur (ADR 0003).
  • La session 4 doit renseigner ici la mesure réelle du bundle Phaser en gzip et le relevé de fps sur mobile d'entrée de gamme.

Mesures — à compléter en session 4

Mesure Cible Relevé (2026-07-27)
Shell JS initial, Phaser exclu (gzip) ≤ 170 Ko 78 Ko
Bundle Phaser seul (gzip) information 348 Ko — sous le seuil de réexamen de 450 Ko
Phaser dans le chemin critique de l'accueil absent absent, vérifié sur le HTML prérendu
Poids total du build ≤ 2 Mo 1,4 Mo
fps scène Ranmasé sur Mali-G52 ≥ 30 stables non mesuré — demande un appareil réel

Le total JS du site atteint 426 Ko gzip, mais 348 Ko ne sont téléchargés qu'à l'entrée dans /je/ranmase/. Un visiteur de l'encyclopédie ne les voit jamais.

Correction apportée à cet ADR par la mise en œuvre

Cet ADR prescrivait un « DPR plafonné à 1,5 » via l'option resolution. Cette option n'existe pas dans Phaser 4 : pixelRatio y est une information matérielle en lecture seule, et resolution avait déjà été neutralisée en Phaser 3.

L'objectif est atteint autrement, et mieux : le tampon de rendu est fixé à 480 × 640, étiré en CSS par le mode FIT. Le GPU dessine donc toujours 480 × 640 pixels, quel que soit le DPR de l'appareil — c'est-à-dire un plafond dur, là où resolution n'aurait donné qu'un plafond relatif.

powerPreference: 'low-power' existe bien, sous la clé render.

Condition de réexamen

Si la mesure de session 4 montre que Phaser dépasse ~450 Ko gzip, ou que les 30 fps ne sont pas tenus sur mobile d'entrée de gamme, la scène « Ranmasé » est réécrite en DOM/CSS avec une boucle rAF maison — le playbook P3 (« DOM d'abord, WebGL seulement où ça paie ») reprend alors la main. Les quatre autres modes n'en dépendent pas : le jeu reste entier.