Build a game
How do I go from a project directory to something that runs?
Install#
Two installers. The compiler builds your game's Motoko; the game tools build and run the package. They are separate because most people who want the compiler do not want a 3D renderer, and the two are licensed separately.
curl -fsSL https://moxzi.ai/install.sh | sh
curl -fsSL https://moxzi.ai/install-game.sh | sh
Each verifies its download against the release's SHA256SUMS before unpacking and aborts on a mismatch. Apple Silicon macOS; the game tools are ~35 MB because they carry a renderer.
Start from the example#
A complete game ships with the tools: Pong, in four Motoko files. Copy it somewhere writable — the installed copy is meant to stay pristine — and build it.
cp -R ~/.local/lib/moxzi-game/examples/pong ~/pong && cd ~/pong
moxzi-game build . out/pong
moxzi-player out/pong native
build compiles the project's Motoko with the moxzi compiler and writes a package: the descriptor, the game wasm, the assets, and a manifest with content hashes. moxzi-player opens a window and runs it.
Or headless — no window, no GPU, which is what you want in CI:
moxzi-game run-headless out/pong 1200 report.json
run-headless executes a fixed tick count and writes a report.
Change something#
The example is laid out so each concern is one file:
| File | What lives there |
|---|---|
game.yaml | entry point, asset folders, simulation rate |
src/Main.mo | the match actor: state, input, the snapshot the renderer draws |
src/Game.mo | the rules — collisions, serves, scoring |
src/Opponent.mo | the AI paddle, an independent actor |
src/Scene.mo | a pure function from game state to what appears on screen |
assets/ | materials, models and sounds, as small YAML files |
Make the ball faster in Game.mo, or change the court colour in assets/court.material.yaml, and rebuild. Every asset file name becomes a Motoko constant — court.material.yaml gives you material_court — so a typo is a compile error rather than a missing texture at runtime.
The toolchain it needs#
The game's Motoko is compiled by the same compiler this site ships, so point the builder at the moxzi you installed above:
export MOXZI_BIN=~/.local/bin/moxzi
export MOXZI_COMPILER=~/.local/lib/moxzi/compiler.wasm
export MOXZI_LINKER=~/.local/lib/moxzi/linker.wasm
Install moxzi if you have not already.
A project#
game.yaml project id, title, entry point, simulation rate, actor capacity, capabilities
src/Main.mo the authoritative simulation
assets/ models, textures, audio
A game gets nothing from the host it did not ask for. capabilities: [http] lets the simulation make HTTPS requests (http_request on the management canister, exactly as on the IC); leave it out and the runtime is closed — an outcall fails by name, and a save can never depend on an answer from outside.
game.yaml is the source descriptor. package.json is generated — if a tool complains that it is missing, you are pointing it at a project directory instead of a built package.
Talking to the Internet Computer from a game#
A game that declares capabilities: [http] can be a client of the IC: mops add ic-agent and use mo:ic-agent from the simulation — query a canister, or submit an update on one tick and poll for it on later ticks, so a courier never blocks a frame on the network. moxzi agent-bindings score.did --name Score -o Score.mo gives a typed façade (Score.connectText(agent, id), then await* score.submit_result(...)). Signing as the player is a product decision for shipped builds; development builds use a configured key. Details: the server docs' agent page — the same library, the same API, in a game.
Export to a browser#
python3 platform/web/export.py out/lanternfall \
--compiler-root <moxzi checkout> --bindgen $(command -v wasm-bindgen) --out out/web
wasm-strip out/web/view/moxzi_web_view_bg.wasm
The strip matters: it takes the renderer from 69 MB to 40 MB, and 12.2 MB to 9.7 MB gzipped, by dropping symbols a player never reads.