@atomazing-org/design-system 1.2.9 → 2.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +92 -0
- package/README.MD +47 -392
- package/dist/index.d.ts +21 -1000
- package/dist/index.js +37 -118
- package/dist/presets/index.d.ts +26 -7
- package/dist/presets/index.js +339 -2
- package/dist/{typography-Dq0wCojD.d.mts → typography-B-BeIk0v.d.ts} +4 -5
- package/migrations/README.UPDATE.md +41 -0
- package/migrations/docs/migrations/design-system/README.md +100 -0
- package/migrations/docs/migrations/design-system/routes/adopt-existing/AEROCRM-EXAMPLE.md +197 -0
- package/migrations/docs/migrations/design-system/routes/adopt-existing/RUNBOOK.md +194 -0
- package/migrations/docs/migrations/design-system/routes/adopt-existing/migration.spec.json +109 -0
- package/migrations/docs/migrations/design-system/routes/greenfield/RUNBOOK.md +61 -0
- package/migrations/docs/migrations/design-system/routes/greenfield/migration.spec.json +58 -0
- package/migrations/docs/migrations/design-system/routes/mui4-to-latest/RUNBOOK.md +140 -0
- package/migrations/docs/migrations/design-system/routes/mui4-to-latest/migration.spec.json +143 -0
- package/migrations/docs/migrations/design-system/routes/mui4-to-latest/token-map.csv +4 -0
- package/migrations/docs/migrations/design-system/schema/migration.spec.schema.json +63 -0
- package/migrations/docs/migrations/design-system/shared/FOUNDATION.md +39 -0
- package/migrations/docs/migrations/design-system/shared/WORKING-RULES.md +194 -0
- package/migrations/docs/migrations/design-system/shared/acceptance.md +83 -0
- package/migrations/docs/migrations/design-system/shared/common-regressions.md +218 -0
- package/migrations/docs/migrations/design-system/shared/gates.md +71 -0
- package/migrations/docs/migrations/design-system/shared/manual-qa-matrix.md +70 -0
- package/migrations/docs/migrations/design-system/shared/phase-exit-criteria.md +129 -0
- package/migrations/docs/migrations/design-system/shared/phases.md +377 -0
- package/migrations/docs/migrations/design-system/shared/rollback.md +13 -0
- package/migrations/skills/design-system-consumer-agent/SKILL.md +84 -0
- package/migrations/skills/design-system-migration-agent/SKILL.md +158 -0
- package/package.json +40 -17
- package/dist/chunk-OYZ4FCLV.mjs +0 -2
- package/dist/chunk-OYZ4FCLV.mjs.map +0 -1
- package/dist/index.d.mts +0 -1181
- package/dist/index.js.map +0 -1
- package/dist/index.mjs +0 -273
- package/dist/index.mjs.map +0 -1
- package/dist/presets/index.d.mts +0 -17
- package/dist/presets/index.js.map +0 -1
- package/dist/presets/index.mjs +0 -2
- package/dist/presets/index.mjs.map +0 -1
- package/dist/typography-Dq0wCojD.d.ts +0 -121
package/AGENTS.md
ADDED
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
# @atomazing-org/design-system Agent Rules
|
|
2
|
+
|
|
3
|
+
These instructions apply when a repository depends on `@atomazing-org/design-system`
|
|
4
|
+
or when an AI agent is asked to integrate, upgrade, or refactor work around this library.
|
|
5
|
+
|
|
6
|
+
## Source Of Truth
|
|
7
|
+
|
|
8
|
+
- `README.MD`
|
|
9
|
+
- `migrations/docs/migrations/design-system/shared/WORKING-RULES.md`
|
|
10
|
+
- `migrations/skills/design-system-consumer-agent/SKILL.md`
|
|
11
|
+
- `migrations/skills/design-system-migration-agent/SKILL.md`
|
|
12
|
+
|
|
13
|
+
If you are working inside `examples/next-app-router`, load
|
|
14
|
+
`examples/next-app-router/AGENTS.md` and treat it as the local source of truth for
|
|
15
|
+
that starter.
|
|
16
|
+
|
|
17
|
+
## Default Integration Rules
|
|
18
|
+
|
|
19
|
+
1. Use only public imports:
|
|
20
|
+
- `@atomazing-org/design-system`
|
|
21
|
+
- `@atomazing-org/design-system/presets`
|
|
22
|
+
2. Do not deep-import internal files from `src/*`, `dist/*`, or private folders.
|
|
23
|
+
3. Use `ThemeProviderWrapper` as the app-level design-system entrypoint.
|
|
24
|
+
4. Use `useThemeSettings()` for theme and dark-mode UI state instead of parallel custom state.
|
|
25
|
+
5. Prefer:
|
|
26
|
+
- `defaultThemes` for standard application surfaces
|
|
27
|
+
- `landingPageThemes` for landing and marketing surfaces
|
|
28
|
+
- `allBuiltInThemes` only when the consumer intentionally wants both packs
|
|
29
|
+
6. Custom presets must use the `ThemePreset` contract with both light and dark schemes.
|
|
30
|
+
7. Do not create a competing root `ThemeProvider` unless it is a thin wrapper around the design system.
|
|
31
|
+
8. For SSR and Next.js:
|
|
32
|
+
- keep the provider in a client boundary
|
|
33
|
+
- do not access `window`, `document`, or `localStorage` at module scope
|
|
34
|
+
9. After dependency, provider, or theme-state changes, the app must still boot in a real browser without startup console errors.
|
|
35
|
+
10. Fix duplicated runtime singleton warnings for `react`, `react-dom`, `@emotion/react`, or `@emotion/styled` before closing migration work.
|
|
36
|
+
11. The active preset must own the application background.
|
|
37
|
+
12. Do not hardcode page-level backgrounds on app shells, route layouts, or page wrappers when that overrides the preset background.
|
|
38
|
+
13. Prefer direct MUI primitives or thin wrappers around them for base controls.
|
|
39
|
+
14. Do not preserve consumer-owned substitute atoms for stock MUI controls unless they carry real custom behavior.
|
|
40
|
+
15. Visible application text should be rendered through `Typography` with an explicit semantic variant.
|
|
41
|
+
16. When MUI interactive controls render visible text, wrap that text in `Typography component="span"` instead of leaving raw text nodes in place.
|
|
42
|
+
17. Shared dialogs, drawers, and bottom sheets must expose stable `aria-labelledby` and `aria-describedby`.
|
|
43
|
+
18. Shared overlay close actions must have explicit accessible labels.
|
|
44
|
+
19. Search overlays that own keyboard-filtered results should use `combobox` and `listbox` semantics.
|
|
45
|
+
20. Browser event listeners belong in effects with cleanup, not render paths or module scope.
|
|
46
|
+
21. Keep preset selection explicit in one app-owned theme module.
|
|
47
|
+
22. Remove zero-value wrappers that only rename a stock MUI primitive or surface.
|
|
48
|
+
23. Use theme helpers such as `alpha()` instead of palette-string alpha suffix hacks.
|
|
49
|
+
24. Decorative gradients and shadow styling do not belong in normal consumer surfaces.
|
|
50
|
+
25. If several app pages share the same workflow shell, extract one shared layout contract.
|
|
51
|
+
26. If local app barrel exports introduce circular chunk warnings, use direct local imports instead.
|
|
52
|
+
27. Fix consumer-owned build warnings with config changes, not warning suppression.
|
|
53
|
+
|
|
54
|
+
## Generic Landing Principles
|
|
55
|
+
|
|
56
|
+
Apply these rules when working on landing-style consumers in general:
|
|
57
|
+
|
|
58
|
+
1. Use `landingPageThemes` intentionally for landing and marketing surfaces.
|
|
59
|
+
2. Let the active preset own the page background.
|
|
60
|
+
3. Keep one primary focus per major section.
|
|
61
|
+
4. Keep scroll natural; avoid forced snap or automatic section scrolling.
|
|
62
|
+
5. Prefer product-facing labels over template-facing labels in visible UI.
|
|
63
|
+
6. Do not recreate preset-owned surface styling in app components.
|
|
64
|
+
7. Prefer MUI-native composition over custom decorative UI logic.
|
|
65
|
+
8. Do not build nested rectangular surface hierarchies.
|
|
66
|
+
9. Keep landing content concise and easy to scan.
|
|
67
|
+
|
|
68
|
+
## When To Propose A Migration
|
|
69
|
+
|
|
70
|
+
Propose a route-based migration before making piecemeal edits if any of the following are true:
|
|
71
|
+
|
|
72
|
+
- the app uses `@material-ui/*`
|
|
73
|
+
- the app already has a custom theme or token layer
|
|
74
|
+
- the app has widespread hardcoded UI tokens that should move to theme values
|
|
75
|
+
- the user asks to adopt, align, standardize, upgrade, or replace the current UI foundation
|
|
76
|
+
- partial integration would leave two competing sources of truth for theme state
|
|
77
|
+
- the app hardcodes root-level page backgrounds that should instead come from the active preset
|
|
78
|
+
|
|
79
|
+
## Route Selection
|
|
80
|
+
|
|
81
|
+
- `@material-ui/*` found in dependencies or imports: use `mui4-to-latest`
|
|
82
|
+
- no existing theme or token migration is needed: use `greenfield`
|
|
83
|
+
- otherwise: use `adopt-existing`
|
|
84
|
+
|
|
85
|
+
## Required Migration Response
|
|
86
|
+
|
|
87
|
+
When migration is the correct path, the agent should:
|
|
88
|
+
|
|
89
|
+
1. Say that route-based migration is recommended instead of ad hoc edits.
|
|
90
|
+
2. Name the selected route and why it applies.
|
|
91
|
+
3. Load `migrations/skills/design-system-migration-agent/SKILL.md`.
|
|
92
|
+
4. Use the runbook and shared gates from `migrations/docs/migrations/design-system/`.
|
package/README.MD
CHANGED
|
@@ -1,46 +1,28 @@
|
|
|
1
1
|
# @atomazing-org/design-system
|
|
2
2
|
|
|
3
|
-
Modern MUI v7 + Emotion design system with strongly differentiated visual presets,
|
|
4
|
-
|
|
5
|
-
## Preview
|
|
6
|
-

|
|
7
|
-
|
|
8
|
-
## Why use it
|
|
9
|
-
|
|
10
|
-
- **True light/dark themes**: each preset ships **two curated schemes** (`light` + `dark`), so backgrounds, cards, and text actually change (not just `palette.mode`).
|
|
11
|
-
- **Works out of the box**: includes ready-made presets you can use immediately.
|
|
12
|
-
- **Easy to extend**: bring your own presets, or combine defaults + custom.
|
|
13
|
-
- **Consistent UI**: global styles + MUI component overrides for predictable visuals.
|
|
14
|
-
- **Safe persistence**: remembers selected theme + dark mode with SSR-safe guards.
|
|
15
|
-
|
|
16
|
-
---
|
|
17
|
-
|
|
3
|
+
Modern MUI v7 + Emotion design system with strongly differentiated visual presets,
|
|
4
|
+
scheme-based light and dark tokens, SSR-safe theming, and persistence.
|
|
18
5
|
|
|
19
6
|
## Installation
|
|
20
7
|
|
|
21
|
-
Install the library:
|
|
22
|
-
|
|
23
8
|
```bash
|
|
24
9
|
npm install @atomazing-org/design-system
|
|
10
|
+
npm install react react-dom @mui/material @emotion/react @emotion/styled
|
|
25
11
|
```
|
|
26
12
|
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
```bash
|
|
30
|
-
npm install @mui/material @mui/icons-material @emotion/react @emotion/styled
|
|
31
|
-
```
|
|
32
|
-
|
|
33
|
-
Optional (only if your project uses Emotion `css` helpers):
|
|
13
|
+
Optional peers:
|
|
34
14
|
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
```
|
|
15
|
+
- `@mui/icons-material`
|
|
16
|
+
- `@emotion/css`
|
|
38
17
|
|
|
39
|
-
|
|
18
|
+
## Package Format
|
|
40
19
|
|
|
41
|
-
|
|
20
|
+
- ESM-only package
|
|
21
|
+
- Public entrypoints:
|
|
22
|
+
- `@atomazing-org/design-system`
|
|
23
|
+
- `@atomazing-org/design-system/presets`
|
|
42
24
|
|
|
43
|
-
|
|
25
|
+
## Quick Start
|
|
44
26
|
|
|
45
27
|
```tsx
|
|
46
28
|
import { ThemeProviderWrapper } from "@atomazing-org/design-system";
|
|
@@ -55,388 +37,61 @@ export function App() {
|
|
|
55
37
|
}
|
|
56
38
|
```
|
|
57
39
|
|
|
58
|
-
|
|
59
|
-
- `themes` can be **default presets**, **your presets**, or **both**.
|
|
60
|
-
- Theme choice + dark mode are persisted (storage key: `appSettings`).
|
|
61
|
-
|
|
62
|
-
---
|
|
63
|
-
|
|
64
|
-
## Built-in presets
|
|
65
|
-
|
|
66
|
-
Built-in presets are **ready-made theme packs shipped with the library**.
|
|
67
|
-
You can use them as-is, or add your own presets alongside them.
|
|
68
|
-
|
|
69
|
-
| Preset | Stable id | Best for |
|
|
70
|
-
|---|---|---|
|
|
71
|
-
| Warm Earth | `warm-earth` | Warm and friendly apps |
|
|
72
|
-
| Editorial Classic | `editorial-classic` | Content-heavy UIs |
|
|
73
|
-
| Modern Minimal | `modern-minimal` | Dashboards and tooling |
|
|
74
|
-
| Neo Glass | `neo-glass` | Modern “glass” style UIs |
|
|
75
|
-
| Retro Terminal | `retro-terminal` | Terminal-inspired branding |
|
|
76
|
-
|
|
77
|
-
Import them from:
|
|
78
|
-
|
|
79
|
-
```ts
|
|
80
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
81
|
-
```
|
|
82
|
-
|
|
83
|
-
## Switching theme (UI)
|
|
84
|
-
|
|
85
|
-
Build a simple theme switcher using the library’s theme settings hook.
|
|
86
|
-
|
|
87
|
-
```tsx
|
|
88
|
-
import { ToggleButton, ToggleButtonGroup } from "@mui/material";
|
|
89
|
-
import { useThemeSettings } from "@atomazing-org/design-system";
|
|
90
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
91
|
-
|
|
92
|
-
export function ThemeSwitcher() {
|
|
93
|
-
const { theme, setTheme } = useThemeSettings();
|
|
94
|
-
|
|
95
|
-
return (
|
|
96
|
-
<ToggleButtonGroup
|
|
97
|
-
size="small"
|
|
98
|
-
exclusive
|
|
99
|
-
value={theme}
|
|
100
|
-
onChange={(_, next) => next && setTheme(next)}
|
|
101
|
-
>
|
|
102
|
-
{defaultThemes.map((t) => (
|
|
103
|
-
<ToggleButton key={t.id} value={t.id}>
|
|
104
|
-
{t.label}
|
|
105
|
-
</ToggleButton>
|
|
106
|
-
))}
|
|
107
|
-
</ToggleButtonGroup>
|
|
108
|
-
);
|
|
109
|
-
}
|
|
110
|
-
```
|
|
111
|
-
|
|
112
|
-
---
|
|
113
|
-
|
|
114
|
-
## Dark mode
|
|
115
|
-
|
|
116
|
-
Dark mode switches the active **scheme** inside the current preset.
|
|
117
|
-
|
|
118
|
-
### Supported values
|
|
40
|
+
Use `useThemeSettings()` for runtime preset and dark-mode controls.
|
|
119
41
|
|
|
120
|
-
-
|
|
121
|
-
- `dark` — always use the preset’s dark scheme
|
|
122
|
-
- `system` — follow OS/browser preference (`prefers-color-scheme`)
|
|
42
|
+
## Built-In Preset Packs
|
|
123
43
|
|
|
124
|
-
|
|
44
|
+
- `defaultThemes`: baseline application presets
|
|
45
|
+
- `landingPageThemes`: extended landing and marketing presets
|
|
46
|
+
- `allBuiltInThemes`: combined pack
|
|
125
47
|
|
|
126
|
-
|
|
48
|
+
## Custom Presets
|
|
127
49
|
|
|
128
|
-
|
|
50
|
+
Custom presets must follow the `ThemePreset` contract:
|
|
129
51
|
|
|
130
|
-
|
|
131
|
-
|
|
52
|
+
- stable `id`
|
|
53
|
+
- human-readable `label`
|
|
54
|
+
- `colorSchemes.light`
|
|
55
|
+
- `colorSchemes.dark`
|
|
132
56
|
|
|
133
|
-
|
|
57
|
+
Each scheme should define:
|
|
134
58
|
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
import { useThemeSettings } from "@atomazing-org/design-system";
|
|
138
|
-
|
|
139
|
-
export function DarkModeSelector() {
|
|
140
|
-
const { darkMode, setDarkMode } = useThemeSettings();
|
|
141
|
-
|
|
142
|
-
return (
|
|
143
|
-
<RadioGroup row value={darkMode} onChange={(e) => setDarkMode(e.target.value as any)}>
|
|
144
|
-
<FormControlLabel value="system" control={<Radio />} label="System" />
|
|
145
|
-
<FormControlLabel value="light" control={<Radio />} label="Light" />
|
|
146
|
-
<FormControlLabel value="dark" control={<Radio />} label="Dark" />
|
|
147
|
-
</RadioGroup>
|
|
148
|
-
);
|
|
149
|
-
}
|
|
150
|
-
```
|
|
151
|
-
|
|
152
|
-
### Forcing mode (optional)
|
|
153
|
-
|
|
154
|
-
If your app does not support dark mode, you can force the effective palette mode:
|
|
155
|
-
|
|
156
|
-
```tsx
|
|
157
|
-
import { ThemeProviderWrapper } from "@atomazing-org/design-system";
|
|
158
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
159
|
-
|
|
160
|
-
export function App() {
|
|
161
|
-
return (
|
|
162
|
-
<ThemeProviderWrapper themes={defaultThemes} darkMode="light">
|
|
163
|
-
{/* your app */}
|
|
164
|
-
</ThemeProviderWrapper>
|
|
165
|
-
);
|
|
166
|
-
}
|
|
167
|
-
```
|
|
168
|
-
|
|
169
|
-
Note: when `darkMode` is set, `darkMode` is locked and `setDarkMode` is ignored.
|
|
170
|
-
|
|
171
|
-
---
|
|
172
|
-
|
|
173
|
-
## Custom themes
|
|
174
|
-
|
|
175
|
-
Provide your own preset(s) to the provider. A preset is one identifiable theme with **two schemes**: `light` and `dark`.
|
|
176
|
-
|
|
177
|
-
### API reference — `ThemePreset`
|
|
178
|
-
|
|
179
|
-
| Field | Type | What it means |
|
|
180
|
-
|---|---|---|
|
|
181
|
-
| `id` | `string` | Stable identifier used for persistence and deduplication. Must be unique. |
|
|
182
|
-
| `label` | `string` | Name shown in UI selectors. |
|
|
183
|
-
| `colorSchemes.light` | `ThemeOptions` | MUI ThemeOptions for light mode. |
|
|
184
|
-
| `colorSchemes.dark` | `ThemeOptions` | MUI ThemeOptions for dark mode. |
|
|
185
|
-
|
|
186
|
-
### Minimum required tokens per scheme
|
|
187
|
-
|
|
188
|
-
Each scheme must define:
|
|
189
|
-
- `palette.background.default` — page background
|
|
190
|
-
- `palette.background.paper` — Card/Paper background
|
|
59
|
+
- `palette.background.default`
|
|
60
|
+
- `palette.background.paper`
|
|
191
61
|
- `palette.text.primary`
|
|
192
62
|
- `palette.text.secondary`
|
|
193
63
|
- `palette.divider`
|
|
194
64
|
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
```ts
|
|
198
|
-
import type { ThemePreset } from "@atomazing-org/design-system";
|
|
65
|
+
## Persistence
|
|
199
66
|
|
|
200
|
-
|
|
201
|
-
id: "my-brand",
|
|
202
|
-
label: "My Brand",
|
|
203
|
-
colorSchemes: {
|
|
204
|
-
light: {
|
|
205
|
-
palette: {
|
|
206
|
-
background: { default: "#ffffff", paper: "#ffffff" },
|
|
207
|
-
text: { primary: "#111111", secondary: "#444444" },
|
|
208
|
-
divider: "rgba(0,0,0,0.12)",
|
|
209
|
-
},
|
|
210
|
-
},
|
|
211
|
-
dark: {
|
|
212
|
-
palette: {
|
|
213
|
-
background: { default: "#0f1115", paper: "#151922" },
|
|
214
|
-
text: { primary: "#f1f3f5", secondary: "#c6cbd1" },
|
|
215
|
-
divider: "rgba(241,243,245,0.16)",
|
|
216
|
-
},
|
|
217
|
-
},
|
|
218
|
-
},
|
|
219
|
-
};
|
|
220
|
-
```
|
|
221
|
-
|
|
222
|
-
### Using defaults + custom presets
|
|
67
|
+
Theme settings are stored in `localStorage` under `appSettings`.
|
|
223
68
|
|
|
224
|
-
|
|
225
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
226
|
-
|
|
227
|
-
const themes = [...defaultThemes, myPreset];
|
|
228
|
-
```
|
|
69
|
+
Current JSON shape:
|
|
229
70
|
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
---
|
|
233
|
-
|
|
234
|
-
## Typography variants
|
|
235
|
-
|
|
236
|
-
The library adds extra typography variants (beyond MUI defaults) so your text styles are consistent across the app.
|
|
237
|
-
|
|
238
|
-
```tsx
|
|
239
|
-
import { Typography } from "@mui/material";
|
|
240
|
-
|
|
241
|
-
export function TypographyDemo() {
|
|
242
|
-
return (
|
|
243
|
-
<>
|
|
244
|
-
<Typography variant="header_lg_bold">Page title</Typography>
|
|
245
|
-
<Typography variant="text_md_regular">Body text</Typography>
|
|
246
|
-
<Typography variant="text_sm_bold">Caption / label</Typography>
|
|
247
|
-
</>
|
|
248
|
-
);
|
|
249
|
-
}
|
|
250
|
-
```
|
|
251
|
-
|
|
252
|
-
Notes:
|
|
253
|
-
- Typography sizing is expected to be **rem-based** (scales with the user’s browser font size settings).
|
|
254
|
-
- Variants are defined in the design system theme (no local “one-off” styles needed).
|
|
255
|
-
|
|
256
|
-
---
|
|
257
|
-
|
|
258
|
-
## Global styles
|
|
259
|
-
|
|
260
|
-
`ThemeProviderWrapper` applies global styles (via Emotion) and MUI component defaults, so the app looks consistent immediately.
|
|
261
|
-
|
|
262
|
-
Set a custom font stack:
|
|
263
|
-
|
|
264
|
-
```tsx
|
|
265
|
-
import { ThemeProviderWrapper } from "@atomazing-org/design-system";
|
|
266
|
-
|
|
267
|
-
export function App() {
|
|
268
|
-
return (
|
|
269
|
-
<ThemeProviderWrapper fontFamily="Inter, system-ui, -apple-system, 'Segoe UI', Roboto, Arial, sans-serif">
|
|
270
|
-
{/* your app */}
|
|
271
|
-
</ThemeProviderWrapper>
|
|
272
|
-
);
|
|
273
|
-
}
|
|
274
|
-
```
|
|
275
|
-
|
|
276
|
-
---
|
|
277
|
-
|
|
278
|
-
## Animations
|
|
279
|
-
|
|
280
|
-
The library exports reusable keyframes so you can keep motion consistent.
|
|
281
|
-
|
|
282
|
-
```tsx
|
|
283
|
-
import styled from "@emotion/styled";
|
|
284
|
-
import { fadeIn } from "@atomazing-org/design-system";
|
|
285
|
-
|
|
286
|
-
const Panel = styled.div`
|
|
287
|
-
animation: ${fadeIn} 240ms ease-in both;
|
|
288
|
-
`;
|
|
289
|
-
|
|
290
|
-
export function AnimatedPanel() {
|
|
291
|
-
return <Panel>Content</Panel>;
|
|
292
|
-
}
|
|
293
|
-
```
|
|
294
|
-
|
|
295
|
-
---
|
|
296
|
-
|
|
297
|
-
## SSR notes
|
|
298
|
-
|
|
299
|
-
- The library is written to be **SSR-safe**: no `window`/`document`/`localStorage` access at module scope.
|
|
300
|
-
- If you use **system** dark mode, the effective mode is derived from `prefers-color-scheme` on the client.
|
|
301
|
-
- In Next.js, place the provider inside a client boundary (e.g., a component with `"use client"`), then wrap your app with `ThemeProviderWrapper`.
|
|
302
|
-
|
|
303
|
-
## Consumer alias guidance (optional)
|
|
304
|
-
|
|
305
|
-
Aliases are **optional**. They help you avoid long relative imports **inside your app**.
|
|
306
|
-
|
|
307
|
-
---
|
|
308
|
-
|
|
309
|
-
## Local development (repo)
|
|
310
|
-
|
|
311
|
-
From the repository root:
|
|
312
|
-
|
|
313
|
-
```bash
|
|
314
|
-
pnpm lint
|
|
315
|
-
pnpm build
|
|
316
|
-
pnpm test
|
|
317
|
-
pnpm -C examples/repro dev
|
|
318
|
-
```
|
|
319
|
-
|
|
320
|
-
---
|
|
321
|
-
|
|
322
|
-
## Peer dependencies
|
|
323
|
-
|
|
324
|
-
Make sure your app installs these (MUI v7 + Emotion):
|
|
325
|
-
|
|
326
|
-
- `react`
|
|
327
|
-
- `react-dom`
|
|
328
|
-
- `@mui/material`
|
|
329
|
-
- `@mui/icons-material` (optional, only if you use icons from MUI)
|
|
330
|
-
- `@emotion/react`
|
|
331
|
-
- `@emotion/styled`
|
|
332
|
-
- `@emotion/css` (optional)
|
|
333
|
-
|
|
334
|
-
---
|
|
335
|
-
|
|
336
|
-
## Troubleshooting
|
|
337
|
-
|
|
338
|
-
### Dark mode switches, but background/cards do not change
|
|
339
|
-
- Ensure your preset provides **both schemes**:
|
|
340
|
-
- `colorSchemes.light.palette.background.default/paper`
|
|
341
|
-
- `colorSchemes.dark.palette.background.default/paper`
|
|
342
|
-
- Avoid hardcoded colors in overrides. Use `theme.palette.*` tokens.
|
|
343
|
-
|
|
344
|
-
### Text is hard to read in dark mode
|
|
345
|
-
- Do not reuse light “ink” constants in dark mode.
|
|
346
|
-
- Check:
|
|
347
|
-
- `palette.text.primary` vs `palette.background.default`
|
|
348
|
-
- `palette.text.secondary` vs `palette.background.paper`
|
|
349
|
-
|
|
350
|
-
### I want to add my own presets
|
|
351
|
-
- Create a `ThemePreset` with `colorSchemes.light` and `colorSchemes.dark`.
|
|
352
|
-
- Combine with defaults: `const themes = [...defaultThemes, myPreset];`
|
|
353
|
-
|
|
354
|
-
## Examples (examples/repro)
|
|
355
|
-
|
|
356
|
-
The repo includes a runnable example app that demonstrates:
|
|
357
|
-
- preset switching
|
|
358
|
-
- dark mode switching
|
|
359
|
-
- background + card surfaces changing correctly
|
|
360
|
-
- token/debug view (if enabled in the example)
|
|
361
|
-
|
|
362
|
-
Run it from the repository root:
|
|
363
|
-
|
|
364
|
-
```bash
|
|
365
|
-
pnpm -C examples/repro dev
|
|
366
|
-
```
|
|
367
|
-
|
|
368
|
-
What to check in the UI:
|
|
369
|
-
- switching to **dark** changes the **page background** and **Card/Paper** background
|
|
370
|
-
- text stays readable on both backgrounds
|
|
371
|
-
- inputs, buttons, menus, and dialogs remain usable
|
|
372
|
-
|
|
373
|
-
---
|
|
374
|
-
|
|
375
|
-
## API reference — `ThemeProviderWrapper`
|
|
376
|
-
|
|
377
|
-
`ThemeProviderWrapper` wires MUI ThemeProvider, global styles, and persisted settings.
|
|
378
|
-
|
|
379
|
-
| Prop | Type | Default | What it does |
|
|
380
|
-
|---|---|---|---|
|
|
381
|
-
| `themes` | `ThemePreset[]` (or built-in `defaultThemes`) | `defaultThemes` | List of presets available to the user. |
|
|
382
|
-
| `fontFamily` | `string` | (theme default) | Optional global font stack for the whole app. |
|
|
383
|
-
| `darkMode` | `DarkModeOptions` | - | Forces mode regardless of persisted settings and system preference. |
|
|
384
|
-
| `children` | `ReactNode` | — | Your application tree. |
|
|
385
|
-
|
|
386
|
-
Minimal usage:
|
|
387
|
-
|
|
388
|
-
```tsx
|
|
389
|
-
import { ThemeProviderWrapper } from "@atomazing-org/design-system";
|
|
390
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
391
|
-
|
|
392
|
-
export function App() {
|
|
393
|
-
return (
|
|
394
|
-
<ThemeProviderWrapper themes={defaultThemes}>
|
|
395
|
-
{/* your app */}
|
|
396
|
-
</ThemeProviderWrapper>
|
|
397
|
-
);
|
|
398
|
-
}
|
|
399
|
-
```
|
|
400
|
-
|
|
401
|
-
---
|
|
402
|
-
|
|
403
|
-
## Public exports (recommended imports)
|
|
404
|
-
|
|
405
|
-
Use only these stable entry points:
|
|
406
|
-
|
|
407
|
-
### Core API
|
|
408
|
-
```ts
|
|
409
|
-
import { ThemeProviderWrapper, useThemeSettings } from "@atomazing-org/design-system";
|
|
410
|
-
```
|
|
411
|
-
|
|
412
|
-
### Built-in presets
|
|
413
|
-
```ts
|
|
414
|
-
import { defaultThemes } from "@atomazing-org/design-system/presets";
|
|
71
|
+
```json
|
|
72
|
+
{ "themeId": "editorial-classic", "darkMode": "system" }
|
|
415
73
|
```
|
|
416
74
|
|
|
417
|
-
|
|
418
|
-
- Avoid deep imports from internal folders. They may change during refactors.
|
|
75
|
+
## SSR Notes
|
|
419
76
|
|
|
420
|
-
|
|
77
|
+
- Keep `ThemeProviderWrapper` inside a client boundary for Next.js and other SSR apps.
|
|
78
|
+
- Do not access `window`, `document`, or `localStorage` at module scope.
|
|
79
|
+
- When dark mode uses `system`, the effective mode resolves on the client after hydration.
|
|
421
80
|
|
|
422
|
-
## Migration
|
|
81
|
+
## Migration Docs
|
|
423
82
|
|
|
424
|
-
If you
|
|
425
|
-
1) Move your theme into a preset shape with **two schemes**:
|
|
426
|
-
- `colorSchemes.light`
|
|
427
|
-
- `colorSchemes.dark`
|
|
428
|
-
2) Ensure each scheme defines the required tokens:
|
|
429
|
-
- `background.default`, `background.paper`
|
|
430
|
-
- `text.primary`, `text.secondary`
|
|
431
|
-
- `divider`
|
|
432
|
-
3) Pass presets into the provider:
|
|
433
|
-
- `themes={[...defaultThemes, myPreset]}` or only `[myPreset]`
|
|
83
|
+
If you are migrating an app to this package, start with:
|
|
434
84
|
|
|
435
|
-
|
|
436
|
-
-
|
|
85
|
+
- `migrations/README.UPDATE.md`
|
|
86
|
+
- `migrations/docs/migrations/design-system/README.md`
|
|
87
|
+
- `migrations/docs/migrations/design-system/shared/WORKING-RULES.md`
|
|
88
|
+
- `migrations/skills/design-system-consumer-agent/SKILL.md`
|
|
89
|
+
- `migrations/skills/design-system-migration-agent/SKILL.md`
|
|
437
90
|
|
|
438
|
-
|
|
91
|
+
## Examples
|
|
439
92
|
|
|
440
|
-
|
|
93
|
+
- `examples/react-app`: canonical Vite smoke consumer for local package validation
|
|
94
|
+
- `examples/next-app-router`: canonical Next.js App Router starter reference
|
|
441
95
|
|
|
442
|
-
|
|
96
|
+
For starter-specific rules, runbooks, and customization guidance, use the local docs
|
|
97
|
+
pack under `examples/next-app-router/`.
|