ThePrimeagen a choisi une manière assez brutale de gérer l’interface de son jeu : la reconstruire presque entièrement à chaque frame.

Pour une page web, cette phrase ressemble à une menace. Pour sa petite UI de jeu écrite en Odin, il trouve au contraire le modèle plus simple à comprendre que l’approche « retained mode » utilisée dans une version précédente.

La vidéo n’essaie pas de prouver qu’une architecture d’interface a gagné pour toujours. Elle montre quelque chose de plus utile : comment déplacer la complexité jusqu’à l’endroit où elle devient supportable pour la personne qui écrit le code.

Retenir l’interface ou la recalculer

Vers 1:28, ThePrimeagen part du modèle familier du DOM.

Dans une interface retenue, les éléments existent dans une structure persistante. On crée un objet, on conserve son identité et on réagit ensuite à des événements : survol, clic, focus, changement d’état.

Son système actuel prend l’autre direction. À partir de 1:45, il décrit une interface en immediate mode. À chaque frame, le programme regarde l’état actuel puis reconstruit les éléments nécessaires.

Pour son jeu, il estime qu’il n’aura généralement qu’entre 50 et 100 éléments d’interface actifs. Dans ce contexte précis, recalculer cette petite arborescence ne l’inquiète pas côté coût.

Ce chiffre appartient à son projet. Ce n’est pas une permission universelle pour redessiner n’importe quelle interface gigantesque soixante fois par seconde et appeler cela de l’élégance.

Le layout commence par les feuilles

À 2:52, il explique s’être inspiré d’une vidéo sur l’algorithme de layout de Clay et en avoir repris une partie des idées.

Ses besoins sont volontairement réduits : boîtes, alignement horizontal ou vertical, centrage, texte et sprites.

La taille des éléments est calculée en descendant jusqu’aux feuilles de l’arbre. Une feuille peut avoir une taille fixe, dépendre de son texte ou de son sprite. Une fois ces dimensions connues, les parents peuvent calculer leur propre taille avec le padding et les gaps.

Puis vient le positionnement.

Vers 5:47, la logique devient presque mécanique : si la taille des enfants est connue, leur position peut être calculée les uns après les autres. Le centrage sur l’axe secondaire revient à comparer la taille du parent et celle de l’enfant.

Rien de tout cela n’est particulièrement mystérieux pris séparément. Le travail consiste à choisir assez peu de règles pour que leur combinaison reste prévisible.

La souris casse la belle histoire

Vers 7:06 arrive le problème qui rend le procédé intéressant.

Imaginons qu’un élément grossisse quand la souris le survole.

Pour savoir si la souris est dans l’élément, il faut connaître sa position et sa taille. Mais sa nouvelle taille dépend justement du fait que la souris soit dedans. L’interface qu’on est en train de construire n’existe pas encore complètement.

On obtient un petit problème de poule et d’œuf, mais avec davantage de rectangles.

La solution de ThePrimeagen consiste à garder la racine du layout précédent. Au début de la frame suivante, il compare la position actuelle de la souris avec la géométrie de la frame précédente. Ce résultat fournit l’état de survol, de drag ou d’entrée/sortie utilisé pendant la construction de la nouvelle interface.

Il accepte donc volontairement une information décalée d’une frame pour conserver un modèle mental simple.

C’est un compromis très jeu vidéo : la frame précédente n’est jamais très loin.

Moins d’événements persistants, plus de calcul explicite

À partir de 9:35, il explique pourquoi cette approche lui plaît.

Dans son ancienne interface retenue, le survol demandait de maintenir de l’état entre plusieurs handlers. Un événement marque l’entrée, un autre la sortie, et le programme doit conserver ce qui s’est passé entre les deux.

Dans son système immédiat, le composant peut demander au moment où il est construit : suis-je survolé maintenant ? Si oui, il choisit directement sa taille ou son animation pour cette frame.

La complexité n’a pas disparu. Elle s’est déplacée vers le calcul du layout, la conservation de la géométrie précédente et la reconstruction continue.

Pour lui, ce déplacement rend le code plus local et plus lisible.

Le détail le plus révélateur arrive quand l’IA pourrait écrire le code

Vers 11:19, ThePrimeagen regarde une version plus verbeuse de son API de composants et fait une remarque assez révélatrice.

Un agent pourrait facilement générer les gros objets de paramètres répétitifs. Ce n’est pas son problème. Lui doit encore lire ce code ensuite.

Il préfère donc fabriquer une petite API de construction qui lui semble plus agréable, même si l’IA saurait parfaitement produire la version qu’il trouve moche.

C’est une contrainte intéressante dans une période où la génération réduit le coût de la frappe.

Si écrire vingt lignes répétitives ne coûte presque plus rien, leur présence peut quand même coûter quelque chose à chaque relecture, chaque debug et chaque modification humaine.

L’esthétique du code ne disparaît pas parce que la machine sait le taper.

Une architecture peut être choisie pour son modèle mental

Le système de ThePrimeagen est jeune. C’est sa première UI immediate-mode, dans un jeu où le nombre d’éléments reste volontairement petit. Il rencontre déjà ses propres compromis et ne prétend pas avoir construit un remplacement général du DOM.

C’est précisément pour ça que la vidéo est utile.

Elle ne montre pas une abstraction terminée. Elle montre quelqu’un qui réduit son problème jusqu’à pouvoir écrire lui-même les règles, puis découvre où ces règles commencent à résister.

Le résultat n’est pas seulement une interface qui aligne correctement des cartes.

C’est un morceau de code dont l’auteur peut encore expliquer, frame après frame, pourquoi chaque rectangle se trouve là.