Wren

  • Template: cart_wren - press "Use this template" and you have a working game.
  • Docker image: ghcr.io/notnullgames/null0-cart-wren:latest
  • Your code: cart/main.wren, interpreted by wren, baked into main.wasm
  • Bindings: carts/wren/null0.wren (editor definitions - the runtime provides the API itself)
  • WASI is available, so ordinary file and stdio calls work.
  • See carts made with Wren
  • API docs for Wren

building

You do not install wren, baked into main.wasm - the docker image has it, and the current null0 bindings, baked in. There is nothing in your project to keep in sync with the engine.

docker run --rm --user $(id -u):$(id -g) \
  -v ./cart:/src -v ./webroot:/out \
  ghcr.io/notnullgames/null0-cart-wren:latest mygame

The template wraps that in npm start, which also serves the result and rebuilds when you save.

Wren notes

  • import "null0" for Null0, BLUE - the API hangs off the Null0 class.
  • Callbacks are Fn values assigned to top-level variables.

a cart, in Wren

This is carts/wren/simple/main.wren in the engine repo - the same file CI builds into the cart below, so it always compiles.

import "null0" for Null0, BLUE, RED, WHITE, FONT_DEFAULT

var load = Fn.new {
  Null0.clear(BLUE)
  Null0.draw_circle(100, 100, 50, RED)
  Null0.draw_text(FONT_DEFAULT, "hello from Wren", 170, 92, WHITE)
}

// other callbacks you can define:
//
//   var update = Fn.new {}
//   var buttonDown = Fn.new { |button, player| }
carts/wren/simple/main.wren

callbacks

A cart implements the callbacks it cares about. In Wren they look like this:

var update = Fn.new {}

See anatomy of a cart for the full list and what each one is passed.