Appearance
Live CSS Preview Implementation Plan
Status: COMPLETED (2026-03-24)
Goal: Provide instant visual feedback in the preview iframe during scrub drag by updating DataStore directly instead of full engine rebuild.
Architecture: During scrub, LocalBuildPreview sends block data to the iframe via a creative-block-update CustomEvent. preview-iframe.ts deep-merges into DataStore.creativeSettings.creativeBlocks, and Vue 3's deep reactivity automatically regenerates the affected block's CSS. One full rebuild fires on mouseup.
Tech Stack: Vue 3 reactivity (Creative Engine), Vue 2 Options API (Application-Frontend), CustomEvent for iframe communication.
Spec: docs/superpowers/specs/2026-03-24-live-css-preview-design.md
Key finding: DataStore.creativeSettings was a plain {} — wrapping it in reactive() was the critical missing piece that made the entire approach work.
File Structure
| File | Repo | Change | Purpose |
|---|---|---|---|
src/services/dataStore.ts | Creative-Engine | Modify (1 line) | Wrap creativeSettings in reactive() |
src/entry.ts | Creative-Engine | Already exported | DataStore export |
src/preview-iframe.ts | Application-Frontend | Modify (~30 lines) | Handle creative-block-update event with deep-merge |
src/pages/.../Preview/LocalBuildPreview.vue | Application-Frontend | Modify (~30 lines) | Send block updates during scrub, MutationObserver for scrub end |
Task 1: Export DataStore from Creative Engine
- [x] Step 1: Add DataStore export — already present in entry.ts
- [x] Step 2: Verify build — clean
- [x] Step 3: Commit —
feat: export DataStore for live preview integration
Task 2: Make creativeSettings reactive
- [x] Step 1: Wrap in reactive() —
creativeSettings: reactive({} as CreativeSettings)in dataStore.ts:52 - [x] Step 2: Verify build — clean (tsc --noEmit exit 0)
- [x] Step 3: Commit —
feat: make creativeSettings reactive for live preview support
Task 3: Add block update event handler in preview-iframe
- [x] Step 1: Add DataStore import
- [x] Step 2: Add event listener + deepMergeReactive
- [x] Step 3: Verify build — clean
- [x] Step 4: Commit —
feat: handle creative-block-update event for live CSS preview+refactor: use deep-merge for block update to preserve reactive proxies
Task 4: Send block updates from LocalBuildPreview during scrub
- [x] Step 1: Add lodash get import
- [x] Step 2: Add selectedBlockPath to mapState
- [x] Step 3: Update watcher to send block update during scrub
- [x] Step 4: Add sendBlockUpdate method
- [x] Step 5: Add MutationObserver for scrub-end rebuild
- [x] Step 6: Verify build — clean
- [x] Step 7: Commit —
feat: send block updates to iframe for live CSS preview during scrub
Task 5: Manual verification
- [x] Tested and confirmed working by user (2026-03-24)