feat(flow editor): palette entries for the 9 input reporter nodes (#208)#212
Conversation
Surface the nine built-in input reporter nodes in the flow editor so they can be authored (codegen shipped in flow-codegen#51 + the parallel more-reporters PR). All are `.other`-kind REPORTERS (rounded, data-only) producing a single `value` output read inside per-frame flows — bool for the key/mouse predicates, f32 for the mouse getters. They carry no exec pins (they sit off the exec spine) and no data INPUT pins: the key/button is an on-node FIELD, not a pin. - IsKeyDown / IsKeyPressed / IsKeyReleased: a `key` field (a KeyboardKey tag, e.g. "space"), `value` output (bool). - IsMouseButtonDown / IsMouseButtonPressed / IsMouseButtonReleased: a `button` field (a MouseButton tag, e.g. "left"), `value` output (bool). - GetMouseX / GetMouseY / GetMouseWheel: no field, `value` output (f32). Mirrors the #207 string-reporter palette path: - flow_doc.isReporterTypeName: add the nine type names so nodeVisual rounds them and the generic classifier never awards them an exec-in anchor. - flow_doc render `.other` arms: a single shared arm emits one `value` data OUTPUT for all nine (no data inputs). - flow_io.other_field_specs: `key` (.text) for the three IsKey* nodes, `button` (.text) for the three IsMouseButton* nodes; GetMouse* need no spec. Seeds round-trip as quoted JSON strings codegen parses verbatim ({ "type": "IsKeyDown", "key": "space" }). - flow_doc palette: new "Input" cluster near the String cluster, seeding key/button defaults "space" / "left"; GetMouse* seed no extras. - tests: appendOtherNode shape + seeded field, reporter classification (rounded, no exec-in), parse/render round-trip (key/button persist, load -> save byte-stable). - gui_tests: bump the hidden test window to 1280x1080 so the grown node palette's bottom "Add raw call…" escape hatch isn't clipped below the inspector child's scroll fold (TE can't auto-scroll to an item ImGui culled), keeping palette_has_plugin_section's wildcard click resolvable.
PR SummaryLow Risk Overview Editor behavior: All nine are treated as rounded reporters with a single Palette: A new Input cluster adds palette buttons for each node, seeding Tests: Unit tests cover append, reporter classification, and parse/render round-trip. The hidden gui-test window height is raised to 1080 so the taller palette keeps + Add raw call… on-screen for ImGui Test Engine clicks. Reviewed by Cursor Bugbot for commit 5ae0882. Bugbot is set up for automated code reviews on this repo. Configure here. |
There was a problem hiding this comment.
Code Review
This pull request adds support for nine input reporter nodes (key/mouse predicates and mouse getters) that poll input states and output a single value. It updates the node specifications, visual rendering, palette UI, and unit tests, as well as increasing the test window height to accommodate the expanded palette. The reviewer suggests simplifying the long chain of string comparisons in flow_doc.zig using an inline for loop to improve code readability and maintainability.
Important
The consumer version of Gemini Code Assist on GitHub is being sunset. Starting June 18, 2026, new organization installations will be blocked, and all code review activity will officially cease on July 17, 2026.
For more details on the timeline and next steps, please review the Help Documentation.
| } else if (std.mem.eql(u8, n.type_name, "IsKeyDown") or | ||
| std.mem.eql(u8, n.type_name, "IsKeyPressed") or | ||
| std.mem.eql(u8, n.type_name, "IsKeyReleased") or | ||
| std.mem.eql(u8, n.type_name, "IsMouseButtonDown") or | ||
| std.mem.eql(u8, n.type_name, "IsMouseButtonPressed") or | ||
| std.mem.eql(u8, n.type_name, "IsMouseButtonReleased") or | ||
| std.mem.eql(u8, n.type_name, "GetMouseX") or | ||
| std.mem.eql(u8, n.type_name, "GetMouseY") or | ||
| std.mem.eql(u8, n.type_name, "GetMouseWheel")) |
There was a problem hiding this comment.
The long chain of std.mem.eql with or operators can be simplified and made more maintainable by using an inline for loop over an array of the input reporter names. This leverages Zig's compile-time unrolling to generate efficient code while keeping the list of names clean and easy to read/extend.
} else if (inline for ([_][]const u8{
"IsKeyDown",
"IsKeyPressed",
"IsKeyReleased",
"IsMouseButtonDown",
"IsMouseButtonPressed",
"IsMouseButtonReleased",
"GetMouseX",
"GetMouseY",
"GetMouseWheel",
}) |name| {
if (std.mem.eql(u8, n.type_name, name)) break true;
} else false)
There was a problem hiding this comment.
Done — extracted isInputReporter(type_name) (a small static-name set, mirroring the existing isReporterTypeName helper right below it), so the .other arm now reads as a call instead of the 9-way or chain.
There was a problem hiding this comment.
Pull request overview
Adds the nine input reporter nodes to the flow editor, ensuring they render as rounded/data-only nodes, can be created from the palette with appropriate seeded fields, and round-trip through parse/render consistent with codegen.
Changes:
- Extend reporter classification +
.otherpin rendering to cover the 9 input reporters, exposing a singlevalueoutput and no exec pins. - Add
other_field_specsentries forIsKey*(key) andIsMouseButton*(button), and add an “Input” palette cluster that seeds those fields. - Adjust the hidden gui-test window height to keep the “+ Add raw call...” button visible to the ImGui Test Engine.
Reviewed changes
Copilot reviewed 4 out of 4 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
src/tests.zig |
Adds unit tests covering seeding, field specs, reporter classification, and parse/render round-trips for input reporters. |
src/modules/flow_doc.zig |
Adds .other pin rendering for input reporters, includes them in isReporterTypeName, and adds an “Input” palette section. |
src/gui_tests.zig |
Increases hidden test window height to prevent TE interactions from failing due to culled off-screen items. |
src/flow_io.zig |
Adds other_field_specs entries for input reporter editable fields (key / button). |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| // Load → save is byte-stable (these carry only string / no extras, | ||
| // so there's no numeric normalisation to settle). | ||
| var doc2 = try flow_io.parse(a, text1); |
| // Tall enough that the flow-editor inspector's node palette — which has | ||
| // grown several reporter clusters (String / Input, #207 / #208) — fits | ||
| // without the bottom "Add raw call…" escape hatch being clipped below | ||
| // the scrolling child's fold. TE can't auto-scroll a child to an item |
Adds the input REPORTER nodes (flow-codegen #51 + #52) to the editor palette — an "Input" cluster. Mirrors the #207 string-reporter path.
Nodes (9, all rounded reporters with a
valueoutput, no exec pins)IsKeyDown/IsKeyPressed/IsKeyReleased—keyfield (bool out)IsMouseButtonDown/IsMouseButtonPressed/IsMouseButtonReleased—buttonfield (bool out)GetMouseX/GetMouseY/GetMouseWheel— no field (f32 out)What
isReporterTypeName(flow_doc.zig): all 9 → rounded, no exec-in..otherpin-render arm: one shared arm emitting avalueoutput (key/button is a FIELD, not a pin).other_field_specs(flow_io.zig):key(.text) for IsKey*,button(.text) for IsMouseButton*.key="space"/button="left").{"type":"IsKeyDown","key":"space"}etc.Note (test-only)
The grown palette pushed the
+ Add raw callescape-hatch below the gui-test window's 720px fold (ImGui culls off-screen items, so the Test Engine couldn't click it). Bumped the hidden gui-test window to 1280x1080. Follow-up worth considering: the palette keeps growing (control/data/string/time/input clusters) — collapsible categories or test scroll-to-item would be more durable than raising the window.zig build test471/471;gui-test26/26;zig buildclean. Parent: labelle-gui#208.