Log inGet started
World

Builtin Library

Branchmain
Branchesmainpublish
Commitdd348ac6c3

README.md

canvas

Immediate-mode 2D-paint widget. The body is a sequence of paint commands (line, bezier, polyline, rect, circle, text) drawn in widget-local coordinates with origin at the top-left and +y going down (egui-standard, opposite of plot). Wires through pointer, drag, double-click, key, and scroll handlers, and forwards role / tag / aria* props for accessibility.

Exports

  • canvas(id: string?, opts: CanvasOpts?) -> WidgetNode — build a canvas widget node from a list of paint commands plus optional interaction handlers.

Types:

  • CanvasOpts = { commands?, width?, height?, onClick?, onPointerDown?, onPointerUp?, onPointerMove?, onDrag?, onDoubleClick?, onKey?, onScroll?, role?, tag?, style?, class?, classes? }

Usage

local canvas = require("@builtin::modules.zui.widget.canvas")

canvas("my-canvas", {
    commands = {
        { kind = "line", a = {10,10}, b = {200,150}, color = "#7AA8FF", width = 2 },
        { kind = "circle", center = {100,100}, radius = 30, fill = "#FF8855" },
        { kind = "text", pos = {10,180}, text = "hello", color = "#fff", fontSize = 14 },
    },
    onClick = "canvas:click",
    style = { width = 600, height = 400, background = "#161B22" },
})

Notes

  • Pointer events surface widget-local cursor coords as either a "x,y" string (legacy) or a structured Luau table (modern handlers).
  • onClick / onPointerDown / onPointerUp carry data.button (0 = left, 1 = right, 2 = middle) identifying which mouse button triggered the event.
  • onKey fires only while the canvas has keyboard focus; onScroll fires while it is hovered.
  • Any opts.aria* key passes through verbatim — no wrapper-side allowlist needed.
  • Command kinds and per-kind fields are defined in crates/zero_ui_protocol/src/canvas.rs.