fix: align widget contract with lib-core.panel API
The widget contract was implemented as render(theme, x, y, w, h) and
handle_input(input_state, theme, x, y, w, h), but lib-core.panel
dispatches widgets as render(ctx) and handle_input(ctx, event) where
ctx = {bounds = {x,y,w,h}, theme, is_focused} and event carries
{kind, x, y, button} for clicks or {kind, dy} for wheel.
The mismatch would have surfaced as a crash on the first render frame
(theme.row_height read on a nil first arg) and as a permanently dead
right-click (no field matched input_state.right_clicked because the
real signature passes an event table). Both bugs were masked by the
existing tests, which exercise the public registration surface but
never drove render or handle_input headless.
Changes:
- widget.render and widget.handle_input now match panel's contract.
- _render_widget consumes ctx.bounds + ctx.theme; reads packed-RGBA
text colours directly instead of falling back to synthetic float
arrays (panel theme stores 0xRRGGBBAA integers).
- _handle_input_widget dispatches on event.kind == "click" and
event.button == "right", iterating _render_rows for hit-testing.
- draw_text now passes theme.font_size_body so the engine receives
the full (text, x, y, size, color) signature.
- Side-effect requires for lib-core.inventory-list and
lib-core.composition replace the unused-local sentinels, dropping
the underscore-shadowing.
- _invoke_context_menu trusts mx/my as preconditions and no longer
defends with `or 0` defaults — the entry-point guards nil.
README documents the widget contract explicitly and captures four
v0.2 hardening notes (is_known cache, WARN rate-limit, empty-action
diagnostic, defensive nil-guard) so the deferral is traceable.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
27
README.md
27
README.md
@@ -51,6 +51,33 @@ v0.1 ships a minimal recipe-list widget:
|
||||
- Tooltip / hover-detail
|
||||
- Stack-count display
|
||||
|
||||
**v0.2 hardening notes (deferred):**
|
||||
- `is_known(ctx)` is called per recipe per frame; no per-frame memoization.
|
||||
Large recipe-registries may want a cache layer.
|
||||
- `is_known(ctx)` errors emit one `[WARN]` per failure per frame; no rate-
|
||||
limit (spammy if a recipe is permanently broken).
|
||||
- Right-click on a row with an empty action-set is silently dropped; a
|
||||
diagnostic warning would help modders catch missing `register_action`
|
||||
calls.
|
||||
|
||||
## Widget Contract
|
||||
|
||||
The widget conforms to `lib-core.panel`'s widget-lifecycle contract (see
|
||||
`lib-core/panel/README.md` §Widget-Lifecycle-Contract):
|
||||
|
||||
```lua
|
||||
widget.render(ctx)
|
||||
widget.handle_input(ctx, event)
|
||||
```
|
||||
|
||||
where `ctx = {bounds = {x,y,w,h}, theme = table, is_focused = bool}` and
|
||||
the panel dispatches input events as `{kind = "click", x, y, button}` or
|
||||
`{kind = "wheel", dy}`. Theme colours are packed-RGBA integers (e.g.
|
||||
`0xE0E0E0FF`), matching the `panel.DEFAULT_THEME` schema.
|
||||
|
||||
Right-click on a row invokes `panel.show_context_menu(x, y, actions)`
|
||||
with the registered actions; left-click and wheel are ignored in v0.1.
|
||||
|
||||
## Row Visibility + Availability rules
|
||||
|
||||
For every frame, the widget rebuilds its row-list by walking
|
||||
|
||||
Reference in New Issue
Block a user