Jeu vidéo / Moteur 3D web

SelixyCARD

Jeu de cartes type UNO en 3D dans le navigateur, moteur Rust en wasm

RustWebAssemblywgpuWGSLAxumPostgreSQLWebSocket

SelixyCARD est un jeu de cartes type UNO qui se joue dans le navigateur, sur une table en 3D. On peut y créer ses propres sets de cartes illustrés, activer des règles optionnelles et jouer à plusieurs.

Le jeu et les sets

Un set compte 108 emplacements. Une page de bibliothèque permet de les illustrer avec un éditeur à recadrage, et une carte sans image reçoit un visuel par défaut. Les règles de base et les options sont écrites une seule fois, dans un module Rust partagé, exécuté par le serveur, qui est le seul juge de la partie.

Le salon permet de créer ou de rejoindre une partie ; les échanges passent par une WebSocket.

Le moteur 3D en Rust et wasm

J’ai écrit le moteur en Rust, compilé en wasm. Il ne s’occupe que du rendu, de l’animation et du pointage : le JavaScript garde la WebSocket, l’état de la partie et l’interface. Le rendu passe par wgpu, avec des shaders en WGSL.

Quelques choix :

  • toutes les cartes sont posées à plat et se superposent par décalage en hauteur, avec une caméra de table basse pour un point de vue immersif ;
  • chaque carte rejoint sa pose cible par lissage exponentiel, indépendant du débit d’images, avec des trajets en arc pour les longs déplacements ;
  • le pointage ne lance pas de rayon : il projette les coins des cartes et teste le quadrilatère, de la carte du dessus à celle du dessous ;
  • l’éventail de la main s’adapte à la place visible, notamment en portrait sur téléphone.

Rendu et décor

Le plan de travail est une ardoise générée dans le shader, avec des traits de craie, sans texture. Les cartes projettent des ombres, et une carte jouée soulève un nuage de poussière de sa couleur à l’impact. Un second module, graphe_pbr, sert à décrire des matériaux sous forme de graphe de nœuds, traduit en GLSL et en WGSL.

Serveur et déploiement

Le serveur est en Rust (Axum) avec PostgreSQL : comptes, sets, images et salons. Le tout est livré dans un pod Podman derrière nginx, par un simple git push. Un audit modulaire et des tests (Rust et JavaScript) accompagnent le dépôt.

Video Game / Web 3D engine

SelixyCARD

UNO-style 3D card game in the browser, with a Rust engine compiled to wasm

RustWebAssemblywgpuWGSLAxumPostgreSQLWebSocket

SelixyCARD is a UNO-style card game played in the browser, on a 3D table. You can create your own illustrated card sets, enable optional rules and play with others.

The game and the sets

A set has 108 slots. A library page lets you illustrate them with a cropping editor, and a card without an image gets a default look. The base rules and the options are written once, in a shared Rust module run by the server, which is the only judge of the game.

The lobby lets you create or join a game; exchanges go through a WebSocket.

The 3D engine in Rust and wasm

I wrote the engine in Rust, compiled to wasm. It only handles rendering, animation and picking: JavaScript keeps the WebSocket, the game state and the interface. Rendering goes through wgpu, with WGSL shaders.

A few choices:

  • all cards lie flat and stack by height offset, with a low table camera for an immersive point of view;
  • each card reaches its target pose through exponential smoothing, independent of frame rate, with arc trajectories for long moves;
  • picking does not cast a ray: it projects the card corners and tests the quadrilateral, from the top card to the bottom one;
  • the hand fan adapts to the visible space, in particular in portrait on a phone.

Rendering and scenery

The work surface is a slate generated in the shader, with chalk strokes, no texture. Cards cast shadows, and a played card kicks up a dust cloud in its own color on impact. A second module, graphe_pbr, describes materials as a node graph, translated to GLSL and WGSL.

Server and deployment

The server is written in Rust (Axum) with PostgreSQL: accounts, sets, images and lobbies. Everything ships in a Podman pod behind nginx, with a simple git push. A modular audit and tests (Rust and JavaScript) come with the repository.