Simal UI

Component specification

The contract every Simal UI component defines before it is released.

A component is not complete when its default state looks right. Its specification is the set of decisions below, captured in code, stories, tests, and generated documentation.

Required contract

AreaThe specification must answer
IntentWhat problem does this solve, and what does it deliberately not solve?
Public APIWhich props are controlled, uncontrolled, required, and platform-only?
StatesDefault, focused, pressed, selected, loading, disabled, empty, error, and read-only as applicable
VariantsWhich variants are semantic, and when should each be used?
ContentLabel, helper, error, truncation, localization, RTL, and long-text behavior
PlatformsWhat is shared, what differs, and why is the difference native rather than accidental?
TokensWhich semantic color, type, radius, spacing, and motion decisions it consumes
AccessibilityName, role, state, focus order, target size, keyboard behavior, and announcements
CompositionValid children/adornments and the layouts where the component must remain stable
VerificationUnit behavior, Storybook matrix, visual baselines, and any required product E2E

Story matrix

Every public component needs a Playground plus stories for the states that can change layout, meaning, or accessibility. A useful minimum is:

  • default and content-stress cases;
  • each visual variant;
  • disabled and read-only when supported;
  • loading and error when supported;
  • selected/open/checked states for interactive collections;
  • adornments and long localized labels where supported;
  • a composition example when spacing depends on surrounding controls.

The global theme toolbar provides light and dark. Visual regression captures both. Platform-specific behavior that cannot be represented faithfully by React Native Web must be called out in the story description and verified on a device separately.

Story metadata is the source of documentation

Component pages are generated from Storybook:

  • the doc comment above meta becomes the component description;
  • argTypes becomes the props table;
  • each story's doc comment and render source become an example;
  • the live preview embeds the same Storybook runtime used by visual tests.

Do not hand-edit generated component MDX. Improve the story, then run pnpm docs:sync.

Definition of done

A shared component is releasable only when:

  • its API is exported from the intended public entry point;
  • the states above are represented or explicitly marked not applicable;
  • important behavior has an active Jest test;
  • Storybook builds with no runtime error;
  • light and dark visual baselines are reviewed;
  • the accessibility panel has no new serious or critical violation;
  • generated docs include a description, import, props, and live examples;
  • package lint, type-check, tests, visual regression, and docs build pass;
  • a consumer-facing change has a release note and a new tag.

A green TypeScript build is not visual verification. A green Storybook build is not native-device verification. Report each boundary honestly.

On this page