Log inGet started
World

Builtin Library

Branchmain
Branchesmainpublish
Commitdd348ac6c3

README.md

panel

Bordered surface for grouping widgets. Accepts top-level shortcut keys (bg, border, borderWidth, padding, gap, minWidth, minHeight, maxWidth, maxHeight) so the common case doesn't require nesting under style = { ... }.

Exports

  • panel(children: { any }?, opts: Opts?) -> any — build the panel widget node. Returned directly by the module.

Types:

  • Opts = { id?, classes?, props?, style?, bg?, border?, borderWidth?, padding?, gap?, minWidth?, minHeight?, maxWidth?, maxHeight?, scroll?, scrollMaxHeight?, scrollId? }

Usage

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

local widget = panel({
    Z.lbl("Header"),
    Z.btn("Action", "click"),
}, {
    bg          = "#101010",
    border      = "#3a3a3a",
    borderWidth = 1,
    padding     = 8,
})

Tall panels — scrolling overflow (closes #3270)

Z.anchor("Center", ...) { Z.panel(rows) } with more rows than the viewport will silently clip top + bottom of the list — content scrolls off-screen with no affordance. Opt into in-place scrolling by passing scroll = true alongside a maxHeight:

local rows = {}
for i = 1, 100 do rows[#rows + 1] = Z.lbl("row " .. i) end

-- Header + footer pin to the panel; the rows scroll between them.
return Z.anchor("Center", {}, {
    Z.panel({
        Z.lbl("Codex", { bold = true }),
        Z.sep(),
        Z.panel(rows, { scroll = true, maxHeight = 480 }),
        Z.sep(),
        Z.btn("Close", "codex:close"),
    }, { bg = "#101010", padding = 12 }),
})

Without scroll = true, maxHeight only clips — scroll = true wraps the children in a scrollArea so overflow rows are reachable via the scrollbar. scrollMaxHeight (optional) bounds only the scroll region when you want the panel itself to size to the header + footer and let the scroll region claim what's left.

Notes

  • Top-level shortcuts merge into opts.style (caller-supplied keys take precedence — explicit style.background wins over opts.bg only because the shortcut writes to style.background after style is captured).
  • Defers to node("panel", ...) so any panel-specific renderer arm changes flow through automatically.
  • Children default to {} — an empty panel renders as a bordered spacer.
  • scroll = true inserts a single scrollArea child wrapping the caller's children. Pair with a maxHeight (or scrollMaxHeight to bound only the scroll region) so the scrollArea has something to scroll against — without a bound the scrollArea fills its parent and no scrolling is observed.