Skip to content

Map A Design System

Map one semantic UI contract to platform components without turning the graph into a render tree.

Status: current Audience: designers, front-end leads, design-system maintainers, and agents Use when: you need to connect Topogram widgets to web, iOS, Android, or desktop component libraries.

Topogram keeps three UI layers separate:

  • ui_contract owns screens, layout usage, screen region overrides, widget placement, actions, messages, and accessibility obligations.
  • region_contract and layout_contract describe reusable semantic work areas such as header, nav, content, toolbar, filters, results, and footer actions.
  • design_contract owns the design-system scope: supported platforms, design package identity, and token mappings.
  • design_realization_set maps semantic widgets to stable platform component refs and behavior support.

The graph is not a render tree. It is a work map. Layouts say where work belongs; widgets say what reusable semantic UI is needed; realization sets say which design-system components implement those widgets on each platform. A widget such as widget_review_queue should be authored once, then mapped to the platform components that realize it.

If you only want to see the practical shape, inspect the focused proof:

Terminal window
git clone https://github.com/attebury/topogram-proof-widget-design-realization.git
cd topogram-proof-widget-design-realization
npm install
npm run verify

Then open:

  • topo/widgets/widget-data-grid.tg: the semantic widget.
  • topo/design-contracts/design-company-web.tg: platform and token scope.
  • topo/design-contracts/realization-set-company-web-widgets.tg: widget-to-platform component mappings.
  • proof/artifacts/ui-design-coverage.md: the designer-readable matrix.
  • proof/artifacts/widget-slice.json: the agent packet for changing the widget.

The matrix is the first artifact to read. It groups the widget by platform, viewport, density, component ref, behavior support, and review state, so design review starts from a component matrix instead of raw graph records.

Start with reusable structure and the shared widget:

region_contract region_collection_results {
name "Collection Results"
description "Primary collection result area."
kind results
pattern resource_table
placement primary
states [loading empty error]
allowed_widget_patterns [resource_table card_list]
status active
}
layout_contract layout_collection_list {
name "Collection List Layout"
description "Collection screen layout with result content."
region {
id results
uses region_collection_results
}
status active
}
widget widget_review_queue {
name "Review Queue"
description "Reusable queue for reviewing submitted items."
category collection
patterns [resource_table card_list]
regions [results toolbar]
status active
}
projection proj_ui_contract {
type ui_contract
screens {
screen review_queue title "Review Queue" kind list layout layout_collection_list
}
widget_bindings {
screen review_queue region results widget widget_review_queue data rows from cap_list_items
}
status active
}

Define the design contract as the platform and token header:

design_contract design_acme_product_ui {
name "Acme Product UI"
description "Acme product design-system scope."
platforms [web ios android]
library acme_product_ui
package "@acme/product-ui"
token_mappings {
color_role danger token "acme.color.danger"
typography_role body token "acme.type.body"
action_role destructive token "acme.action.destructive"
}
status active
}

Map widgets with a widget-first realization set:

design_realization_set realization_set_review_queue {
name "Review Queue Realizations"
description "Maps the Review Queue widget to Acme platform components."
design_contract design_acme_product_ui
status active
widget_realization {
id review_queue_web_grid
widget widget_review_queue
platform web
viewport wide
component_ref "acme.reviewQueue.grid"
pattern resource_table
density compact
state_coverage [loading empty error]
role_contexts [reviewer manager]
theme_contexts [light dark]
locale_contexts [default_locale]
review_notes "Bulk action is contract-only until the grid adapter proves it."
status rendered
behaviors_rendered [selection sorting]
behaviors_contract_only [bulk_action]
}
widget_realization {
id review_queue_ios_list
widget widget_review_queue
platform ios
viewport any
component_ref "acme.reviewQueue.list"
pattern card_list
density comfortable
state_coverage [loading empty error]
role_contexts [reviewer]
theme_contexts [system]
locale_contexts [default_locale]
status implementation_owned
behaviors_rendered [selection]
behaviors_implementation_owned [bulk_action]
}
widget_realization {
id review_queue_android_cards
widget widget_review_queue
platform android
viewport any
component_ref "acme.reviewQueue.cards"
pattern card_list
density comfortable
state_coverage [loading]
role_contexts [reviewer]
theme_contexts [system]
locale_contexts [default_locale]
status unsupported
behaviors_unsupported [bulk_action]
}
}

Use component_ref as a stable design-system identity. Do not use source import paths such as src/components/ReviewQueueGrid. Import paths move when code is refactored; component refs describe the design-system contract.

Run coverage before claiming parity:

Terminal window
topogram query ui-design-coverage ./topo --projection proj_web_surface --json
topogram emit ui-realization-report ./topo --projection proj_web_surface --json
topogram query slice ./topo --widget widget_review_queue --json

Review these states:

  • rendered: the generator or maintained implementation proves the mapping.
  • contract_only: the semantic mapping exists, but behavior needs implementation or stronger proof.
  • implementation_owned: maintained/native code owns the realization.
  • unsupported: the platform does not support that widget or behavior yet.
  • missing platform: the design contract declares a platform with no matching widget realization.
  • missing state: a realization has not declared required loading, empty, or error state coverage.
  • missing token, accessibility, or i18n: the widget has no mapped design token, authored accessibility obligation, or message key evidence.

Unsupported and contract-only entries are developer/agent review work. They should appear in reports and slices, not disappear behind generic fallback UI.

For designer review, use Markdown:

Terminal window
topogram query ui-design-coverage ./topo --projection proj_web_surface --format markdown

That output is a widget-first matrix. It is easier to read at scale than raw .tg records because each row shows the widget, platform, viewport, density, component ref, state coverage, and review status.

Use that matrix as the shared review surface:

  • designers confirm component refs, states, density, and platform expectations;
  • front-end leads confirm whether each component ref is implemented or owned by maintained code;
  • agents use the review rows to find unsupported, contract-only, missing-state, missing-token, missing-i18n, and missing-accessibility work.

Extractor packages may propose design_realizations candidates when they see a custom data grid, native list, or bespoke component that appears to implement a known widget. These candidates are review-only:

return {
findings: [],
candidates: {
design_realizations: [{
id_hint: "review_queue_web_grid",
realization_set_id_hint: "realization_set_review_queue",
design_contract_id_hint: "design_acme_product_ui",
widget_id: "widget_review_queue",
platform: "web",
viewport: "wide",
component_ref: "acme.reviewQueue.grid",
pattern: "resource_table",
status: "rendered",
behaviors_rendered: ["selection"],
behaviors_contract_only: ["bulk_action"],
confidence: "medium",
evidence: [{ file: "src/review/ReviewQueue.tsx", reason: "Uses Acme ReviewQueueGrid." }],
missing_decisions: ["Confirm bulk action behavior support."]
}]
},
diagnostics: []
};

topogram adopt design-realizations --write only writes canonical design_realization_set records after the referenced widget and design contract exist or are selected in the same adoption plan.

Figma and Storybook are evidence sources, not the design source of truth. The first Storybook bridge is package-backed and intentionally narrow: @topogram/extractor-storybook-design reads static CSF story files with explicit parameters.topogram metadata and emits review-only design_realizations candidates. It does not run Storybook, parse MDX, use screenshots, or replace design_contract and design_realization_set.

A future Figma bridge should also propose component refs and variants from design component identity, but those proposals should stay review-only until a human or agent adopts them.

For the built-in proof fixture:

Terminal window
topogram query ui-design-coverage engine/tests/fixtures/workspaces/app-basic --projection proj_web_surface --json
topogram query ui-design-coverage engine/tests/fixtures/workspaces/app-basic --projection proj_web_surface --format markdown
topogram emit ui-realization-report engine/tests/fixtures/workspaces/app-basic --projection proj_web_surface --json
topogram query slice engine/tests/fixtures/workspaces/app-basic --widget widget_data_grid --detail compact --json

For project work, replace the fixture path with ./topo.