@marwes-ui/react 1.0.1 → 1.0.3
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/README.md +67 -1
- package/dist/index.d.ts +18 -3
- package/dist/index.js +260 -112
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
<div align="center">
|
|
2
2
|
|
|
3
|
-
<img alt="Marwes Design System" src="https://raw.githubusercontent.com/niklas-westman/marwes/main/.github/assets/banner
|
|
3
|
+
<img alt="Marwes Design System" src="https://raw.githubusercontent.com/niklas-westman/marwes/main/.github/assets/banner.png" width="100%" style="border-radius: 40px;">
|
|
4
4
|
|
|
5
5
|
<br>
|
|
6
6
|
<br>
|
|
@@ -312,6 +312,72 @@ export function App() {
|
|
|
312
312
|
|
|
313
313
|
`defaultMode` sets the initial uncontrolled mode. `toggleMode()` updates the provider, so Marwes components, preset CSS, and custom app styles that use `--mw-*` variables all move together without duplicating local theme state.
|
|
314
314
|
|
|
315
|
+
### System And Persisted Preference
|
|
316
|
+
|
|
317
|
+
`mode` is always the rendered visual mode: `ThemeMode.light` or `ThemeMode.dark`. `preference` is the app or user choice: `ThemeMode.light`, `ThemeMode.dark`, or `"system"`. Use `preference` and `defaultPreference` when your UI needs a system option; keep using `mode`, `defaultMode`, and `onModeChange` when you only need concrete light/dark compatibility.
|
|
318
|
+
|
|
319
|
+
```tsx
|
|
320
|
+
import { Button, ButtonVariant, MarwesProvider, ThemeMode, useThemeMode } from "@marwes-ui/react"
|
|
321
|
+
|
|
322
|
+
function ThemeMenu() {
|
|
323
|
+
const { mode, preference, systemMode, isSystem, setPreference, setMode } = useThemeMode()
|
|
324
|
+
|
|
325
|
+
return (
|
|
326
|
+
<div>
|
|
327
|
+
<p>
|
|
328
|
+
Rendering {mode}; preference is {preference}; system is {systemMode}.
|
|
329
|
+
</p>
|
|
330
|
+
<Button variant={ButtonVariant.secondary} onClick={() => setPreference("system")}>
|
|
331
|
+
Use system
|
|
332
|
+
</Button>
|
|
333
|
+
<Button variant={ButtonVariant.secondary} onClick={() => setMode(ThemeMode.dark)}>
|
|
334
|
+
Use dark
|
|
335
|
+
</Button>
|
|
336
|
+
{isSystem ? "Following system" : null}
|
|
337
|
+
</div>
|
|
338
|
+
)
|
|
339
|
+
}
|
|
340
|
+
|
|
341
|
+
export function App() {
|
|
342
|
+
return (
|
|
343
|
+
<MarwesProvider
|
|
344
|
+
defaultPreference="system"
|
|
345
|
+
storageKey="marwes-theme"
|
|
346
|
+
enableSystem
|
|
347
|
+
>
|
|
348
|
+
<ThemeMenu />
|
|
349
|
+
<AppShell />
|
|
350
|
+
</MarwesProvider>
|
|
351
|
+
)
|
|
352
|
+
}
|
|
353
|
+
```
|
|
354
|
+
|
|
355
|
+
`useThemeMode().mode` never returns `"system"`; it is always the concrete mode Marwes rendered. `useThemeMode().preference` returns the active app/user preference, and `setPreference("system")` is the system-capable setter. `setMode(mode)` remains a concrete light/dark convenience.
|
|
356
|
+
|
|
357
|
+
`storageKey` is opt-in and defaults to `false`. Storage reads and writes are failure-safe, so private browsing or unavailable storage will fall back to normal provider state. `enableSystem` defaults to `true`; set it to `false` to avoid `matchMedia` detection and resolve `"system"` through the light fallback.
|
|
358
|
+
|
|
359
|
+
This layer does not provide SSR no-flash behavior. Server output can still render the fallback mode before the client applies a stored or system preference. Use it for client-side preference and persistence, not for a no-flash SSR guarantee.
|
|
360
|
+
|
|
361
|
+
### Root Target Sync
|
|
362
|
+
|
|
363
|
+
By default Marwes keeps theme state scoped to the provider element. If your app shell also needs the resolved mode on `html` or `body`, set `target` and `attribute`:
|
|
364
|
+
|
|
365
|
+
```tsx
|
|
366
|
+
<MarwesProvider
|
|
367
|
+
defaultPreference="system"
|
|
368
|
+
storageKey="marwes-theme"
|
|
369
|
+
target="html"
|
|
370
|
+
attribute="class"
|
|
371
|
+
disableTransitionOnChange
|
|
372
|
+
>
|
|
373
|
+
<AppShell />
|
|
374
|
+
</MarwesProvider>
|
|
375
|
+
```
|
|
376
|
+
|
|
377
|
+
`target` can be `"provider"`, `"html"`, or `"body"`. `attribute` can be `"class"`, `"data-theme"`, or `"data-mode"`. Class mode only adds the active `light` / `dark` class and removes the opposite one; unrelated classes are preserved. The provider root still keeps `mw-theme--light` / `mw-theme--dark` and provider-scoped `--mw-*` variables in every target mode.
|
|
378
|
+
|
|
379
|
+
Use one global-target provider per app shell. If multiple providers target `html` or `body`, deciding which provider owns that global element is app-owned behavior.
|
|
380
|
+
|
|
315
381
|
For a simple brand pass, override shared values once and let Marwes fill the rest. If your product needs different brand colors in light and dark mode, control `mode` and switch between two small `ThemeInput` override objects:
|
|
316
382
|
|
|
317
383
|
```tsx
|
package/dist/index.d.ts
CHANGED
|
@@ -1,26 +1,41 @@
|
|
|
1
1
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
|
-
import { ThemeInput, ThemeMode, FontLoadingConfig, ResolvedTheme, ButtonOptions, InputOptions, SelectOptions, SelectAppearance as SelectAppearance$1, SelectOption as SelectOption$1, TextareaOptions, RichTextOptions, InputOtpOptions, CurrencyCode, iconRegistry, IconSize, IconStrokeWidth, AvatarOptions, CheckboxProps as CheckboxProps$1, DividerOptions, DividerSize, DividerOrientation, SpinnerOptions, SpacingOptions, SpacingSize, HeadingOptions, HeadingSize, ParagraphOptions, ParagraphSize, ToastOptions, ToastVariant, ToastIntent, ToastPlacement, TooltipOptions, IconNameType, RadioOptions, BadgeOptions, SwitchOptions, SliderOptions, TabOptions, DialogOptions } from '@marwes-ui/core';
|
|
3
|
-
export { AvatarSize, AvatarType, BadgeVariant, ButtonAction, ButtonSize, ButtonVariant, Density, FontLoadingConfig, FontLoadingMode, FontLoadingOptions, IconName, MwAvailableFont, MwFontFallback, MwGoogleFontFamily, MwStyledTheme, MwThemeVarName, MwThemeVarNames, MwThemeVarReference, MwThemeVars, ResolvedTheme, SpacingSize, Spacings, SwitchSize, Theme, ThemeInput, ThemeMode, ToneName, createFontStack, mwAvailableFonts, mwFontFallbacks, mwGoogleFontFamilies, mwStyledTheme, mwThemeVarNames, mwThemeVars, mwVar } from '@marwes-ui/core';
|
|
2
|
+
import { ThemeInput, ThemePreference, ThemeMode, FontLoadingConfig, ResolvedTheme, ButtonOptions, InputOptions, SelectOptions, SelectAppearance as SelectAppearance$1, SelectOption as SelectOption$1, TextareaOptions, RichTextOptions, InputOtpOptions, CurrencyCode, iconRegistry, IconSize, IconStrokeWidth, AvatarOptions, CheckboxProps as CheckboxProps$1, DividerOptions, DividerSize, DividerOrientation, SpinnerOptions, SpacingOptions, SpacingSize, HeadingOptions, HeadingSize, ParagraphOptions, ParagraphSize, ToastOptions, ToastVariant, ToastIntent, ToastPlacement, TooltipOptions, IconNameType, RadioOptions, BadgeOptions, SwitchOptions, SliderOptions, TabOptions, DialogOptions } from '@marwes-ui/core';
|
|
3
|
+
export { AvatarSize, AvatarType, BadgeVariant, ButtonAction, ButtonSize, ButtonVariant, Density, FontLoadingConfig, FontLoadingMode, FontLoadingOptions, IconName, MwAvailableFont, MwFontFallback, MwGoogleFontFamily, MwStyledTheme, MwThemeVarName, MwThemeVarNames, MwThemeVarReference, MwThemeVars, ResolvedTheme, SpacingSize, Spacings, SwitchSize, Theme, ThemeInput, ThemeMode, ThemePreference, ToneName, createFontStack, mwAvailableFonts, mwFontFallbacks, mwGoogleFontFamilies, mwStyledTheme, mwThemeVarNames, mwThemeVars, mwVar } from '@marwes-ui/core';
|
|
4
4
|
import * as React from 'react';
|
|
5
5
|
|
|
6
|
+
type ThemeTarget = "provider" | "html" | "body";
|
|
7
|
+
type ThemeAttribute = "class" | "data-theme" | "data-mode";
|
|
8
|
+
|
|
6
9
|
type MarwesProviderProps = {
|
|
7
10
|
theme?: ThemeInput;
|
|
11
|
+
defaultPreference?: ThemePreference;
|
|
12
|
+
preference?: ThemePreference;
|
|
8
13
|
defaultMode?: ThemeMode;
|
|
9
14
|
mode?: ThemeMode;
|
|
10
15
|
fontLoading?: FontLoadingConfig;
|
|
16
|
+
onPreferenceChange?: (preference: ThemePreference) => void;
|
|
11
17
|
onModeChange?: (mode: ThemeMode) => void;
|
|
18
|
+
storageKey?: string | false;
|
|
19
|
+
enableSystem?: boolean;
|
|
20
|
+
target?: ThemeTarget;
|
|
21
|
+
attribute?: ThemeAttribute;
|
|
22
|
+
disableTransitionOnChange?: boolean;
|
|
12
23
|
children: React.ReactNode;
|
|
13
24
|
};
|
|
14
|
-
declare function MarwesProvider({ theme, defaultMode, mode: controlledMode, fontLoading, onModeChange, children, }: MarwesProviderProps): react_jsx_runtime.JSX.Element;
|
|
25
|
+
declare function MarwesProvider({ theme, defaultPreference, preference: controlledPreference, defaultMode, mode: controlledMode, fontLoading, onPreferenceChange, onModeChange, storageKey, enableSystem, target, attribute, disableTransitionOnChange, children, }: MarwesProviderProps): react_jsx_runtime.JSX.Element;
|
|
15
26
|
|
|
16
27
|
declare function useTheme(): ResolvedTheme;
|
|
17
28
|
|
|
18
29
|
type ThemeModeContextValue = {
|
|
19
30
|
mode: ThemeMode;
|
|
31
|
+
preference: ThemePreference;
|
|
32
|
+
systemMode: ThemeMode;
|
|
20
33
|
setMode: (mode: ThemeMode) => void;
|
|
34
|
+
setPreference: (preference: ThemePreference) => void;
|
|
21
35
|
toggleMode: () => void;
|
|
22
36
|
isDark: boolean;
|
|
23
37
|
isLight: boolean;
|
|
38
|
+
isSystem: boolean;
|
|
24
39
|
};
|
|
25
40
|
declare function useThemeMode(): ThemeModeContextValue;
|
|
26
41
|
|