Skip to content

feat: shared screens / reusable components#41

Merged
trmquang93 merged 1 commit intomainfrom
feat/reusable-components
Apr 26, 2026
Merged

feat: shared screens / reusable components#41
trmquang93 merged 1 commit intomainfrom
feat/reusable-components

Conversation

@trmquang93
Copy link
Copy Markdown
Collaborator

Summary

  • Let users explicitly mark screens as reusable components so AI build instructions describe each component once and link from every placement, instead of regenerating the same code multiple times.
  • Instances mirror their canonical's image and hotspots at render time — edits on the canonical propagate live; hotspot editing is canonical-only.
  • Generated instructions add a components/<slug>.md file per canonical with a Placements table; instance entries in screens.md are stubs that link to it.

Implementation

  • Data model (useScreenManager.js): adds componentId / componentRole to screens, new setScreenComponent(id, mode) action with auto-promotion of the first instance when a canonical is deleted; duplicateSelection demotes copied canonicals to instances.
  • Backward compat (importFlow.js): backfills missing fields and enforces one canonical per componentId (drops orphan instances, demotes duplicate canonicals).
  • UI: Sidebar Component section (mark canonical / "Instance of…" picker / unlink / open canonical), ScreensPanel context-menu items, ScreenNode purple border + ⟳ Component / ↗ Instance pills, theme tokens.
  • Render-time visual swap (resolveInstanceVisuals.js): pure helper that merges canonical's imageData, dimensions, and hotspots into an instance at draw time. Hotspot edits, + Link, drag-to-create, and resize handles are gated off on instances.
  • Instruction generation (generateInstructionFiles.js): exported getComponentGroups; instances render as a stub linking to the canonical's component file; canonicals get a "see component file" header; main.md adds a components/ row only when canonicals exist; new generateComponentFiles emits per-component markdown with a Placements table (canonical + instances, link counts) and full spec.
  • MCP (mcp-server): update_screen accepts componentId (string|null) and componentRole (canonical|instance|null).
  • Docs: user guide gets a "Reusable Components" section.

Test plan

  • npm test — 685 tests across 36 files passing (added 8 for resolveInstanceVisuals + 10 for component grouping = 18 new)
  • npm run lint — 0 errors, 0 warnings
  • npm run build — success (only pre-existing chunk-size advisory)
  • Manual: mark canonical → mark another instance → instance image swaps to canonical's, hotspots mirror, edits propagate live
  • Manual: delete canonical → first instance auto-promotes
  • Manual: duplicate a canonical → copy is an instance, not a second canonical
  • Manual: generate instructions → exactly one components/<slug>.md per canonical, instance entries are stubs

Let users explicitly mark screens as reusable components so the AI build
instructions describe each component once instead of duplicating code for
every placement.

- Sidebar + context-menu UI to mark canonical / pick "Instance of…" / unlink
- Purple `⟳ Component` and `↗ Instance` pills on the canvas
- Instances render the canonical's image and hotspots at draw time, so edits
  on the canonical propagate live; hotspot editing is canonical-only
- generateInstructionFiles emits one `components/<slug>.md` per canonical;
  instances in `screens.md` link to it instead of duplicating the spec
- Auto-promotion: deleting a canonical promotes the first instance, so
  groups can never become orphaned
- importFlow backfills the new fields and enforces one canonical per group
- MCP `update_screen` accepts componentId / componentRole
- User guide updated
@trmquang93 trmquang93 merged commit 23826c6 into main Apr 26, 2026
1 check passed
@trmquang93 trmquang93 deleted the feat/reusable-components branch April 26, 2026 23:52
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant