Skip to content

Declarative API

Joseph Gettings edited this page Jul 4, 2026 · 9 revisions

Declarative API — RGXAddon

The authoring surface for RGX addons, governed by THE SIMPLICITY CONTRACT: evolution is additive-only — what you write today keeps working forever. The machine-checkable shape lives in schemas/rgx-addon.schema.json, with keys annotated x-rgx-ships: "today" (implemented) or "tier4" (frozen target). The repo's docs/DECLARATIVE-API.md is the canonical copy of this page.

Entry point

RGXAddon("MyAddon", { ... })
RGXAddon "MyAddon" { ... }     -- curried form; identical

RGXAddon is a global the framework provides — ## RequiredDeps: RGX-Framework guarantees it exists before your file runs. Returns the addon object.

The rule: bare forms assume, advanced forms unlock

Every key works bare with assumed arguments, and accepts an advanced form when you need more — one vocabulary, no second API. minimap = true assumes an icon, a left-click that opens your panel, and angle persistence to addon.db; minimap = { icon = ..., onRightClick = ... } unlocks the rest.

Shipped keys

Key Bare form Advanced form
slash string | string[] — registers /cmd; assumed handler opens the options panel same table + handler = function(addon, msg)
minimap true (default icon) | string (icon path) — assumed left-click opens the panel; dragged angle persists to addon.db full opts table (tooltip, defaultAngle, onRightClick, onCtrlRight, ...)
db table of profile defaults; creates addon.db on ADDON_LOADED. SavedVariables name assumes <Name>DB with non-identifier characters stripped — declare it in your TOC dbName override; global; onSwitch
options TabName = { controls... }; builds a tabbed panel with db-bound controls (save and restore) per-control keys below; Tier 4 adds columns and multi-page tabs
title assumes the addon name string override
welcome string printed with the branded prefix on load
onInit function(addon), runs after db/options exist — the imperative escape hatch
brand assumes 58be81 hex string (no #)
table use an existing table as the addon object

Controls

{ section = "Header Text" }
{ toggle = "dbKey", label = "Label", default = true }
{ slider = "dbKey", label = "Label", min = 0, max = 100, step = 1, suffix = "%" }
{ color = "dbKey", label = "Label", default = { r = 1, g = 1, b = 1 } }
{ dropdown = "dbKey", label = "Label", items = { "a", "b" }, width = 260 }
{ button = "Button Text", action = function() ... end, width = 120, height = 22 }

Only the db key is required — labels assume the capitalized key, slider range assumes 0–100, color default assumes the db default. Persistence and visual restore are not the author's job.

Layout model

One composable vocabulary, top to bottom: panel → main page + tabs → tabs can be multi-paged → 1–2 column card grid → rows/cards holding the widgets. What ships today is panel → tabs → a single column of controls; Tier 4 implements the rest (columns = 1|2|3 and multi-page tabs) without changing anything you write today.

The addon object

Scoped plumbing on the returned object, all routed through the framework's taint-safe paths:

onInit = function(self)
    self:RegisterEvent("PLAYER_LOGIN", function() self:Print("Ready!") end)
    self:After(2, function() ... end)
    self:Every(30, function() self:Scan() end)
    self:Print("branded chat output")
end

Tier 4 (contract-frozen, not yet implemented)

Human trigger words (on = { levelup = fn }), one-line control strings ("slider volume 0-100"), card-grid layouts, and multi-page tabs. These validate against the schema but do not run yet — RGX-MCP's rgx_validate_addon flags them.

Reference implementation

RGX-Hello is the canonical example — the smallest complete RGX addon, plus the framework's in-game test suite. See Testing.

Clone this wiki locally