@castui/cast-ui 4.8.0 → 4.9.0

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 CHANGED
@@ -163,6 +163,61 @@ The full guide lives in the
163
163
  [hosted Storybook](https://main--6990f00d7b8682c18d2ed5f3.chromatic.com)
164
164
  under **Guides → Customisation**.
165
165
 
166
+ ## Responsive layout
167
+
168
+ Cast UI ships a set of breakpoints and hooks for building layouts that adapt
169
+ across phones, tablets, and desktops. The values follow the Material 3 window
170
+ size classes, so the same numbers hold up across watches, phones, foldables,
171
+ tablets, and large screens.
172
+
173
+ | Tier | Range (dp) | Typical devices |
174
+ |------|-----------|-----------------|
175
+ | `base` | `< 600` | Watches and every phone in portrait. Your default layout. |
176
+ | `sm` | `>= 600` | Large phones in landscape, foldables unfolded, small tablets |
177
+ | `md` | `>= 840` | Tablets |
178
+ | `lg` | `>= 1200` | Laptops and desktops |
179
+ | `xl` | `>= 1600` | Large desktops and TVs |
180
+
181
+ The hooks read the live window width, so they update on resize, rotation, and
182
+ foldables, and they behave the same on the web. The most common one picks a
183
+ value per tier:
184
+
185
+ ```tsx
186
+ import { useResponsiveValue, useBreakpoint, useMinWidth } from '@castui/cast-ui';
187
+
188
+ function Gallery() {
189
+ const columns = useResponsiveValue({ base: 1, md: 2, xl: 4 });
190
+ // 1 column on phones, 2 on tablets, 4 on large desktops
191
+ ...
192
+ }
193
+ ```
194
+
195
+ `useResponsiveValue` is mobile-first: a tier with no value falls back to the
196
+ nearest one below it, so `{ base: 1, md: 2 }` gives 1 up to `md` and 2 from
197
+ `md` on. The other two hooks cover the rest:
198
+
199
+ ```tsx
200
+ const tier = useBreakpoint(); // 'base' | 'sm' | 'md' | 'lg' | 'xl'
201
+ const isWide = useMinWidth('lg'); // true from 1200dp up
202
+ ```
203
+
204
+ The raw thresholds are also exported as `breakpoints` if you need a number
205
+ directly.
206
+
207
+ A few things worth knowing. React Native has no CSS media queries, so a
208
+ breakpoint here is a width threshold you compare against, not automatic
209
+ restyling. `base` is the mobile-first default: you write the phone layout with
210
+ no breakpoint, then add overrides for larger screens. The gap between a small
211
+ and a large phone is better handled with flexible layout (flex, percentages,
212
+ `maxWidth`) than with a breakpoint.
213
+
214
+ Breakpoints are a fixed foundation, which sets them apart from the rest of the
215
+ theme. They are not part of `ThemeProvider`: they do not change with density,
216
+ they are not touched by brand colour overrides, and they are not carried in
217
+ `cast-theme.json`. The scale stays identical in every app, so layouts stay
218
+ predictable. The same values live as the `breakpoint/*` primitive variables in
219
+ the [cast-ui-kit Figma file](https://www.figma.com/design/JGtlpxLPJMZcwvQ3UZ9ZUl/cast-ui-kit).
220
+
166
221
  ## Theming from Figma — the cast-sync plugin
167
222
 
168
223
  [`cast-sync/`](./cast-sync) is a Figma plugin that turns the Figma file's
@@ -0,0 +1 @@
1
+ export { useBreakpoint, useMinWidth, useResponsiveValue } from './useBreakpoint';
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.useResponsiveValue = exports.useMinWidth = exports.useBreakpoint = void 0;
4
+ var useBreakpoint_1 = require("./useBreakpoint");
5
+ Object.defineProperty(exports, "useBreakpoint", { enumerable: true, get: function () { return useBreakpoint_1.useBreakpoint; } });
6
+ Object.defineProperty(exports, "useMinWidth", { enumerable: true, get: function () { return useBreakpoint_1.useMinWidth; } });
7
+ Object.defineProperty(exports, "useResponsiveValue", { enumerable: true, get: function () { return useBreakpoint_1.useResponsiveValue; } });
@@ -0,0 +1,22 @@
1
+ import { type Breakpoint, type BreakpointKey } from '../tokens/breakpoints';
2
+ /**
3
+ * The active breakpoint tier for the current window width. Mobile-first:
4
+ * 'base' below `sm`, then 'sm' | 'md' | 'lg' | 'xl' as the width grows.
5
+ *
6
+ * const bp = useBreakpoint(); // 'base' | 'sm' | 'md' | 'lg' | 'xl'
7
+ */
8
+ export declare function useBreakpoint(): BreakpointKey;
9
+ /**
10
+ * True when the window is at or above the given breakpoint.
11
+ *
12
+ * const isWide = useMinWidth('lg'); // true from 1024dp up
13
+ */
14
+ export declare function useMinWidth(breakpoint: Breakpoint): boolean;
15
+ /**
16
+ * Pick a value for the current breakpoint, mobile-first. Supply values for any
17
+ * subset of tiers; the value at the current tier wins, falling back to the
18
+ * nearest defined tier below it.
19
+ *
20
+ * const columns = useResponsiveValue({ base: 1, md: 2, xl: 4 });
21
+ */
22
+ export declare function useResponsiveValue<T>(values: Partial<Record<BreakpointKey, T>>): T | undefined;
@@ -0,0 +1,45 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.useBreakpoint = useBreakpoint;
4
+ exports.useMinWidth = useMinWidth;
5
+ exports.useResponsiveValue = useResponsiveValue;
6
+ /**
7
+ * Responsive hooks built on the breakpoint scale.
8
+ *
9
+ * These read the live window width via react-native's useWindowDimensions, so
10
+ * they recompute on resize, rotation, and foldable changes, and they work the
11
+ * same on web (react-native-web). Breakpoints are a standalone foundation: they
12
+ * are not part of the theme and do not change with density.
13
+ */
14
+ const react_native_1 = require("react-native");
15
+ const breakpoints_1 = require("../tokens/breakpoints");
16
+ /**
17
+ * The active breakpoint tier for the current window width. Mobile-first:
18
+ * 'base' below `sm`, then 'sm' | 'md' | 'lg' | 'xl' as the width grows.
19
+ *
20
+ * const bp = useBreakpoint(); // 'base' | 'sm' | 'md' | 'lg' | 'xl'
21
+ */
22
+ function useBreakpoint() {
23
+ const { width } = (0, react_native_1.useWindowDimensions)();
24
+ return (0, breakpoints_1.resolveBreakpoint)(width);
25
+ }
26
+ /**
27
+ * True when the window is at or above the given breakpoint.
28
+ *
29
+ * const isWide = useMinWidth('lg'); // true from 1024dp up
30
+ */
31
+ function useMinWidth(breakpoint) {
32
+ const { width } = (0, react_native_1.useWindowDimensions)();
33
+ return width >= breakpoints_1.breakpoints[breakpoint];
34
+ }
35
+ /**
36
+ * Pick a value for the current breakpoint, mobile-first. Supply values for any
37
+ * subset of tiers; the value at the current tier wins, falling back to the
38
+ * nearest defined tier below it.
39
+ *
40
+ * const columns = useResponsiveValue({ base: 1, md: 2, xl: 4 });
41
+ */
42
+ function useResponsiveValue(values) {
43
+ const current = useBreakpoint();
44
+ return (0, breakpoints_1.resolveResponsiveValue)(values, current);
45
+ }
package/dist/index.d.ts CHANGED
@@ -1,5 +1,6 @@
1
- export { lightColors, darkColors, colorSchemes, intentColors, disabledColors, controlTokens, surfaceTokens, textTokens, overlayTokens, selectColors, menuColors, tagTokens, errorTokens, listColors, checkboxColors, toggleColors, progressColors, tabsColors, radioColors, avatarColors, skeletonColors, sliderColors, tableColors, fontFamily, fontWeight, label, title, body, heading, display, caption, type IntentName, type ProminenceName, type StateName, type ColorMode, type ColorScheme, type LabelSize, iconSize, type IconSize, } from './tokens';
1
+ export { lightColors, darkColors, colorSchemes, intentColors, disabledColors, controlTokens, surfaceTokens, textTokens, overlayTokens, selectColors, menuColors, tagTokens, errorTokens, listColors, checkboxColors, toggleColors, progressColors, tabsColors, radioColors, avatarColors, skeletonColors, sliderColors, tableColors, fontFamily, fontWeight, label, title, body, heading, display, caption, type IntentName, type ProminenceName, type StateName, type ColorMode, type ColorScheme, type LabelSize, iconSize, type IconSize, breakpoints, breakpointOrder, resolveBreakpoint, resolveResponsiveValue, type Breakpoint, type BreakpointKey, } from './tokens';
2
2
  export { ThemeProvider, useTheme, themes, applyCastTheme, type Theme, type ThemeProviderProps, type CastThemeFile, type CastThemeProps, type DensityTheme, type ComponentTokens, type ButtonSizeTokens, type ButtonThemeTokens, type DialogSizeTokens, type DialogThemeTokens, type InputSizeTokens, type InputThemeTokens, type SelectContentTokens, type SelectOptionTokens, type SelectGroupTokens, type SelectSeparatorTokens, type SelectThemeTokens, type ListItemTokens, type ListSubheaderTokens, type ListThemeTokens, type CheckboxSizeTokens, type CheckboxThemeTokens, type AlertSizeTokens, type AlertThemeTokens, type ToggleSizeTokens, type ToggleThemeTokens, type CardSizeTokens, type CardThemeTokens, type BadgeSizeTokens, type BadgeThemeTokens, type RadioSizeTokens, type RadioThemeTokens, type ToastSizeTokens, type ToastThemeTokens, type ChipSizeTokens, type ChipThemeTokens, type AvatarSizeTokens, type AvatarThemeTokens, type PopoverSizeTokens, type PopoverThemeTokens, type TooltipSizeTokens, type TooltipThemeTokens, type ProgressSizeTokens, type ProgressThemeTokens, type TabsSizeTokens, type TabsThemeTokens, type SpinnerSizeTokens, type SpinnerThemeTokens, type BottomSheetThemeTokens, type LinkSizeTokens, type LinkThemeTokens, type BreadcrumbsSizeTokens, type BreadcrumbsThemeTokens, type CodeBlockSizeTokens, type CodeBlockThemeTokens, type DrawerThemeTokens, type MenuItemTokens, type MenuGroupTokens, type MenuThemeTokens, type ToggleButtonGroupSizeTokens, type ToggleButtonGroupThemeTokens, type AppBarSizeTokens, type AppBarThemeTokens, type SliderSizeTokens, type SliderThemeTokens, type SpeedDialSizeTokens, type SpeedDialThemeTokens, type TableSizeTokens, type TableThemeTokens, type DeepPartial, } from './theme';
3
+ export { useBreakpoint, useMinWidth, useResponsiveValue, } from './hooks';
3
4
  export { Button, type ButtonProps, type ButtonSize } from './components/Button';
4
5
  export { Icon, type IconProps } from './components/Icon';
5
6
  export { Dialog, DialogContent, type DialogProps, type DialogContentProps, type DialogAction, type DialogSize, } from './components/Dialog';
package/dist/index.js CHANGED
@@ -1,7 +1,8 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.ListDivider = exports.ListSubheader = exports.ListItem = exports.List = exports.SelectDropdown = exports.SelectTag = exports.SelectSeparator = exports.SelectGroup = exports.SelectOption = exports.Select = exports.DialogContent = exports.Dialog = exports.Icon = exports.Button = exports.applyCastTheme = exports.themes = exports.useTheme = exports.ThemeProvider = exports.iconSize = exports.caption = exports.display = exports.heading = exports.body = exports.title = exports.label = exports.fontWeight = exports.fontFamily = exports.tableColors = exports.sliderColors = exports.skeletonColors = exports.avatarColors = exports.radioColors = exports.tabsColors = exports.progressColors = exports.toggleColors = exports.checkboxColors = exports.listColors = exports.errorTokens = exports.tagTokens = exports.menuColors = exports.selectColors = exports.overlayTokens = exports.textTokens = exports.surfaceTokens = exports.controlTokens = exports.disabledColors = exports.intentColors = exports.colorSchemes = exports.darkColors = exports.lightColors = void 0;
4
- exports.Autocomplete = exports.TableCell = exports.TableRow = exports.TableBody = exports.TableHead = exports.Table = exports.SpeedDialAction = exports.SpeedDial = exports.Slider = exports.AppBar = exports.ToggleButton = exports.ToggleButtonGroup = exports.MenuContent = exports.MenuLabel = exports.MenuDivider = exports.MenuItem = exports.Menu = exports.DrawerContent = exports.Drawer = exports.CodeBlock = exports.Breadcrumb = exports.Breadcrumbs = exports.Backdrop = exports.Link = exports.AccordionItem = exports.Accordion = exports.Tab = exports.Tabs = exports.BottomSheetContent = exports.BottomSheet = exports.Spinner = exports.Progress = exports.Text = exports.Tooltip = exports.Skeleton = exports.Popover = exports.Avatar = exports.Divider = exports.Chip = exports.Toast = exports.RadioGroup = exports.Radio = exports.Input = exports.Badge = exports.Card = exports.Toggle = exports.Alert = exports.Checkbox = void 0;
3
+ exports.SelectGroup = exports.SelectOption = exports.Select = exports.DialogContent = exports.Dialog = exports.Icon = exports.Button = exports.useResponsiveValue = exports.useMinWidth = exports.useBreakpoint = exports.applyCastTheme = exports.themes = exports.useTheme = exports.ThemeProvider = exports.resolveResponsiveValue = exports.resolveBreakpoint = exports.breakpointOrder = exports.breakpoints = exports.iconSize = exports.caption = exports.display = exports.heading = exports.body = exports.title = exports.label = exports.fontWeight = exports.fontFamily = exports.tableColors = exports.sliderColors = exports.skeletonColors = exports.avatarColors = exports.radioColors = exports.tabsColors = exports.progressColors = exports.toggleColors = exports.checkboxColors = exports.listColors = exports.errorTokens = exports.tagTokens = exports.menuColors = exports.selectColors = exports.overlayTokens = exports.textTokens = exports.surfaceTokens = exports.controlTokens = exports.disabledColors = exports.intentColors = exports.colorSchemes = exports.darkColors = exports.lightColors = void 0;
4
+ exports.Table = exports.SpeedDialAction = exports.SpeedDial = exports.Slider = exports.AppBar = exports.ToggleButton = exports.ToggleButtonGroup = exports.MenuContent = exports.MenuLabel = exports.MenuDivider = exports.MenuItem = exports.Menu = exports.DrawerContent = exports.Drawer = exports.CodeBlock = exports.Breadcrumb = exports.Breadcrumbs = exports.Backdrop = exports.Link = exports.AccordionItem = exports.Accordion = exports.Tab = exports.Tabs = exports.BottomSheetContent = exports.BottomSheet = exports.Spinner = exports.Progress = exports.Text = exports.Tooltip = exports.Skeleton = exports.Popover = exports.Avatar = exports.Divider = exports.Chip = exports.Toast = exports.RadioGroup = exports.Radio = exports.Input = exports.Badge = exports.Card = exports.Toggle = exports.Alert = exports.Checkbox = exports.ListDivider = exports.ListSubheader = exports.ListItem = exports.List = exports.SelectDropdown = exports.SelectTag = exports.SelectSeparator = void 0;
5
+ exports.Autocomplete = exports.TableCell = exports.TableRow = exports.TableBody = exports.TableHead = void 0;
5
6
  // Cast UI — Cross-platform design system component library
6
7
  //
7
8
  // Tokens
@@ -38,12 +39,21 @@ Object.defineProperty(exports, "heading", { enumerable: true, get: function () {
38
39
  Object.defineProperty(exports, "display", { enumerable: true, get: function () { return tokens_1.display; } });
39
40
  Object.defineProperty(exports, "caption", { enumerable: true, get: function () { return tokens_1.caption; } });
40
41
  Object.defineProperty(exports, "iconSize", { enumerable: true, get: function () { return tokens_1.iconSize; } });
42
+ Object.defineProperty(exports, "breakpoints", { enumerable: true, get: function () { return tokens_1.breakpoints; } });
43
+ Object.defineProperty(exports, "breakpointOrder", { enumerable: true, get: function () { return tokens_1.breakpointOrder; } });
44
+ Object.defineProperty(exports, "resolveBreakpoint", { enumerable: true, get: function () { return tokens_1.resolveBreakpoint; } });
45
+ Object.defineProperty(exports, "resolveResponsiveValue", { enumerable: true, get: function () { return tokens_1.resolveResponsiveValue; } });
41
46
  // Theme
42
47
  var theme_1 = require("./theme");
43
48
  Object.defineProperty(exports, "ThemeProvider", { enumerable: true, get: function () { return theme_1.ThemeProvider; } });
44
49
  Object.defineProperty(exports, "useTheme", { enumerable: true, get: function () { return theme_1.useTheme; } });
45
50
  Object.defineProperty(exports, "themes", { enumerable: true, get: function () { return theme_1.themes; } });
46
51
  Object.defineProperty(exports, "applyCastTheme", { enumerable: true, get: function () { return theme_1.applyCastTheme; } });
52
+ // Hooks
53
+ var hooks_1 = require("./hooks");
54
+ Object.defineProperty(exports, "useBreakpoint", { enumerable: true, get: function () { return hooks_1.useBreakpoint; } });
55
+ Object.defineProperty(exports, "useMinWidth", { enumerable: true, get: function () { return hooks_1.useMinWidth; } });
56
+ Object.defineProperty(exports, "useResponsiveValue", { enumerable: true, get: function () { return hooks_1.useResponsiveValue; } });
47
57
  // Components
48
58
  var Button_1 = require("./components/Button");
49
59
  Object.defineProperty(exports, "Button", { enumerable: true, get: function () { return Button_1.Button; } });
@@ -0,0 +1,57 @@
1
+ /**
2
+ * Breakpoint scale — named min-width thresholds in density-independent pixels.
3
+ *
4
+ * Mirrors the Figma `breakpoint/{sm,md,lg,xl}` primitive variables. This is a
5
+ * foundation reference scale, not a runtime theme value. The numbers do not
6
+ * change with density, they are not part of the ThemeProvider theme, and
7
+ * cast-sync does not export them. Read them with the useBreakpoint /
8
+ * useResponsiveValue hooks, which watch the live window width.
9
+ *
10
+ * Values follow Material 3 window size classes, which are derived from real
11
+ * device-width data across the whole spectrum. The scale is mobile-first: a
12
+ * width is "at" a breakpoint when it is greater than or equal to that
13
+ * breakpoint's value, and anything below `sm` is the implicit `base` tier.
14
+ *
15
+ * Device mapping (width in dp):
16
+ *
17
+ * base < 600 Watches, and every phone in portrait. iPhone SE 320,
18
+ * iPhone 15 390, Pro Max 430, Pixel 7 412, Apple Watch
19
+ * 136-205. This is your default, design-here-first layout.
20
+ * sm >= 600 Large phones in landscape, foldables unfolded, small
21
+ * tablets in portrait.
22
+ * md >= 840 Tablets. iPad portrait ~768-834 (sits at the top of sm),
23
+ * iPad landscape and larger tablets land here and up.
24
+ * lg >= 1200 Laptops and desktops.
25
+ * xl >= 1600 Large desktops and TVs.
26
+ *
27
+ * React Native has no CSS media queries, so a breakpoint here is a width
28
+ * threshold you compare the window against at runtime. It does not restyle
29
+ * anything on its own. Small-vs-large phone differences belong to fluid layout
30
+ * (flex, percentages, maxWidth), not breakpoints. A watch is its own surface,
31
+ * not a tier: it falls into `base` and shares the default layout, which is the
32
+ * safe behaviour for a kit that does not target watchOS.
33
+ */
34
+ /** The named breakpoint tiers. */
35
+ export type Breakpoint = 'sm' | 'md' | 'lg' | 'xl';
36
+ /** A breakpoint tier including the implicit below-`sm` base tier. */
37
+ export type BreakpointKey = 'base' | Breakpoint;
38
+ /** Min-width thresholds in dp (Material 3 window size classes). */
39
+ export declare const breakpoints: Record<Breakpoint, number>;
40
+ /** Tiers ordered smallest to largest, base first. */
41
+ export declare const breakpointOrder: readonly BreakpointKey[];
42
+ /**
43
+ * Resolve a raw window width (dp) to its active breakpoint tier. Mobile-first:
44
+ * returns the largest tier whose threshold the width has reached, or `base`
45
+ * below `sm`.
46
+ */
47
+ export declare function resolveBreakpoint(width: number): BreakpointKey;
48
+ /**
49
+ * Pick a value for a tier, mobile-first. Supply values for any subset of tiers.
50
+ * The chosen value is the one at the current tier or, if that tier has none,
51
+ * the nearest defined tier below it. If nothing is defined at or below the
52
+ * current tier, the smallest defined tier above is used. Returns undefined when
53
+ * `values` is empty.
54
+ *
55
+ * resolveResponsiveValue({ base: 1, md: 2, xl: 4 }, 'lg') // => 2
56
+ */
57
+ export declare function resolveResponsiveValue<T>(values: Partial<Record<BreakpointKey, T>>, current: BreakpointKey): T | undefined;
@@ -0,0 +1,92 @@
1
+ "use strict";
2
+ /**
3
+ * Breakpoint scale — named min-width thresholds in density-independent pixels.
4
+ *
5
+ * Mirrors the Figma `breakpoint/{sm,md,lg,xl}` primitive variables. This is a
6
+ * foundation reference scale, not a runtime theme value. The numbers do not
7
+ * change with density, they are not part of the ThemeProvider theme, and
8
+ * cast-sync does not export them. Read them with the useBreakpoint /
9
+ * useResponsiveValue hooks, which watch the live window width.
10
+ *
11
+ * Values follow Material 3 window size classes, which are derived from real
12
+ * device-width data across the whole spectrum. The scale is mobile-first: a
13
+ * width is "at" a breakpoint when it is greater than or equal to that
14
+ * breakpoint's value, and anything below `sm` is the implicit `base` tier.
15
+ *
16
+ * Device mapping (width in dp):
17
+ *
18
+ * base < 600 Watches, and every phone in portrait. iPhone SE 320,
19
+ * iPhone 15 390, Pro Max 430, Pixel 7 412, Apple Watch
20
+ * 136-205. This is your default, design-here-first layout.
21
+ * sm >= 600 Large phones in landscape, foldables unfolded, small
22
+ * tablets in portrait.
23
+ * md >= 840 Tablets. iPad portrait ~768-834 (sits at the top of sm),
24
+ * iPad landscape and larger tablets land here and up.
25
+ * lg >= 1200 Laptops and desktops.
26
+ * xl >= 1600 Large desktops and TVs.
27
+ *
28
+ * React Native has no CSS media queries, so a breakpoint here is a width
29
+ * threshold you compare the window against at runtime. It does not restyle
30
+ * anything on its own. Small-vs-large phone differences belong to fluid layout
31
+ * (flex, percentages, maxWidth), not breakpoints. A watch is its own surface,
32
+ * not a tier: it falls into `base` and shares the default layout, which is the
33
+ * safe behaviour for a kit that does not target watchOS.
34
+ */
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.breakpointOrder = exports.breakpoints = void 0;
37
+ exports.resolveBreakpoint = resolveBreakpoint;
38
+ exports.resolveResponsiveValue = resolveResponsiveValue;
39
+ /** Min-width thresholds in dp (Material 3 window size classes). */
40
+ exports.breakpoints = {
41
+ sm: 600,
42
+ md: 840,
43
+ lg: 1200,
44
+ xl: 1600,
45
+ };
46
+ /** Tiers ordered smallest to largest, base first. */
47
+ exports.breakpointOrder = [
48
+ 'base',
49
+ 'sm',
50
+ 'md',
51
+ 'lg',
52
+ 'xl',
53
+ ];
54
+ /**
55
+ * Resolve a raw window width (dp) to its active breakpoint tier. Mobile-first:
56
+ * returns the largest tier whose threshold the width has reached, or `base`
57
+ * below `sm`.
58
+ */
59
+ function resolveBreakpoint(width) {
60
+ if (width >= exports.breakpoints.xl)
61
+ return 'xl';
62
+ if (width >= exports.breakpoints.lg)
63
+ return 'lg';
64
+ if (width >= exports.breakpoints.md)
65
+ return 'md';
66
+ if (width >= exports.breakpoints.sm)
67
+ return 'sm';
68
+ return 'base';
69
+ }
70
+ /**
71
+ * Pick a value for a tier, mobile-first. Supply values for any subset of tiers.
72
+ * The chosen value is the one at the current tier or, if that tier has none,
73
+ * the nearest defined tier below it. If nothing is defined at or below the
74
+ * current tier, the smallest defined tier above is used. Returns undefined when
75
+ * `values` is empty.
76
+ *
77
+ * resolveResponsiveValue({ base: 1, md: 2, xl: 4 }, 'lg') // => 2
78
+ */
79
+ function resolveResponsiveValue(values, current) {
80
+ const idx = exports.breakpointOrder.indexOf(current);
81
+ for (let i = idx; i >= 0; i--) {
82
+ const v = values[exports.breakpointOrder[i]];
83
+ if (v !== undefined)
84
+ return v;
85
+ }
86
+ for (let i = idx + 1; i < exports.breakpointOrder.length; i++) {
87
+ const v = values[exports.breakpointOrder[i]];
88
+ if (v !== undefined)
89
+ return v;
90
+ }
91
+ return undefined;
92
+ }
@@ -1,3 +1,4 @@
1
1
  export { lightColors, darkColors, colorSchemes, intentColors, disabledColors, controlTokens, surfaceTokens, textTokens, overlayTokens, selectColors, menuColors, tagTokens, errorTokens, listColors, checkboxColors, toggleColors, progressColors, tabsColors, radioColors, avatarColors, skeletonColors, sliderColors, tableColors, type IntentName, type ProminenceName, type StateName, type ColorMode, type ColorScheme, } from './colors';
2
2
  export { fontFamily, fontWeight, label, title, body, heading, display, caption, type LabelSize, } from './typography';
3
3
  export { iconSize, type IconSize } from './icon';
4
+ export { breakpoints, breakpointOrder, resolveBreakpoint, resolveResponsiveValue, type Breakpoint, type BreakpointKey, } from './breakpoints';
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.iconSize = exports.caption = exports.display = exports.heading = exports.body = exports.title = exports.label = exports.fontWeight = exports.fontFamily = exports.tableColors = exports.sliderColors = exports.skeletonColors = exports.avatarColors = exports.radioColors = exports.tabsColors = exports.progressColors = exports.toggleColors = exports.checkboxColors = exports.listColors = exports.errorTokens = exports.tagTokens = exports.menuColors = exports.selectColors = exports.overlayTokens = exports.textTokens = exports.surfaceTokens = exports.controlTokens = exports.disabledColors = exports.intentColors = exports.colorSchemes = exports.darkColors = exports.lightColors = void 0;
3
+ exports.resolveResponsiveValue = exports.resolveBreakpoint = exports.breakpointOrder = exports.breakpoints = exports.iconSize = exports.caption = exports.display = exports.heading = exports.body = exports.title = exports.label = exports.fontWeight = exports.fontFamily = exports.tableColors = exports.sliderColors = exports.skeletonColors = exports.avatarColors = exports.radioColors = exports.tabsColors = exports.progressColors = exports.toggleColors = exports.checkboxColors = exports.listColors = exports.errorTokens = exports.tagTokens = exports.menuColors = exports.selectColors = exports.overlayTokens = exports.textTokens = exports.surfaceTokens = exports.controlTokens = exports.disabledColors = exports.intentColors = exports.colorSchemes = exports.darkColors = exports.lightColors = void 0;
4
4
  var colors_1 = require("./colors");
5
5
  Object.defineProperty(exports, "lightColors", { enumerable: true, get: function () { return colors_1.lightColors; } });
6
6
  Object.defineProperty(exports, "darkColors", { enumerable: true, get: function () { return colors_1.darkColors; } });
@@ -36,3 +36,8 @@ Object.defineProperty(exports, "display", { enumerable: true, get: function () {
36
36
  Object.defineProperty(exports, "caption", { enumerable: true, get: function () { return typography_1.caption; } });
37
37
  var icon_1 = require("./icon");
38
38
  Object.defineProperty(exports, "iconSize", { enumerable: true, get: function () { return icon_1.iconSize; } });
39
+ var breakpoints_1 = require("./breakpoints");
40
+ Object.defineProperty(exports, "breakpoints", { enumerable: true, get: function () { return breakpoints_1.breakpoints; } });
41
+ Object.defineProperty(exports, "breakpointOrder", { enumerable: true, get: function () { return breakpoints_1.breakpointOrder; } });
42
+ Object.defineProperty(exports, "resolveBreakpoint", { enumerable: true, get: function () { return breakpoints_1.resolveBreakpoint; } });
43
+ Object.defineProperty(exports, "resolveResponsiveValue", { enumerable: true, get: function () { return breakpoints_1.resolveResponsiveValue; } });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@castui/cast-ui",
3
- "version": "4.8.0",
3
+ "version": "4.9.0",
4
4
  "description": "A cross-platform design system for React Native (iOS, Android, Web) with multi-theme support.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",