Refactor themes & motion UI; replace presets with user-saved themes - #460
Conversation
- De-emphasise power knobs and move them to a collapsed "Advanced" section at the end of each category (borders, shadows, spacing, motion, typography). - Home panel links to every token domain and tool, and surfaces saved themes with a quick "save current" action. - Replace curated theme presets with user-saved themes: a new savedThemes store (localStorage) backs save/apply/delete in the Themes panel and Home. - Remove opinionated style presets (corner style, elevation, density, text shadow) so all design options are token-driven; text-shadow edited per token. - Font-weight pickers offer the full 100-900 numeric scale. - Reposition previews: shadows elevation and spacing scale previews move to the top of their categories; motion duration preview sits inside the durations group; borders radius preview stays within the radius group. - Reorganise the Motion panel into Live preview / Durations / Easing / Stagger / Advanced. Easing tokens are now editable and the live demo plays a chosen easing + duration so changes are visible. - Shadow glow now has a working preview bound to --sf-shadow-glow. - Flow space and other var-based sliders (prose spacing, media radius, scroll shadow size) gained raw-input mode for entering variables/expressions. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MW6NcRM3dtJndBz9kgXnL7
|
Warning Review limit reached
Next review available in: 31 minutes Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available. How can I continue?After more reviews become available, a review can be triggered using the To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews. How do review limits work?CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability. For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window. Please refer docs for additional details. Review details⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Plus Run ID: 📒 Files selected for processing (10)
📝 WalkthroughWalkthroughRemoves the curated ChangesPreset Removal and Saved Themes Refactor
Estimated code review effort🎯 4 (Complex) | ⏱️ ~60 minutes Possibly related PRs
Suggested labels
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
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 |
PR Summary by QodoRefactor themes & motion UI; replace presets with user-saved themes
AI Description
Diagram
High-Level Assessment
Files changed (17)
|
Code Review by Qodo
Context used✅ Compliance rules (platform):
6 rules 1.
|
There was a problem hiding this comment.
Actionable comments posted: 6
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@configurator/src/components/panels/EffectsPanel.svelte`:
- Around line 283-292: The controlled input in EffectsPanel.svelte is trimming
on every keystroke, which breaks multi-word values like space-separated shadows.
Update the oninput handler for the input bound to overrides[t.token] so it reads
the raw HTMLInputElement value, uses a trimmed check only to decide between
onSet and onReset, and stores the untrimmed value when calling onSet; keep any
trimming behavior out of the per-keystroke path, using on blur only if needed.
In `@configurator/src/components/panels/MotionPanel.svelte`:
- Around line 133-150: The easing and duration controls in MotionPanel.svelte
are unlabeled selects, so add accessible names to both dropdowns. Update the
select elements tied to demoEase and demoDuration with distinct aria-labels or
visible labels so assistive technologies can distinguish the easing picker from
the duration picker.
In `@configurator/src/components/panels/ThemesPanel.svelte`:
- Around line 104-108: The delete control in ThemesPanel.svelte is only revealed
via group hover, so it remains hidden for keyboard and touch users. Update the
button styling in the theme row markup so the delete action becomes visible on
focus/focus-within as well, and consider showing it by default for
non-hover/small-screen contexts; keep the change localized to the delete button
around handleDelete(theme.id) and the surrounding group-hover classes.
In `@configurator/src/components/panels/TypographyPanel.svelte`:
- Line 69: The weight picker in TypographyPanel.svelte now exposes weights that
the Google font loader does not request, so custom fonts can fall back to
synthesized styles. Update injectGoogleFont to request the full weight range
used by WEIGHT_OPTIONS, including the lighter and heavier values, and keep the
weight list in sync with the options shown in the panel.
In `@configurator/src/lib/savedThemes.ts`:
- Around line 25-31: The persistence flow in write() is swallowing localStorage
quota/security failures, so save/delete/rename callers still act as if the theme
list was persisted successfully. Update the savedThemes helpers that call
write() to detect and propagate persistence failure from write() instead of
always returning the updated list, and ensure the public save/delete/rename
paths only report success when the localStorage write actually succeeds.
- Around line 13-20: The read() helper in savedThemes.ts is accepting any parsed
array as SavedSlot[] without validating the record shape, which lets malformed
or legacy localStorage entries slip through. Update read() to filter/validate
each parsed item before returning it, ensuring every SavedSlot has the expected
fields including overrides, and discard invalid entries so downstream uses like
Object.keys(theme.overrides) in the saved-themes panels cannot fail.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro Plus
Run ID: 938b7143-4d87-4841-aef1-eaf171726cdd
📒 Files selected for processing (17)
configurator/src/App.svelteconfigurator/src/components/DomainPanel.svelteconfigurator/src/components/inputs/PowerKnobRow.svelteconfigurator/src/components/inputs/StylePresetCards.svelteconfigurator/src/components/panels/BordersPanel.svelteconfigurator/src/components/panels/EffectsPanel.svelteconfigurator/src/components/panels/HomePanel.svelteconfigurator/src/components/panels/MacrosPanel.svelteconfigurator/src/components/panels/MotionPanel.svelteconfigurator/src/components/panels/ShadowsPanel.svelteconfigurator/src/components/panels/SpacingPanel.svelteconfigurator/src/components/panels/ThemesPanel.svelteconfigurator/src/components/panels/TypographyPanel.svelteconfigurator/src/lib/savedThemes.tsconfigurator/src/lib/stylePresets.tsconfigurator/src/lib/themes.tsconfigurator/src/types.ts
💤 Files with no reviewable changes (4)
- configurator/src/lib/stylePresets.ts
- configurator/src/types.ts
- configurator/src/lib/themes.ts
- configurator/src/components/inputs/StylePresetCards.svelte
- savedThemes: validate SavedSlot shape on read() to guard against malformed/legacy localStorage entries crashing ThemesPanel - savedThemes: write() now returns boolean; save/delete/rename only report success when the localStorage write actually succeeds - MotionPanel/ShadowsPanel: guard parseFloat results with isFinite() to prevent NaN propagating into sliders, transitions, and timers - MotionPanel: add aria-label to easing/duration preview selects - EffectsPanel: stop trimming on every keystroke so multi-word shadow values (e.g. "0 4px 8px ...") can be typed without spaces being stripped mid-entry - TypographyPanel: expand Google Fonts weight request from 300–700 to 100–900 to match the full WEIGHT_OPTIONS range - ThemesPanel: make delete button visible on focus and touch (was opacity-0 until group hover only, inaccessible to keyboard users) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MW6NcRM3dtJndBz9kgXnL7
On narrow screens the fixed rail + 360px panel + preview split left the live preview off-screen and overflowed several toolbars. Now: - Below the md breakpoint the body folds to a single full-width column with a Controls ⇄ Preview toggle bar; each view folds the other away so both the panel and the preview are fully usable on mobile. Desktop keeps the side-by-side layout unchanged. - Header sheds secondary actions on small screens (share, import, the subtitle, and the "customised ·" label) so nothing is clipped. - Preview toolbar wraps instead of cutting off; the template-tab group scrolls horizontally so every template stays reachable. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MW6NcRM3dtJndBz9kgXnL7
…board previews - Restore the Share and Import header buttons on small screens (all toolbar actions are now always visible); reclaim the space by collapsing only the brand text to the logo below the sm breakpoint, which removes no functionality. - Remove the Docs and Dashboard live-preview templates entirely (TEMPLATES entries, DOCS_BODY/DASHBOARD_BODY bodies, BODIES map, and the PreviewTemplate union). Marketing, Components and Stylescape remain. previewTemplate is in-memory only, so no stored value can reference the removed templates. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MW6NcRM3dtJndBz9kgXnL7
Summary
This PR replaces the curated theme preset system with a user-driven saved themes feature, and significantly refactors the Motion panel to improve easing/duration editing and preview experience. The Themes panel now lets users save their current configuration as a named theme and re-apply it later (stored in localStorage), rather than applying pre-baked design system presets.
Key Changes
Themes System
lib/themes.ts(8 curated preset themes) andPresetThemetypelib/savedThemes.tswith localStorage-backed theme persistence:listSavedThemes()— retrieve all saved themessaveTheme(name, overrides)— create a new theme snapshotdeleteTheme(id)— remove a saved themerenameTheme(id, name)— update theme nameSavedSlottype to replacePresetTheme(same shape, different semantics)ThemesPanel.svelte:Motion Panel Overhaul
cubic-bezier(0.34, 1.56, 0.64, 1)tolinear(0, 0.6 30%, 1.08 55%, 0.98 75%, 1)for smoother behavioreaseValue(token)to resolve easing overrides with fallback to defaultsHome Panel Updates
Spacing & Borders Panels
StylePresetCardscomponent and preset UIType System
PresetThemeinterfaceSavedSlot(now the primary theme type)StylePresetinterface (no longer used)Cleanup
lib/stylePresets.ts(corner, shadow, text-shadow presets)https://claude.ai/code/session_01MW6NcRM3dtJndBz9kgXnL7
Summary by CodeRabbit
New Features
Bug Fixes