Repository navigation
Conversation
The UI elements board asks for many new components, but nothing told a contributor where a component goes, how it names its props and events, who owns its state, or what evidence a PR needs. The one open component PR put its file in engine/components and shipped keyboard handlers that never fire, which the existing structure would have ruled out. docs/COMPONENTS.md writes down the rules VirtualList and CameraView already follow: placement in packages/elements, the .tsx/.css/.d.ts/index/exports files, function components unless a resource needs an explicit cleanup method, the Component<GeaElement, Props> shape for class components with props destructured in template, controlled state, native-control prop names, and class maps for state with the caller's class on the root and fixed part classes inside. It checks the two existing components against the contract. It proposes typed onChange(next) as the one rule without precedent, and notes that native elements now use onChange for a committed InputEvent. Both READMEs link to it. It records what the targets and the engine cannot do yet: - How control tags render on the pixel engine (ESP32, RP2350, WASM simulator, Linux, Android), macOS, iOS (a UIKit view per node) and Windows (radio as a text field, select and stepper as plain views). A new native tag needs a NodeType, a Document factory, both geatsc tag maps, an intrinsic typing and a mapping in each native renderer. - The browser target, the default for gea dev and gea simulate, is not evidence for a native target. Pebble has its own engine and is out of scope. - Stylesheet rules have no :focus/:checked/:disabled, attribute selectors or +/~ combinators; .name:active sets background-color only. The DOM queries (querySelector, matches, closest) accept attribute selectors and :disabled. - onFocus/onBlur are dropped on every native target. focusin and focusout fire when the active input changes, including on a tap outside every input and on focus(), which a native renderer can refuse. Key events target the focused node and bubble; onKeyDown on a component root becomes a document-level listener. There is no Tab order or focus ring, so components attach no key handlers until core#5. - A Style object prop forwarded to a JSX style attribute fails as a C++ static_assert, so components take no style prop. - The bitmap font is ASCII only. It lists the example, pipeline test and target matrix a PR must bring, with a separate level for browser-only testing. For animation tests it says to call startCssAnimations before each pumpFrame, as core/runtime.cpp does on the device, and to re-query nodes after a function component re-renders. It notes that the model pipeline test builds with --allow-any. Tests: documentation only; nothing was built or run. Each claim was checked in the source at geastack/core 617eb3f and the sibling repos, including macos_renderer.mm, view_reconciler.mm, ios_main.mm, win32_renderer.cpp, rpios_display.cpp, android_display.cpp, tree_events.cpp, runtime.cpp, node.cpp, touch_runtime.cpp, input.cpp, selector.cpp, style.cpp, node_model.h, cpp-mounted-lowering.ts, cpp-mounted.ts, cpp-template-renderer.ts, build-gea-vite-geatsc.mjs, gea_runtime.h, packages/core/index.d.ts, BookCover.tsx and the cli README, and every cited path exists. The style-prop and animation-test limits were hit while building ProgressBar, whose pipeline test passes with the described approach.
|
Important
This repository does not receive automatic reviews because it has fewer than 10 stars. ⚙️ Run configuration
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
This was referenced Oct 17, 2026
Open
A native build resolves value imports of @geastack/elements to
components/index.ts, not index.d.ts. The contract listed the props type
export only for index.d.ts, so a component following it shipped a type
that `import { Name, type NameProps }` accepts in tsc but geatsc rejects
with "has no exported member". The Files table now puts the type export
in index.ts too, and a paragraph explains why.
Tests: a scratch app that imports InlineAlert with its variant type this
way fails to build natively while index.ts lacks the type and builds
once it has it; the same holds for ProgressBarProps and the VirtualList
types (core#69, core#71).
Author
|
Pushed 77136e9: the Files table now puts the props type export in |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #2.
Problem
The UI elements board lists many components to build, but nothing tells a contributor where a component goes, how to name its props and events, who owns its state, or what a PR has to prove. The first open component PR put its files in
engine/componentsand shipped key handlers that never fire. A written contract would have ruled both out.Change
docs/COMPONENTS.md, linked from both READMEs. It writes down the rulesVirtualListandCameraViewalready follow and checks both components against them:packages/elements, plus the.tsx/.css/.d.ts/index/exportsfiles a component touches;Component<GeaElement, Props>, props destructured intemplate) is only for a component that owns a resource and needs an explicit cleanup method;classon the root and fixed part classes inside;It also records what the engine and targets cannot do yet, so components don't depend on it:
:focus/:checked/:disabledor attribute selectors in stylesheets;onFocus/onBlurare dropped;styleprop forwarding;Open question for review
The doc proposes
onChange(next: T)with a typed value as the one rule with no precedent in the existing elements. Native elements now useonChange(event: InputEvent)for a committed change, so the same name would carry a different payload on a component. The doc says so and leaves the choice to you. Settling it before #22–#46 land would avoid renames.Tests
Documentation only; nothing was built or run. Each claim was checked against the source it cites at
617eb3fand in the apple, windows, cli, debugger and examples repos, and every cited path exists. Two limits were found while building the ProgressBar (#69): the style-prop limit and the need to callstartCssAnimationsbefore eachpumpFramein a test.