UiNode
Since 0.6
One node of a screen description.
This is the frozen wire contract between the TSX compiler and the engine: { format: 1, screen, root }, with a node carrying its role, its identity, its classes, its data attributes, its text and its children. It is deliberately data rather than a builder — a screen an agent can print, diff and post is a screen an agent can debug.
Signature
export interface UiNode {
role: UiRole
/**
* Stable author id, flat within the screen. `GET /ui` reports it qualified: `pause:resume`.
*
* May not contain `/` or `:` — those are the id grammar's own separators, so an id using one
* could forge a sibling's derived id. The engine refuses it and falls back to the derived
* form rather than letting two nodes answer to one name.
*/
id?: string
/** Diffing key. A keyed child keeps its identity across a rebuild even if its position moves. */
key?: string
classes?: string[]
/** Data attributes without the `data-` prefix. Variants are data, not generated class strings. */
data?: Record<string, string | number | boolean>
/** A literal string. Mutually exclusive with `textKey`. */
text?: string
/** A `meta.strings` key. §2.11 makes this the default and a literal the marked case. */
textKey?: string
/**
* Per-node props. On the **root** these configure the screen itself — `inputContext`,
* `modal`, `dismissible`, `clickThrough`, `cursor`, `pausesWorld`. On any other node they are accepted,
* kept and reported as `ui.screen.props-ignored` until the binding table lands; they are
* never silently dropped.
*/
props?: Record<string, unknown>
children?: UiNode[]
}
Import: import type { UiNode } from "@argus/api"
Members
| Member | Signature | Description |
|---|---|---|
role | role: UiRole | |
id | id?: string | Stable author id, flat within the screen. GET /ui reports it qualified: pause:resume. May not contain / or : — those are the id grammar's own separators, so an id using one could forge a sibling's derived id. The engine refuses it and falls back to the derived form rather than letting two nodes answer to one name. |
key | key?: string | Diffing key. A keyed child keeps its identity across a rebuild even if its position moves. |
classes | classes?: string[] | |
data | data?: Record<string, string | number | boolean> | Data attributes without the data- prefix. Variants are data, not generated class strings. |
text | text?: string | A literal string. Mutually exclusive with textKey. |
textKey | textKey?: string | A meta.strings key. §2.11 makes this the default and a literal the marked case. |
props | props?: Record<string, unknown> | Per-node props. On the root these configure the screen itself — inputContext, modal, dismissible, clickThrough, cursor, pausesWorld. On any other node they are accepted, kept and reported as ui.screen.props-ignored until the binding table lands; they are never silently dropped. |
children | children?: UiNode[] |
Example
The tested fixture fixtures/app/agent.ts.
import type { Behavior } from "@argus/api"
// Sends a nav agent to `props.target` once, then reports arrival through ctx.state so the
// test can read it without polling the crowd directly.
export default {
init(ctx) {
ctx.state.arrived = false
ctx.nav?.goTo(ctx.props.target as [number, number, number])
},
update(ctx) {
if (ctx.nav?.arrived) ctx.state.arrived = true
},
} satisfies Behavior