@titan-design/react-ui 0.9.1 → 0.9.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.
@@ -1,517 +1,318 @@
1
1
  import { ViewStyle, ViewProps } from 'react-native';
2
2
 
3
3
  /**
4
- * Elevation System
5
- *
6
- * A unified depth system where each elevation level corresponds to:
7
- * - Calculated surface color (derived from base using lighten)
8
- * - Shadow intensity and style (raised/pressed)
9
- * - Dynamically calculated shadow colors (derived from surface color)
10
- * - Semantic name for reference
11
- *
12
- * Elevation range: -2 (deep inset) to +5 (floating overlay)
13
- *
14
- * Negative elevations: Inset/pressed elements (sunken into surface)
15
- * Zero elevation: Base surface (background/page level)
16
- * Positive elevations: Raised elements (floating above surface)
17
- *
18
- * All colors are calculated dynamically from a base surface color,
19
- * allowing for custom surfaces and consistent color relationships.
20
- *
21
- * Lighting Model: Light source from upper-right corner
22
- * - Raised elements are always lighter than base (consistent across themes)
23
- * - Base colors must allow sufficient lightening in both themes
24
- */
25
-
26
- type ElevationLevel = -2 | -1 | 0 | 1 | 2 | 3 | 4 | 5;
27
- interface ElevationConfig {
28
- /** Semantic name for this elevation level */
29
- name: string;
30
- /** Amount to lighten base color (0-1) */
31
- colorAdjustment: number;
32
- /** Shadow intensity */
33
- shadowIntensity: 'subtle' | 'medium' | 'strong';
34
- /** Shadow style: raised (floating) or pressed (inset) */
35
- shadowStyle: 'raised' | 'pressed';
36
- /** Description of use case */
37
- description: string;
38
- }
39
- declare const elevationSystem: Record<ElevationLevel, ElevationConfig>;
40
- /**
41
- * Get elevation configuration for a given level
42
- */
43
- declare function getElevationConfig(level: ElevationLevel): ElevationConfig;
44
- /**
45
- * Calculate surface color for an elevation level from a base color.
46
- * Results are cached to avoid redundant calculations.
47
- *
48
- * @param baseColor - Base surface color (hex)
49
- * @param level - Elevation level
50
- * @param theme - Current theme ('light' or 'dark')
51
- * @returns Calculated surface color (hex)
52
- */
53
- declare function getElevationSurface(baseColor: string, level: ElevationLevel, theme: 'light' | 'dark'): string;
54
- /**
55
- * Get shadow style for an elevation level, calculated dynamically from surface color.
56
- * Results are cached to avoid redundant calculations.
57
- *
58
- * @param baseColor - Base surface color (hex)
59
- * @param level - Elevation level
60
- * @param theme - Current theme ('light' or 'dark')
61
- * @param isHovered - Whether element is hovered
62
- * @returns ViewStyle with shadow properties
63
- */
64
- declare function getElevationShadow(baseColor: string, level: ElevationLevel, theme: 'light' | 'dark', isHovered?: boolean): ViewStyle;
65
- /**
66
- * Get base surface color from theme.
67
- * This is the foundation color that all elevations are calculated from.
68
- *
69
- * IMPORTANT: Base colors must be chosen to allow sufficient lightening.
70
- *
71
- * **Light Mode**: Cannot use `#FFFFFF` (white) - cannot lighten white!
72
- * - Use `#F3F4F6` (neutral[100]) - can lighten to `#FAFAFA` → `#FFFFFF`
73
- * - This allows raised elevations to be lighter (closer to white)
4
+ * Semantic Design Tokens
74
5
  *
75
- * **Dark Mode**: Need lighter base to allow sufficient lightening
76
- * - Use `#191919` (charcoal[600]) - allows lightening to `#2A2A2A` at max elevation
6
+ * Meaningful tokens following DTCG (Design Tokens Community Group) naming conventions.
7
+ * Pattern: {category}-{intent}-{variant?}-{state?}
77
8
  *
78
- * Can be overridden to use custom base colors for special cases.
79
- */
80
- declare function getBaseSurfaceColor(theme: 'light' | 'dark'): string;
81
- /**
82
- * Component-specific elevation ranges
83
- * Defines which elevation levels each component type can use
9
+ * Categories:
10
+ * - brand-* : Brand colors (primary, secondary, accent)
11
+ * - status-* : Feedback colors (success, error, warning, info)
12
+ * - result-* : Outcome indicators (improve, degrade, inconclusive, neutral)
13
+ * - data-* : Data visualization colors (chart series)
14
+ * - on-* : Text on colored backgrounds
15
+ * - surface-* : Elevated containers (NOT "paper")
16
+ * - background-* : Page backgrounds
17
+ * - text-* : Text colors
18
+ * - border-* : Border colors
19
+ * - interactive-* : Hover/focus/active/disabled states
84
20
  */
85
- declare const componentElevationRanges: {
86
- readonly button: {
87
- readonly allowed: readonly [2];
88
- readonly default: 2;
89
- readonly hover: 3;
90
- };
91
- readonly card: {
92
- readonly allowed: readonly [1, 2, 3];
93
- readonly default: 2;
94
- readonly hover: 3;
95
- };
96
- readonly input: {
97
- readonly allowed: readonly [-2, -1, 0];
98
- readonly default: -1;
99
- };
100
- readonly overlay: {
101
- readonly allowed: readonly [4, 5];
102
- readonly default: 4;
103
- };
21
+ declare const semanticColorsLight: {
22
+ readonly 'brand-primary': "#FF7900";
23
+ readonly 'brand-primary-light': "#FFA063";
24
+ readonly 'brand-primary-dark': "#DA5F00";
25
+ readonly 'brand-primary-subtle': "rgba(255, 121, 0, 0.08)";
26
+ readonly 'brand-primary-hover': "#DA5F00";
27
+ readonly 'brand-primary-active': "#B94A00";
28
+ readonly 'brand-secondary': "#307B9B";
29
+ readonly 'brand-secondary-light': "#2697B7";
30
+ readonly 'brand-secondary-dark': "#2A617F";
31
+ readonly 'brand-secondary-subtle': "rgba(48, 123, 155, 0.08)";
32
+ readonly 'brand-secondary-hover': "#2A617F";
33
+ readonly 'brand-secondary-active': "#22465F";
34
+ readonly 'on-brand-primary': "#FFFFFF";
35
+ readonly 'on-brand-secondary': "#FFFFFF";
36
+ readonly 'status-success': "#2ED573";
37
+ readonly 'status-success-light': "#58F69E";
38
+ readonly 'status-success-dark': "#298732";
39
+ readonly 'status-success-subtle': "#E3FFEE";
40
+ readonly 'status-live': "#2ED573";
41
+ readonly 'status-live-muted': "#22A444";
42
+ readonly 'status-error': "#D14343";
43
+ readonly 'status-error-light': "#E05254";
44
+ readonly 'status-error-dark': "#A4221C";
45
+ readonly 'status-error-subtle': "#FFF4F4";
46
+ readonly 'status-error-vivid': "#FF4757";
47
+ readonly 'status-error-vivid-light': "#FF6070";
48
+ readonly 'status-error-vivid-dark': "#C42539";
49
+ readonly 'status-error-vivid-subtle': "rgba(255, 71, 87, 0.12)";
50
+ readonly 'status-warning': "#F9B415";
51
+ readonly 'status-warning-light': "#FFD352";
52
+ readonly 'status-warning-dark': "#C27400";
53
+ readonly 'status-warning-subtle': "#FFF7DD";
54
+ readonly 'status-info': "#2196F3";
55
+ readonly 'status-info-light': "#78C2FF";
56
+ readonly 'status-info-dark': "#1072CB";
57
+ readonly 'status-info-subtle': "#EFF8FF";
58
+ readonly 'on-status-success': "#FFFFFF";
59
+ readonly 'on-status-error': "#FFFFFF";
60
+ readonly 'on-status-warning': "#FFFFFF";
61
+ readonly 'on-status-info': "#FFFFFF";
62
+ readonly 'result-improve': "#4caf50";
63
+ readonly 'result-improve-light': "rgba(76, 175, 80, 0.12)";
64
+ readonly 'result-improve-dark': "#248a24";
65
+ readonly 'result-degrade': "#ef5350";
66
+ readonly 'result-degrade-light': "rgba(239, 83, 80, 0.12)";
67
+ readonly 'result-degrade-dark': "#b30000";
68
+ readonly 'result-inconclusive': "#9E9A97";
69
+ readonly 'result-inconclusive-light': "rgba(158, 154, 151, 0.12)";
70
+ readonly 'result-neutral': "#6B7280";
71
+ readonly 'on-result-improve': "#FFFFFF";
72
+ readonly 'on-result-degrade': "#FFFFFF";
73
+ readonly 'on-result-inconclusive': "#FFFFFF";
74
+ readonly 'data-1': "#1965B0";
75
+ readonly 'data-2': "#4EB265";
76
+ readonly 'data-3': "#F7F056";
77
+ readonly 'data-4': "#DC050C";
78
+ readonly 'data-5': "#882E72";
79
+ readonly 'data-6': "#F4A736";
80
+ readonly 'data-7': "#7BAFDE";
81
+ readonly 'data-8': "#90C987";
82
+ readonly 'data-9': "#CAACCB";
83
+ readonly 'data-10': "#EE8026";
84
+ readonly 'text-primary': "#121828";
85
+ readonly 'text-secondary': "#65748B";
86
+ readonly 'text-tertiary': "#9CA3AF";
87
+ readonly 'text-disabled': "rgba(55, 65, 81, 0.48)";
88
+ readonly 'text-inverse': "#FFFFFF";
89
+ readonly 'text-link': "#5048E5";
90
+ readonly 'text-link-hover': "#3832A0";
91
+ readonly 'surface-base': "#FFFFFF";
92
+ readonly 'surface-elevated': "#FAFAFA";
93
+ readonly 'surface-raised': "#F3F4F6";
94
+ readonly 'surface-overlay': "#FFFFFF";
95
+ readonly 'surface-input': "#FAFAFA";
96
+ readonly 'background-base': "#EBEBEB";
97
+ readonly 'background-default': "#FFFFFF";
98
+ readonly 'background-subtle': "#FAFAFA";
99
+ readonly 'border-default': "#E8E9EB";
100
+ readonly 'border-subtle': "#F3F4F6";
101
+ readonly 'border-strong': "#D1D5DB";
102
+ readonly 'border-prominent': "#9CA3AF";
103
+ readonly 'border-focus': "#5048E5";
104
+ readonly 'border-input': "#D1D5DB";
105
+ readonly 'border-input-hover': "#9CA3AF";
106
+ readonly 'border-input-focus': "#5048E5";
107
+ readonly 'border-input-error': "#D14343";
108
+ readonly 'interactive-hover': "rgba(55, 65, 81, 0.04)";
109
+ readonly 'interactive-focus': "rgba(55, 65, 81, 0.12)";
110
+ readonly 'interactive-active': "rgba(55, 65, 81, 0.16)";
111
+ readonly 'interactive-selected': "rgba(55, 65, 81, 0.08)";
112
+ readonly 'interactive-disabled': "rgba(55, 65, 81, 0.12)";
113
+ readonly 'interactive-disabled-text': "rgba(55, 65, 81, 0.26)";
114
+ readonly divider: "#E8E9EB";
115
+ readonly 'avatar-background': "#6B7280";
116
+ readonly 'avatar-text': "#FFFFFF";
104
117
  };
105
- type ComponentType = keyof typeof componentElevationRanges;
106
- /**
107
- * Validate and clamp elevation to component's allowed range
108
- */
109
- declare function getValidatedElevation(component: ComponentType, requested: ElevationLevel): ElevationLevel;
110
- type GlowIntensity = 'subtle' | 'medium' | 'strong';
111
- /**
112
- * Get a glow shadow style for emphasis/active states.
113
- *
114
- * Creates a colored radial glow around an element, useful for:
115
- * - Active recording indicators (orange glow)
116
- * - Success states (green glow)
117
- * - Error/danger indicators (red glow)
118
- * - Focus rings and attention-drawing elements
119
- *
120
- * @param color - Glow color (hex string, e.g. '#FF7900')
121
- * @param intensity - Glow intensity level
122
- * @returns ViewStyle with platform-specific shadow properties
123
- */
124
- declare function getGlowShadow(color: string, intensity?: GlowIntensity): ViewStyle;
125
-
126
- /**
127
- * Primitive Design Tokens
128
- *
129
- * Raw values with no semantic meaning. These are the foundation of the design system
130
- * and should rarely be used directly in components. Use semantic tokens instead.
131
- */
132
- declare const primitiveColors: {
133
- readonly blue: {
134
- readonly 50: "#EFF6FF";
135
- readonly 100: "#DBEAFE";
136
- readonly 200: "#BFDBFE";
137
- readonly 300: "#93C5FD";
138
- readonly 400: "#60A5FA";
139
- readonly 500: "#3B82F6";
140
- readonly 600: "#5048E5";
141
- readonly 700: "#3832A0";
142
- readonly 800: "#1E40AF";
143
- readonly 900: "#1E3A8A";
144
- };
145
- readonly red: {
146
- readonly 50: "#FEF2F2";
147
- readonly 100: "#FEE2E2";
148
- readonly 200: "#FECACA";
149
- readonly 300: "#FCA5A5";
150
- readonly 400: "#DA6868";
151
- readonly 500: "#EF4444";
152
- readonly 600: "#D14343";
153
- readonly 700: "#922E2E";
154
- readonly 800: "#991B1B";
155
- readonly 900: "#7F1D1D";
118
+ declare const semanticColorsDark: {
119
+ readonly 'brand-primary': "#FF7900";
120
+ readonly 'brand-primary-light': "#FFA063";
121
+ readonly 'brand-primary-dark': "#DA5F00";
122
+ readonly 'brand-primary-subtle': "rgba(255, 121, 0, 0.12)";
123
+ readonly 'brand-primary-hover': "#FFA063";
124
+ readonly 'brand-primary-active': "#FFC7A2";
125
+ readonly 'brand-secondary': "#307B9B";
126
+ readonly 'brand-secondary-light': "#2697B7";
127
+ readonly 'brand-secondary-dark': "#2A617F";
128
+ readonly 'brand-secondary-subtle': "rgba(48, 123, 155, 0.12)";
129
+ readonly 'brand-secondary-hover': "#2697B7";
130
+ readonly 'brand-secondary-active': "#01B5D1";
131
+ readonly 'on-brand-primary': "#FFFFFF";
132
+ readonly 'on-brand-secondary': "#FFFFFF";
133
+ readonly 'status-success': "#2ED573";
134
+ readonly 'status-success-light': "#58F69E";
135
+ readonly 'status-success-dark': "#298732";
136
+ readonly 'status-success-subtle': "rgba(46, 213, 115, 0.12)";
137
+ readonly 'status-live': "#2ED573";
138
+ readonly 'status-live-muted': "#22A444";
139
+ readonly 'status-error': "#D14343";
140
+ readonly 'status-error-light': "#E05254";
141
+ readonly 'status-error-dark': "#A4221C";
142
+ readonly 'status-error-subtle': "rgba(209, 67, 67, 0.12)";
143
+ readonly 'status-error-vivid': "#FF4757";
144
+ readonly 'status-error-vivid-light': "#FF6070";
145
+ readonly 'status-error-vivid-dark': "#C42539";
146
+ readonly 'status-error-vivid-subtle': "rgba(255, 71, 87, 0.12)";
147
+ readonly 'status-warning': "#F9B415";
148
+ readonly 'status-warning-light': "#FFD352";
149
+ readonly 'status-warning-dark': "#C27400";
150
+ readonly 'status-warning-subtle': "rgba(249, 180, 21, 0.12)";
151
+ readonly 'status-info': "#2196F3";
152
+ readonly 'status-info-light': "#78C2FF";
153
+ readonly 'status-info-dark': "#1072CB";
154
+ readonly 'status-info-subtle': "rgba(33, 150, 243, 0.12)";
155
+ readonly 'on-status-success': "#FFFFFF";
156
+ readonly 'on-status-error': "#FFFFFF";
157
+ readonly 'on-status-warning': "#FFFFFF";
158
+ readonly 'on-status-info': "#FFFFFF";
159
+ readonly 'result-improve': "#4caf50";
160
+ readonly 'result-improve-light': "rgba(76, 175, 80, 0.16)";
161
+ readonly 'result-improve-dark': "#248a24";
162
+ readonly 'result-degrade': "#ef5350";
163
+ readonly 'result-degrade-light': "rgba(239, 83, 80, 0.16)";
164
+ readonly 'result-degrade-dark': "#b30000";
165
+ readonly 'result-inconclusive': "#9E9A97";
166
+ readonly 'result-inconclusive-light': "rgba(158, 154, 151, 0.16)";
167
+ readonly 'result-neutral': "#9CA3AF";
168
+ readonly 'on-result-improve': "#FFFFFF";
169
+ readonly 'on-result-degrade': "#FFFFFF";
170
+ readonly 'on-result-inconclusive': "#FFFFFF";
171
+ readonly 'data-1': "#1965B0";
172
+ readonly 'data-2': "#4EB265";
173
+ readonly 'data-3': "#F7F056";
174
+ readonly 'data-4': "#DC050C";
175
+ readonly 'data-5': "#882E72";
176
+ readonly 'data-6': "#F4A736";
177
+ readonly 'data-7': "#7BAFDE";
178
+ readonly 'data-8': "#90C987";
179
+ readonly 'data-9': "#CAACCB";
180
+ readonly 'data-10': "#EE8026";
181
+ readonly 'text-primary': "#F3F4F6";
182
+ readonly 'text-secondary': "#9CA3AF";
183
+ readonly 'text-tertiary': "#6B7280";
184
+ readonly 'text-disabled': "rgba(255, 255, 255, 0.38)";
185
+ readonly 'text-inverse': "#111827";
186
+ readonly 'text-link': "#828DF8";
187
+ readonly 'text-link-hover': "#60A5FA";
188
+ readonly 'surface-base': "#161616";
189
+ readonly 'surface-elevated': "#191919";
190
+ readonly 'surface-raised': "#1C1C1C";
191
+ readonly 'surface-overlay': "#191919";
192
+ readonly 'surface-input': "#191919";
193
+ readonly 'background-base': "#101010";
194
+ readonly 'background-default': "#161616";
195
+ readonly 'background-subtle': "#1C1C1C";
196
+ readonly 'border-default': "#1F1F1F";
197
+ readonly 'border-subtle': "#1C1C1C";
198
+ readonly 'border-strong': "#2C2C2C";
199
+ readonly 'border-prominent': "#3C3C3C";
200
+ readonly 'border-focus': "#828DF8";
201
+ readonly 'border-input': "#4B5563";
202
+ readonly 'border-input-hover': "#6B7280";
203
+ readonly 'border-input-focus': "#828DF8";
204
+ readonly 'border-input-error': "#EF4444";
205
+ readonly 'interactive-hover': "rgba(255, 255, 255, 0.04)";
206
+ readonly 'interactive-focus': "rgba(255, 255, 255, 0.12)";
207
+ readonly 'interactive-active': "rgba(255, 255, 255, 0.16)";
208
+ readonly 'interactive-selected': "rgba(255, 255, 255, 0.08)";
209
+ readonly 'interactive-disabled': "rgba(255, 255, 255, 0.12)";
210
+ readonly 'interactive-disabled-text': "rgba(255, 255, 255, 0.26)";
211
+ readonly divider: "#1F1F1F";
212
+ readonly 'avatar-background': "#4B5563";
213
+ readonly 'avatar-text': "#FFFFFF";
214
+ };
215
+ declare const semanticTypography: {
216
+ readonly h1: {
217
+ readonly fontFamily: "heading";
218
+ readonly fontSize: "3.5rem";
219
+ readonly fontWeight: 700;
220
+ readonly lineHeight: 1.375;
156
221
  };
157
- readonly redVivid: {
158
- readonly 50: "#FFECEE";
159
- readonly 100: "#FFD6DB";
160
- readonly 200: "#FFB3BC";
161
- readonly 300: "#FF8593";
162
- readonly 400: "#FF6070";
163
- readonly 500: "#FF4757";
164
- readonly 600: "#E63548";
165
- readonly 700: "#C42539";
166
- readonly 800: "#9E1C2C";
167
- readonly 900: "#7A1520";
222
+ readonly h2: {
223
+ readonly fontFamily: "heading";
224
+ readonly fontSize: "3rem";
225
+ readonly fontWeight: 700;
226
+ readonly lineHeight: 1.375;
168
227
  };
169
- readonly neutral: {
170
- readonly 50: "#FAFAFA";
171
- readonly 100: "#F3F4F6";
172
- readonly 200: "#E5E7EB";
173
- readonly 300: "#D1D5DB";
174
- readonly 400: "#9CA3AF";
175
- readonly 500: "#6B7280";
176
- readonly 600: "#4B5563";
177
- readonly 700: "#374151";
178
- readonly 800: "#1F2937";
179
- readonly 900: "#111827";
180
- readonly 950: "#030712";
228
+ readonly h3: {
229
+ readonly fontFamily: "heading";
230
+ readonly fontSize: "2.25rem";
231
+ readonly fontWeight: 700;
232
+ readonly lineHeight: 1.375;
181
233
  };
182
- readonly charcoal: {
183
- readonly 0: "#6E6E6E";
184
- readonly 50: "#5D5D5D";
185
- readonly 100: "#4C4C4C";
186
- readonly 200: "#3C3C3C";
187
- readonly 300: "#2C2C2C";
188
- readonly 400: "#1F1F1F";
189
- readonly 500: "#1C1C1C";
190
- readonly 600: "#191919";
191
- readonly 700: "#161616";
192
- readonly 800: "#131313";
193
- readonly 900: "#101010";
234
+ readonly h4: {
235
+ readonly fontFamily: "heading";
236
+ readonly fontSize: "2rem";
237
+ readonly fontWeight: 700;
238
+ readonly lineHeight: 1.375;
194
239
  };
195
- readonly white: "#FFFFFF";
196
- readonly black: "#000000";
197
- readonly transparent: "transparent";
198
- };
199
- /**
200
- * Derived tonal ramps (TD-05.09 color foundations)
201
- *
202
- * Seven OKLCH-generated hue ramps, 11 perceptual lightness steps each (50 -> 950).
203
- * Built with hue-torsion + a chroma arc, anchored through existing brand/semantic
204
- * hexes. `pin` marks the step each ramp flows through its anchor.
205
- * This is the single source of truth for chromatic hexes — the categorical palette
206
- * below references these steps rather than duplicating values.
207
- * See coordination/design-explorations/foundations.
208
- */
209
- declare const primitiveRamps: {
210
- readonly red: {
211
- readonly 50: "#FFF4F4";
212
- readonly 100: "#FFE3E5";
213
- readonly 200: "#FFC2C5";
214
- readonly 300: "#FF9A9D";
215
- readonly 400: "#F77175";
216
- readonly 500: "#E05254";
217
- readonly 600: "#D14343";
218
- readonly 700: "#A4221C";
219
- readonly 800: "#7E1002";
220
- readonly 900: "#5A0900";
221
- readonly 950: "#3D0400";
240
+ readonly h5: {
241
+ readonly fontFamily: "heading";
242
+ readonly fontSize: "1.5rem";
243
+ readonly fontWeight: 600;
244
+ readonly lineHeight: 1.375;
222
245
  };
223
- readonly orange: {
224
- readonly 50: "#FFF5ED";
225
- readonly 100: "#FFE6D4";
226
- readonly 200: "#FFC7A2";
227
- readonly 300: "#FFA063";
228
- readonly 400: "#FF7900";
229
- readonly 500: "#DA5F00";
230
- readonly 600: "#B94A00";
231
- readonly 700: "#983804";
232
- readonly 800: "#6F290F";
233
- readonly 900: "#4E1C0C";
234
- readonly 950: "#331107";
246
+ readonly h6: {
247
+ readonly fontFamily: "heading";
248
+ readonly fontSize: "1.125rem";
249
+ readonly fontWeight: 600;
250
+ readonly lineHeight: 1.375;
235
251
  };
236
- readonly amber: {
237
- readonly 50: "#FFF7DD";
238
- readonly 100: "#FFEAA9";
239
- readonly 200: "#FFD352";
240
- readonly 300: "#F9B415";
241
- readonly 400: "#E08C00";
242
- readonly 500: "#C27400";
243
- readonly 600: "#A45E00";
244
- readonly 700: "#814D14";
245
- readonly 800: "#5B3A1A";
246
- readonly 900: "#442503";
247
- readonly 950: "#301500";
252
+ readonly body1: {
253
+ readonly fontFamily: "body";
254
+ readonly fontSize: "1rem";
255
+ readonly fontWeight: 400;
256
+ readonly lineHeight: 1.5;
248
257
  };
249
- readonly green: {
250
- readonly 50: "#E3FFEE";
251
- readonly 100: "#B5FFD2";
252
- readonly 200: "#58F69E";
253
- readonly 300: "#2ED573";
254
- readonly 400: "#21C05D";
255
- readonly 500: "#22A444";
256
- readonly 600: "#298732";
257
- readonly 700: "#2B6B25";
258
- readonly 800: "#264D1C";
259
- readonly 900: "#1B3515";
260
- readonly 950: "#11220D";
258
+ readonly body2: {
259
+ readonly fontFamily: "body";
260
+ readonly fontSize: "0.875rem";
261
+ readonly fontWeight: 400;
262
+ readonly lineHeight: 1.57;
261
263
  };
262
- readonly cyan: {
263
- readonly 50: "#E6FBFF";
264
- readonly 100: "#C2F6FF";
265
- readonly 200: "#62EAFF";
266
- readonly 300: "#22D3EE";
267
- readonly 400: "#01B5D1";
268
- readonly 500: "#2697B7";
269
- readonly 600: "#307B9B";
270
- readonly 700: "#2A617F";
271
- readonly 800: "#22465F";
272
- readonly 900: "#0B3149";
273
- readonly 950: "#001F36";
264
+ readonly subtitle1: {
265
+ readonly fontFamily: "body";
266
+ readonly fontSize: "1rem";
267
+ readonly fontWeight: 500;
268
+ readonly lineHeight: 1.75;
274
269
  };
275
- readonly blue: {
276
- readonly 50: "#EFF8FF";
277
- readonly 100: "#D9EFFF";
278
- readonly 200: "#ACDBFF";
279
- readonly 300: "#78C2FF";
280
- readonly 400: "#3CA8FF";
281
- readonly 500: "#2196F3";
282
- readonly 600: "#1072CB";
283
- readonly 700: "#135AA8";
284
- readonly 800: "#14407E";
285
- readonly 900: "#112C5A";
286
- readonly 950: "#091B3C";
270
+ readonly subtitle2: {
271
+ readonly fontFamily: "body";
272
+ readonly fontSize: "0.875rem";
273
+ readonly fontWeight: 500;
274
+ readonly lineHeight: 1.57;
287
275
  };
288
- readonly magenta: {
289
- readonly 50: "#FFF3F9";
290
- readonly 100: "#FFE2F1";
291
- readonly 200: "#FFBDE2";
292
- readonly 300: "#FF8FD5";
293
- readonly 400: "#ED69C3";
294
- readonly 500: "#D548AF";
295
- readonly 600: "#BA2996";
296
- readonly 700: "#9C0D7A";
297
- readonly 800: "#77005A";
298
- readonly 900: "#56003F";
299
- readonly 950: "#3B0029";
276
+ readonly caption: {
277
+ readonly fontFamily: "body";
278
+ readonly fontSize: "0.75rem";
279
+ readonly fontWeight: 400;
280
+ readonly lineHeight: 1.66;
300
281
  };
301
- };
302
- /**
303
- * Categorical (qualitative) palette — an ordered, CVD-safe series expressed as
304
- * references into {@link primitiveRamps} (one source of truth; the palette moves
305
- * with the ramps).
306
- *
307
- * Design: a single canonical hue order (blue, magenta, red, orange, green, cyan,
308
- * amber), with steps chosen vivid-midtone-first and fanned lighter/darker as the
309
- * series grows to preserve separation. The sequence is nested-stable — a chart
310
- * with N series uses the first N colors, and the series index is stable as N
311
- * changes. Colorblind-safe worst-case deuteranopia/protanopia floor 8 holds
312
- * through {@link CATEGORICAL_CVD_SAFE_MAX} colors; the 7th is an extended color
313
- * that should be paired with a legend or other secondary encoding.
314
- *
315
- * Two variants: `default` (vivid, sits on neutral/light surfaces, legible under
316
- * black text) and `dark` (deeper shades legible under white text on a fill). A
317
- * separate "light" variant was dropped — the vivid `default` picks already clear
318
- * black-text contrast, so it doubles as the light-context palette.
319
- */
320
- declare const categoricalPalette: {
321
- readonly default: readonly ["#2196F3", "#D548AF", "#E05254", "#FF7900", "#2ED573", "#22D3EE", "#A45E00"];
322
- readonly dark: readonly ["#1072CB", "#BA2996", "#E05254", "#B94A00", "#264D1C", "#22465F", "#C27400"];
323
- };
324
- /** Largest series count that holds the CVD floor without a legend. */
325
- declare const CATEGORICAL_CVD_SAFE_MAX = 6;
326
- /**
327
- * Categorical palette variant.
328
- * - `default` : vivid; neutral/light surfaces, legible under black text
329
- * - `dark` : deeper shades, legible under white text on a filled swatch
330
- */
331
- type CategoricalVariant = keyof typeof categoricalPalette;
332
- /**
333
- * Get a color from the ordered categorical palette by series index.
334
- * The palette is nested-stable, so the color for a given index does not change
335
- * with the total series count; `index` simply wraps past the end.
336
- *
337
- * @param index - 0-based series index (wraps past the end)
338
- * @param variant - `default` (black-text / light surfaces) or `dark` (white text)
339
- * @returns The hex color string
340
- */
341
- declare function getCategoricalColor(index: number, variant?: CategoricalVariant): string;
342
- /**
343
- * Diverging status scale (BodyMap training-status: under → optimal → over) as
344
- * references into {@link primitiveRamps}. A true diverging shape — `optimal` is
345
- * the lightest center, the extremes go darker — so the signal reads in lightness
346
- * (colorblind-robust; worst-case deut/protanopia min ΔE ~10.9) and the direction
347
- * reads in the blue↔red axis (the CVD-safe hue pair).
348
- *
349
- * Tuned so every stop is dark enough for the fill yet light enough that BLACK
350
- * text clears 4.5:1 on all five — no per-cell white/black flipping. The value
351
- * valley is symmetric: the two mid-arms (maintenance / approaching) sit at equal
352
- * lightness (both ~0.53 relative luminance), the ends darker.
353
- */
354
- declare const divergingScale: readonly ["#2196F3", "#22D3EE", "#58F69E", "#F9B415", "#D14343"];
355
- /**
356
- * Sequential "effort" scale (low → high intensity: green → yellow → orange → red)
357
- * as references into {@link primitiveRamps}. A 6-stop ordinal palette; the
358
- * velocity/RPE strip sub-samples it. Every adjacent pair clears the CVD floor
359
- * (min deut/protan ΔE ≥ 4.5), and within that the hue walk is kept smooth —
360
- * the amber-200 → amber-300 → orange-400 run steps the yellow→orange transition
361
- * gradually rather than lurching. Order encodes magnitude, so it tolerates the
362
- * green↔red CVD pair. Stops 0–3 take black text; the dark reds take white.
363
- */
364
- declare const sequentialEffort: readonly ["#2ED573", "#FFD352", "#F9B415", "#FF7900", "#D14343", "#A4221C"];
365
- /**
366
- * Best-contrast text color (black or white) for a solid fill — for labels sitting
367
- * on categorical/diverging/effort swatches. Uses the WCAG relative-luminance ratio.
368
- */
369
- declare function bestTextColor(hex: string): '#000000' | '#FFFFFF';
370
- /**
371
- * Discrete rainbow palette for data visualization
372
- * Based on Paul Tol's color schemes: https://personal.sron.nl/~pault/#fig:scheme_rainbow_discrete
373
- */
374
- declare const discreteRainbow: readonly ["#E8ECFB", "#D9CCE3", "#D1BBD7", "#CAACCB", "#BA8DB4", "#AE76A3", "#AA6F9E", "#994F88", "#882E72", "#1965B0", "#437DBF", "#5289C7", "#6195CF", "#7BAFDE", "#4EB265", "#90C987", "#CAE0AB", "#F7F056", "#F7CB45", "#F6C141", "#F4A736", "#F1932D", "#EE8026", "#E8601C", "#E65518", "#DC050C", "#A5170E", "#72190E", "#42150A"];
375
- /**
376
- * Get a color from the discrete rainbow palette for a given index and palette size.
377
- * Colors are optimized for visual distinction at each palette size.
378
- *
379
- * @param index - The index of the color in the series (0-based)
380
- * @param size - The total number of colors needed (1-23)
381
- * @returns The hex color string
382
- */
383
- declare function getDiscreteRainbowColor(index: number, size: number): string;
384
- declare const primitiveTypography: {
385
- readonly fontFamilies: {
386
- readonly sans: readonly ["Inter", "-apple-system", "BlinkMacSystemFont", "Segoe UI", "Helvetica", "Arial", "sans-serif"];
387
- readonly body: readonly ["Nunito Sans", "sans-serif"];
388
- readonly heading: readonly ["Space Grotesk", "sans-serif"];
389
- readonly mono: readonly ["SF Mono", "Monaco", "Inconsolata", "Fira Mono", "Droid Sans Mono", "Source Code Pro", "monospace"];
282
+ readonly overline: {
283
+ readonly fontFamily: "body";
284
+ readonly fontSize: "0.75rem";
285
+ readonly fontWeight: 600;
286
+ readonly lineHeight: 2.5;
287
+ readonly letterSpacing: "0.5px";
288
+ readonly textTransform: "uppercase";
390
289
  };
391
- readonly fontSizes: {
392
- readonly xs: "0.75rem";
393
- readonly sm: "0.875rem";
394
- readonly base: "1rem";
395
- readonly lg: "1.125rem";
396
- readonly xl: "1.5rem";
397
- readonly '2xl': "2rem";
398
- readonly '3xl': "2.25rem";
399
- readonly '4xl': "3rem";
400
- readonly '5xl': "3.5rem";
290
+ readonly button: {
291
+ readonly fontFamily: "sans";
292
+ readonly fontSize: "0.875rem";
293
+ readonly fontWeight: 600;
294
+ readonly lineHeight: 1.75;
401
295
  };
402
- readonly fontWeights: {
403
- readonly normal: 400;
404
- readonly medium: 500;
405
- readonly semibold: 600;
406
- readonly bold: 700;
296
+ };
297
+ declare const buttonSizes: {
298
+ readonly sm: {
299
+ readonly paddingX: "16px";
300
+ readonly paddingY: "6px";
301
+ readonly fontSize: "0.875rem";
407
302
  };
408
- readonly lineHeights: {
409
- readonly none: 1;
410
- readonly tight: 1.375;
411
- readonly snug: 1.5;
412
- readonly normal: 1.57;
413
- readonly relaxed: 1.66;
414
- readonly loose: 1.75;
303
+ readonly md: {
304
+ readonly paddingX: "20px";
305
+ readonly paddingY: "8px";
306
+ readonly fontSize: "0.875rem";
415
307
  };
416
- readonly letterSpacing: {
417
- readonly tighter: "-0.05em";
418
- readonly tight: "-0.025em";
419
- readonly normal: "0em";
420
- readonly wide: "0.025em";
421
- readonly wider: "0.05em";
422
- readonly widest: "0.5px";
308
+ readonly lg: {
309
+ readonly paddingX: "24px";
310
+ readonly paddingY: "11px";
311
+ readonly fontSize: "1rem";
423
312
  };
424
313
  };
425
- declare const primitiveSpacing: {
426
- readonly 0: "0";
427
- readonly px: "1px";
428
- readonly 0.5: "0.125rem";
429
- readonly 1: "0.25rem";
430
- readonly 1.5: "0.375rem";
431
- readonly 2: "0.5rem";
432
- readonly 2.5: "0.625rem";
433
- readonly 3: "0.75rem";
434
- readonly 3.5: "0.875rem";
435
- readonly 4: "1rem";
436
- readonly 5: "1.25rem";
437
- readonly 6: "1.5rem";
438
- readonly 7: "1.75rem";
439
- readonly 8: "2rem";
440
- readonly 9: "2.25rem";
441
- readonly 10: "2.5rem";
442
- readonly 11: "2.75rem";
443
- readonly 12: "3rem";
444
- readonly 14: "3.5rem";
445
- readonly 16: "4rem";
446
- readonly 20: "5rem";
447
- readonly 24: "6rem";
448
- readonly 28: "7rem";
449
- readonly 32: "8rem";
450
- };
451
- declare const primitiveBorderRadius: {
452
- readonly none: "0";
453
- readonly sm: "4px";
454
- readonly DEFAULT: "8px";
455
- readonly md: "8px";
456
- readonly lg: "12px";
457
- readonly xl: "16px";
458
- readonly '2xl': "24px";
459
- readonly full: "9999px";
460
- };
461
- declare const primitiveShadows: {
462
- readonly none: "none";
463
- readonly sm: "0px 1px 2px rgba(100, 116, 139, 0.12)";
464
- readonly DEFAULT: "0px 1px 3px rgba(100, 116, 139, 0.12), 0px 1px 2px rgba(100, 116, 139, 0.24)";
465
- readonly md: "0px 4px 6px rgba(100, 116, 139, 0.12)";
466
- readonly lg: "0px 10px 15px rgba(100, 116, 139, 0.12)";
467
- readonly xl: "0px 20px 25px rgba(100, 116, 139, 0.12)";
468
- readonly '2xl': "0px 25px 50px rgba(100, 116, 139, 0.25)";
469
- readonly inner: "inset 0 2px 4px 0 rgba(0, 0, 0, 0.06)";
470
- };
471
- declare const primitiveBreakpoints: {
472
- readonly xs: 0;
473
- readonly sm: 600;
474
- readonly md: 1000;
475
- readonly lg: 1200;
476
- readonly xl: 1920;
477
- };
478
- declare const primitiveZIndex: {
479
- readonly hide: -1;
480
- readonly auto: "auto";
481
- readonly base: 0;
482
- readonly docked: 10;
483
- readonly dropdown: 1000;
484
- readonly sticky: 1100;
485
- readonly drawer: 1100;
486
- readonly banner: 1200;
487
- readonly appBar: 1200;
488
- readonly overlay: 1300;
489
- readonly modal: 1400;
490
- readonly popover: 1500;
491
- readonly skipLink: 1600;
492
- readonly toast: 1700;
493
- readonly tooltip: 1800;
494
- };
495
-
496
- /**
497
- * Semantic Design Tokens
498
- *
499
- * Meaningful tokens following DTCG (Design Tokens Community Group) naming conventions.
500
- * Pattern: {category}-{intent}-{variant?}-{state?}
501
- *
502
- * Categories:
503
- * - brand-* : Brand colors (primary, secondary, accent)
504
- * - status-* : Feedback colors (success, error, warning, info)
505
- * - result-* : Outcome indicators (improve, degrade, inconclusive, neutral)
506
- * - data-* : Data visualization colors (chart series)
507
- * - on-* : Text on colored backgrounds
508
- * - surface-* : Elevated containers (NOT "paper")
509
- * - background-* : Page backgrounds
510
- * - text-* : Text colors
511
- * - border-* : Border colors
512
- * - interactive-* : Hover/focus/active/disabled states
513
- */
514
- declare const semanticColorsLight: {
314
+ type ThemeMode = 'light' | 'dark';
315
+ declare function getSemanticColors(mode: ThemeMode): {
515
316
  readonly 'brand-primary': "#FF7900";
516
317
  readonly 'brand-primary-light': "#FFA063";
517
318
  readonly 'brand-primary-dark': "#DA5F00";
@@ -607,8 +408,7 @@ declare const semanticColorsLight: {
607
408
  readonly divider: "#E8E9EB";
608
409
  readonly 'avatar-background': "#6B7280";
609
410
  readonly 'avatar-text': "#FFFFFF";
610
- };
611
- declare const semanticColorsDark: {
411
+ } | {
612
412
  readonly 'brand-primary': "#FF7900";
613
413
  readonly 'brand-primary-light': "#FFA063";
614
414
  readonly 'brand-primary-dark': "#DA5F00";
@@ -705,298 +505,498 @@ declare const semanticColorsDark: {
705
505
  readonly 'avatar-background': "#4B5563";
706
506
  readonly 'avatar-text': "#FFFFFF";
707
507
  };
708
- declare const semanticTypography: {
709
- readonly h1: {
710
- readonly fontFamily: "heading";
711
- readonly fontSize: "3.5rem";
712
- readonly fontWeight: 700;
713
- readonly lineHeight: 1.375;
714
- };
715
- readonly h2: {
716
- readonly fontFamily: "heading";
717
- readonly fontSize: "3rem";
718
- readonly fontWeight: 700;
719
- readonly lineHeight: 1.375;
508
+
509
+ /**
510
+ * Elevation System
511
+ *
512
+ * A unified depth system where each elevation level corresponds to:
513
+ * - Calculated surface color (derived from base using lighten)
514
+ * - Shadow intensity and style (raised/pressed)
515
+ * - Dynamically calculated shadow colors (derived from surface color)
516
+ * - Semantic name for reference
517
+ *
518
+ * Elevation range: -2 (deep inset) to +5 (floating overlay)
519
+ *
520
+ * Negative elevations: Inset/pressed elements (sunken into surface)
521
+ * Zero elevation: Base surface (background/page level)
522
+ * Positive elevations: Raised elements (floating above surface)
523
+ *
524
+ * All colors are calculated dynamically from a base surface color,
525
+ * allowing for custom surfaces and consistent color relationships.
526
+ *
527
+ * Lighting Model: Light source from upper-right corner
528
+ * - Raised elements are always lighter than base (consistent across themes)
529
+ * - Base colors must allow sufficient lightening in both themes
530
+ */
531
+
532
+ type ElevationLevel = -2 | -1 | 0 | 1 | 2 | 3 | 4 | 5;
533
+ interface ElevationConfig {
534
+ /** Semantic name for this elevation level */
535
+ name: string;
536
+ /** Amount to lighten base color (0-1) */
537
+ colorAdjustment: number;
538
+ /** Shadow intensity */
539
+ shadowIntensity: 'subtle' | 'medium' | 'strong';
540
+ /** Shadow style: raised (floating) or pressed (inset) */
541
+ shadowStyle: 'raised' | 'pressed';
542
+ /** Description of use case */
543
+ description: string;
544
+ }
545
+ declare const elevationSystem: Record<ElevationLevel, ElevationConfig>;
546
+ /**
547
+ * Get elevation configuration for a given level
548
+ */
549
+ declare function getElevationConfig(level: ElevationLevel): ElevationConfig;
550
+ /**
551
+ * Calculate surface color for an elevation level from a base color.
552
+ * Results are cached to avoid redundant calculations.
553
+ *
554
+ * @param baseColor - Base surface color (hex)
555
+ * @param level - Elevation level
556
+ * @param theme - Current theme ('light' or 'dark')
557
+ * @returns Calculated surface color (hex)
558
+ */
559
+ declare function getElevationSurface(baseColor: string, level: ElevationLevel, theme: 'light' | 'dark'): string;
560
+ /**
561
+ * Get shadow style for an elevation level, calculated dynamically from surface color.
562
+ * Results are cached to avoid redundant calculations.
563
+ *
564
+ * @param baseColor - Base surface color (hex)
565
+ * @param level - Elevation level
566
+ * @param theme - Current theme ('light' or 'dark')
567
+ * @param isHovered - Whether element is hovered
568
+ * @returns ViewStyle with shadow properties
569
+ */
570
+ declare function getElevationShadow(baseColor: string, level: ElevationLevel, theme: 'light' | 'dark', isHovered?: boolean): ViewStyle;
571
+ /**
572
+ * Get base surface color from theme.
573
+ * This is the foundation color that all elevations are calculated from.
574
+ *
575
+ * IMPORTANT: Base colors must be chosen to allow sufficient lightening.
576
+ *
577
+ * **Light Mode**: Cannot use `#FFFFFF` (white) - cannot lighten white!
578
+ * - Use `#F3F4F6` (neutral[100]) - can lighten to `#FAFAFA` → `#FFFFFF`
579
+ * - This allows raised elevations to be lighter (closer to white)
580
+ *
581
+ * **Dark Mode**: Need lighter base to allow sufficient lightening
582
+ * - Use `#191919` (charcoal[600]) - allows lightening to `#2A2A2A` at max elevation
583
+ *
584
+ * Can be overridden to use custom base colors for special cases.
585
+ */
586
+ declare function getBaseSurfaceColor(theme: 'light' | 'dark'): string;
587
+ /**
588
+ * Component-specific elevation ranges
589
+ * Defines which elevation levels each component type can use
590
+ */
591
+ declare const componentElevationRanges: {
592
+ readonly button: {
593
+ readonly allowed: readonly [2];
594
+ readonly default: 2;
595
+ readonly hover: 3;
720
596
  };
721
- readonly h3: {
722
- readonly fontFamily: "heading";
723
- readonly fontSize: "2.25rem";
724
- readonly fontWeight: 700;
725
- readonly lineHeight: 1.375;
597
+ readonly card: {
598
+ readonly allowed: readonly [1, 2, 3];
599
+ readonly default: 2;
600
+ readonly hover: 3;
726
601
  };
727
- readonly h4: {
728
- readonly fontFamily: "heading";
729
- readonly fontSize: "2rem";
730
- readonly fontWeight: 700;
731
- readonly lineHeight: 1.375;
602
+ readonly input: {
603
+ readonly allowed: readonly [-2, -1, 0];
604
+ readonly default: -1;
732
605
  };
733
- readonly h5: {
734
- readonly fontFamily: "heading";
735
- readonly fontSize: "1.5rem";
736
- readonly fontWeight: 600;
737
- readonly lineHeight: 1.375;
606
+ readonly overlay: {
607
+ readonly allowed: readonly [4, 5];
608
+ readonly default: 4;
738
609
  };
739
- readonly h6: {
740
- readonly fontFamily: "heading";
741
- readonly fontSize: "1.125rem";
742
- readonly fontWeight: 600;
743
- readonly lineHeight: 1.375;
610
+ };
611
+ type ComponentType = keyof typeof componentElevationRanges;
612
+ /**
613
+ * Validate and clamp elevation to component's allowed range
614
+ */
615
+ declare function getValidatedElevation(component: ComponentType, requested: ElevationLevel): ElevationLevel;
616
+ type GlowIntensity = 'subtle' | 'medium' | 'strong';
617
+ /**
618
+ * Get a glow shadow style for emphasis/active states.
619
+ *
620
+ * Creates a colored radial glow around an element, useful for:
621
+ * - Active recording indicators (orange glow)
622
+ * - Success states (green glow)
623
+ * - Error/danger indicators (red glow)
624
+ * - Focus rings and attention-drawing elements
625
+ *
626
+ * @param color - Glow color (hex string, e.g. '#FF7900')
627
+ * @param intensity - Glow intensity level
628
+ * @returns ViewStyle with platform-specific shadow properties
629
+ */
630
+ declare function getGlowShadow(color: string, intensity?: GlowIntensity): ViewStyle;
631
+
632
+ /**
633
+ * Primitive Design Tokens
634
+ *
635
+ * Raw values with no semantic meaning. These are the foundation of the design system
636
+ * and should rarely be used directly in components. Use semantic tokens instead.
637
+ */
638
+ declare const primitiveColors: {
639
+ readonly blue: {
640
+ readonly 50: "#EFF6FF";
641
+ readonly 100: "#DBEAFE";
642
+ readonly 200: "#BFDBFE";
643
+ readonly 300: "#93C5FD";
644
+ readonly 400: "#60A5FA";
645
+ readonly 500: "#3B82F6";
646
+ readonly 600: "#5048E5";
647
+ readonly 700: "#3832A0";
648
+ readonly 800: "#1E40AF";
649
+ readonly 900: "#1E3A8A";
744
650
  };
745
- readonly body1: {
746
- readonly fontFamily: "body";
747
- readonly fontSize: "1rem";
748
- readonly fontWeight: 400;
749
- readonly lineHeight: 1.5;
651
+ readonly red: {
652
+ readonly 50: "#FEF2F2";
653
+ readonly 100: "#FEE2E2";
654
+ readonly 200: "#FECACA";
655
+ readonly 300: "#FCA5A5";
656
+ readonly 400: "#DA6868";
657
+ readonly 500: "#EF4444";
658
+ readonly 600: "#D14343";
659
+ readonly 700: "#922E2E";
660
+ readonly 800: "#991B1B";
661
+ readonly 900: "#7F1D1D";
750
662
  };
751
- readonly body2: {
752
- readonly fontFamily: "body";
753
- readonly fontSize: "0.875rem";
754
- readonly fontWeight: 400;
755
- readonly lineHeight: 1.57;
663
+ readonly redVivid: {
664
+ readonly 50: "#FFECEE";
665
+ readonly 100: "#FFD6DB";
666
+ readonly 200: "#FFB3BC";
667
+ readonly 300: "#FF8593";
668
+ readonly 400: "#FF6070";
669
+ readonly 500: "#FF4757";
670
+ readonly 600: "#E63548";
671
+ readonly 700: "#C42539";
672
+ readonly 800: "#9E1C2C";
673
+ readonly 900: "#7A1520";
756
674
  };
757
- readonly subtitle1: {
758
- readonly fontFamily: "body";
759
- readonly fontSize: "1rem";
760
- readonly fontWeight: 500;
761
- readonly lineHeight: 1.75;
675
+ readonly neutral: {
676
+ readonly 50: "#FAFAFA";
677
+ readonly 100: "#F3F4F6";
678
+ readonly 200: "#E5E7EB";
679
+ readonly 300: "#D1D5DB";
680
+ readonly 400: "#9CA3AF";
681
+ readonly 500: "#6B7280";
682
+ readonly 600: "#4B5563";
683
+ readonly 700: "#374151";
684
+ readonly 800: "#1F2937";
685
+ readonly 900: "#111827";
686
+ readonly 950: "#030712";
762
687
  };
763
- readonly subtitle2: {
764
- readonly fontFamily: "body";
765
- readonly fontSize: "0.875rem";
766
- readonly fontWeight: 500;
767
- readonly lineHeight: 1.57;
688
+ readonly charcoal: {
689
+ readonly 0: "#6E6E6E";
690
+ readonly 50: "#5D5D5D";
691
+ readonly 100: "#4C4C4C";
692
+ readonly 200: "#3C3C3C";
693
+ readonly 300: "#2C2C2C";
694
+ readonly 400: "#1F1F1F";
695
+ readonly 500: "#1C1C1C";
696
+ readonly 600: "#191919";
697
+ readonly 700: "#161616";
698
+ readonly 800: "#131313";
699
+ readonly 900: "#101010";
768
700
  };
769
- readonly caption: {
770
- readonly fontFamily: "body";
771
- readonly fontSize: "0.75rem";
772
- readonly fontWeight: 400;
773
- readonly lineHeight: 1.66;
701
+ readonly white: "#FFFFFF";
702
+ readonly black: "#000000";
703
+ readonly transparent: "transparent";
704
+ };
705
+ /**
706
+ * Derived tonal ramps (TD-05.09 color foundations)
707
+ *
708
+ * Seven OKLCH-generated hue ramps, 11 perceptual lightness steps each (50 -> 950).
709
+ * Built with hue-torsion + a chroma arc, anchored through existing brand/semantic
710
+ * hexes. `pin` marks the step each ramp flows through its anchor.
711
+ * This is the single source of truth for chromatic hexes — the categorical palette
712
+ * below references these steps rather than duplicating values.
713
+ * See coordination/design-explorations/foundations.
714
+ */
715
+ declare const primitiveRamps: {
716
+ readonly red: {
717
+ readonly 50: "#FFF4F4";
718
+ readonly 100: "#FFE3E5";
719
+ readonly 200: "#FFC2C5";
720
+ readonly 300: "#FF9A9D";
721
+ readonly 400: "#F77175";
722
+ readonly 500: "#E05254";
723
+ readonly 600: "#D14343";
724
+ readonly 700: "#A4221C";
725
+ readonly 800: "#7E1002";
726
+ readonly 900: "#5A0900";
727
+ readonly 950: "#3D0400";
774
728
  };
775
- readonly overline: {
776
- readonly fontFamily: "body";
777
- readonly fontSize: "0.75rem";
778
- readonly fontWeight: 600;
779
- readonly lineHeight: 2.5;
780
- readonly letterSpacing: "0.5px";
781
- readonly textTransform: "uppercase";
729
+ readonly orange: {
730
+ readonly 50: "#FFF5ED";
731
+ readonly 100: "#FFE6D4";
732
+ readonly 200: "#FFC7A2";
733
+ readonly 300: "#FFA063";
734
+ readonly 400: "#FF7900";
735
+ readonly 500: "#DA5F00";
736
+ readonly 600: "#B94A00";
737
+ readonly 700: "#983804";
738
+ readonly 800: "#6F290F";
739
+ readonly 900: "#4E1C0C";
740
+ readonly 950: "#331107";
782
741
  };
783
- readonly button: {
784
- readonly fontFamily: "sans";
785
- readonly fontSize: "0.875rem";
786
- readonly fontWeight: 600;
787
- readonly lineHeight: 1.75;
742
+ readonly amber: {
743
+ readonly 50: "#FFF7DD";
744
+ readonly 100: "#FFEAA9";
745
+ readonly 200: "#FFD352";
746
+ readonly 300: "#F9B415";
747
+ readonly 400: "#E08C00";
748
+ readonly 500: "#C27400";
749
+ readonly 600: "#A45E00";
750
+ readonly 700: "#814D14";
751
+ readonly 800: "#5B3A1A";
752
+ readonly 900: "#442503";
753
+ readonly 950: "#301500";
754
+ };
755
+ readonly green: {
756
+ readonly 50: "#E3FFEE";
757
+ readonly 100: "#B5FFD2";
758
+ readonly 200: "#58F69E";
759
+ readonly 300: "#2ED573";
760
+ readonly 400: "#21C05D";
761
+ readonly 500: "#22A444";
762
+ readonly 600: "#298732";
763
+ readonly 700: "#2B6B25";
764
+ readonly 800: "#264D1C";
765
+ readonly 900: "#1B3515";
766
+ readonly 950: "#11220D";
767
+ };
768
+ readonly cyan: {
769
+ readonly 50: "#E6FBFF";
770
+ readonly 100: "#C2F6FF";
771
+ readonly 200: "#62EAFF";
772
+ readonly 300: "#22D3EE";
773
+ readonly 400: "#01B5D1";
774
+ readonly 500: "#2697B7";
775
+ readonly 600: "#307B9B";
776
+ readonly 700: "#2A617F";
777
+ readonly 800: "#22465F";
778
+ readonly 900: "#0B3149";
779
+ readonly 950: "#001F36";
780
+ };
781
+ readonly blue: {
782
+ readonly 50: "#EFF8FF";
783
+ readonly 100: "#D9EFFF";
784
+ readonly 200: "#ACDBFF";
785
+ readonly 300: "#78C2FF";
786
+ readonly 400: "#3CA8FF";
787
+ readonly 500: "#2196F3";
788
+ readonly 600: "#1072CB";
789
+ readonly 700: "#135AA8";
790
+ readonly 800: "#14407E";
791
+ readonly 900: "#112C5A";
792
+ readonly 950: "#091B3C";
793
+ };
794
+ readonly magenta: {
795
+ readonly 50: "#FFF3F9";
796
+ readonly 100: "#FFE2F1";
797
+ readonly 200: "#FFBDE2";
798
+ readonly 300: "#FF8FD5";
799
+ readonly 400: "#ED69C3";
800
+ readonly 500: "#D548AF";
801
+ readonly 600: "#BA2996";
802
+ readonly 700: "#9C0D7A";
803
+ readonly 800: "#77005A";
804
+ readonly 900: "#56003F";
805
+ readonly 950: "#3B0029";
788
806
  };
789
807
  };
790
- declare const buttonSizes: {
791
- readonly sm: {
792
- readonly paddingX: "16px";
793
- readonly paddingY: "6px";
794
- readonly fontSize: "0.875rem";
808
+ /**
809
+ * Categorical (qualitative) palette — an ordered, CVD-safe series expressed as
810
+ * references into {@link primitiveRamps} (one source of truth; the palette moves
811
+ * with the ramps).
812
+ *
813
+ * Design: a single canonical hue order (blue, magenta, red, orange, green, cyan,
814
+ * amber), with steps chosen vivid-midtone-first and fanned lighter/darker as the
815
+ * series grows to preserve separation. The sequence is nested-stable — a chart
816
+ * with N series uses the first N colors, and the series index is stable as N
817
+ * changes. Colorblind-safe worst-case deuteranopia/protanopia floor 8 holds
818
+ * through {@link CATEGORICAL_CVD_SAFE_MAX} colors; the 7th is an extended color
819
+ * that should be paired with a legend or other secondary encoding.
820
+ *
821
+ * Two variants: `default` (vivid, sits on neutral/light surfaces, legible under
822
+ * black text) and `dark` (deeper shades legible under white text on a fill). A
823
+ * separate "light" variant was dropped — the vivid `default` picks already clear
824
+ * black-text contrast, so it doubles as the light-context palette.
825
+ */
826
+ declare const categoricalPalette: {
827
+ readonly default: readonly ["#2196F3", "#D548AF", "#E05254", "#FF7900", "#2ED573", "#22D3EE", "#A45E00"];
828
+ readonly dark: readonly ["#1072CB", "#BA2996", "#E05254", "#B94A00", "#264D1C", "#22465F", "#C27400"];
829
+ };
830
+ /** Largest series count that holds the CVD floor without a legend. */
831
+ declare const CATEGORICAL_CVD_SAFE_MAX = 6;
832
+ /**
833
+ * Categorical palette variant.
834
+ * - `default` : vivid; neutral/light surfaces, legible under black text
835
+ * - `dark` : deeper shades, legible under white text on a filled swatch
836
+ */
837
+ type CategoricalVariant = keyof typeof categoricalPalette;
838
+ /**
839
+ * Get a color from the ordered categorical palette by series index.
840
+ * The palette is nested-stable, so the color for a given index does not change
841
+ * with the total series count; `index` simply wraps past the end.
842
+ *
843
+ * @param index - 0-based series index (wraps past the end)
844
+ * @param variant - `default` (black-text / light surfaces) or `dark` (white text)
845
+ * @returns The hex color string
846
+ */
847
+ declare function getCategoricalColor(index: number, variant?: CategoricalVariant): string;
848
+ /**
849
+ * Diverging status scale (BodyMap training-status: under → optimal → over) as
850
+ * references into {@link primitiveRamps}. A true diverging shape — `optimal` is
851
+ * the lightest center, the extremes go darker — so the signal reads in lightness
852
+ * (colorblind-robust; worst-case deut/protanopia min ΔE ~10.9) and the direction
853
+ * reads in the blue↔red axis (the CVD-safe hue pair).
854
+ *
855
+ * Tuned so every stop is dark enough for the fill yet light enough that BLACK
856
+ * text clears 4.5:1 on all five — no per-cell white/black flipping. The value
857
+ * valley is symmetric: the two mid-arms (maintenance / approaching) sit at equal
858
+ * lightness (both ~0.53 relative luminance), the ends darker.
859
+ */
860
+ declare const divergingScale: readonly ["#2196F3", "#22D3EE", "#58F69E", "#F9B415", "#D14343"];
861
+ /**
862
+ * Sequential "effort" scale (low → high intensity: green → yellow → orange → red)
863
+ * as references into {@link primitiveRamps}. A 6-stop ordinal palette; the
864
+ * velocity/RPE strip sub-samples it. Every adjacent pair clears the CVD floor
865
+ * (min deut/protan ΔE ≥ 4.5), and within that the hue walk is kept smooth —
866
+ * the amber-200 → amber-300 → orange-400 run steps the yellow→orange transition
867
+ * gradually rather than lurching. Order encodes magnitude, so it tolerates the
868
+ * green↔red CVD pair. Stops 0–3 take black text; the dark reds take white.
869
+ */
870
+ declare const sequentialEffort: readonly ["#2ED573", "#FFD352", "#F9B415", "#FF7900", "#D14343", "#A4221C"];
871
+ /**
872
+ * Best-contrast text color (black or white) for a solid fill — for labels sitting
873
+ * on categorical/diverging/effort swatches. Uses the WCAG relative-luminance ratio.
874
+ */
875
+ declare function bestTextColor(hex: string): '#000000' | '#FFFFFF';
876
+ /**
877
+ * Discrete rainbow palette for data visualization
878
+ * Based on Paul Tol's color schemes: https://personal.sron.nl/~pault/#fig:scheme_rainbow_discrete
879
+ */
880
+ declare const discreteRainbow: readonly ["#E8ECFB", "#D9CCE3", "#D1BBD7", "#CAACCB", "#BA8DB4", "#AE76A3", "#AA6F9E", "#994F88", "#882E72", "#1965B0", "#437DBF", "#5289C7", "#6195CF", "#7BAFDE", "#4EB265", "#90C987", "#CAE0AB", "#F7F056", "#F7CB45", "#F6C141", "#F4A736", "#F1932D", "#EE8026", "#E8601C", "#E65518", "#DC050C", "#A5170E", "#72190E", "#42150A"];
881
+ /**
882
+ * Get a color from the discrete rainbow palette for a given index and palette size.
883
+ * Colors are optimized for visual distinction at each palette size.
884
+ *
885
+ * @param index - The index of the color in the series (0-based)
886
+ * @param size - The total number of colors needed (1-23)
887
+ * @returns The hex color string
888
+ */
889
+ declare function getDiscreteRainbowColor(index: number, size: number): string;
890
+ declare const primitiveTypography: {
891
+ readonly fontFamilies: {
892
+ readonly sans: readonly ["Inter", "-apple-system", "BlinkMacSystemFont", "Segoe UI", "Helvetica", "Arial", "sans-serif"];
893
+ readonly body: readonly ["Nunito Sans", "sans-serif"];
894
+ readonly heading: readonly ["Space Grotesk", "sans-serif"];
895
+ readonly mono: readonly ["SF Mono", "Monaco", "Inconsolata", "Fira Mono", "Droid Sans Mono", "Source Code Pro", "monospace"];
795
896
  };
796
- readonly md: {
797
- readonly paddingX: "20px";
798
- readonly paddingY: "8px";
799
- readonly fontSize: "0.875rem";
897
+ readonly fontSizes: {
898
+ readonly xs: "0.75rem";
899
+ readonly sm: "0.875rem";
900
+ readonly base: "1rem";
901
+ readonly lg: "1.125rem";
902
+ readonly xl: "1.5rem";
903
+ readonly '2xl': "2rem";
904
+ readonly '3xl': "2.25rem";
905
+ readonly '4xl': "3rem";
906
+ readonly '5xl': "3.5rem";
800
907
  };
801
- readonly lg: {
802
- readonly paddingX: "24px";
803
- readonly paddingY: "11px";
804
- readonly fontSize: "1rem";
908
+ readonly fontWeights: {
909
+ readonly normal: 400;
910
+ readonly medium: 500;
911
+ readonly semibold: 600;
912
+ readonly bold: 700;
913
+ };
914
+ readonly lineHeights: {
915
+ readonly none: 1;
916
+ readonly tight: 1.375;
917
+ readonly snug: 1.5;
918
+ readonly normal: 1.57;
919
+ readonly relaxed: 1.66;
920
+ readonly loose: 1.75;
921
+ };
922
+ readonly letterSpacing: {
923
+ readonly tighter: "-0.05em";
924
+ readonly tight: "-0.025em";
925
+ readonly normal: "0em";
926
+ readonly wide: "0.025em";
927
+ readonly wider: "0.05em";
928
+ readonly widest: "0.5px";
805
929
  };
806
930
  };
807
- type ThemeMode = 'light' | 'dark';
808
- declare function getSemanticColors(mode: ThemeMode): {
809
- readonly 'brand-primary': "#FF7900";
810
- readonly 'brand-primary-light': "#FFA063";
811
- readonly 'brand-primary-dark': "#DA5F00";
812
- readonly 'brand-primary-subtle': "rgba(255, 121, 0, 0.08)";
813
- readonly 'brand-primary-hover': "#DA5F00";
814
- readonly 'brand-primary-active': "#B94A00";
815
- readonly 'brand-secondary': "#307B9B";
816
- readonly 'brand-secondary-light': "#2697B7";
817
- readonly 'brand-secondary-dark': "#2A617F";
818
- readonly 'brand-secondary-subtle': "rgba(48, 123, 155, 0.08)";
819
- readonly 'brand-secondary-hover': "#2A617F";
820
- readonly 'brand-secondary-active': "#22465F";
821
- readonly 'on-brand-primary': "#FFFFFF";
822
- readonly 'on-brand-secondary': "#FFFFFF";
823
- readonly 'status-success': "#2ED573";
824
- readonly 'status-success-light': "#58F69E";
825
- readonly 'status-success-dark': "#298732";
826
- readonly 'status-success-subtle': "#E3FFEE";
827
- readonly 'status-live': "#2ED573";
828
- readonly 'status-live-muted': "#22A444";
829
- readonly 'status-error': "#D14343";
830
- readonly 'status-error-light': "#E05254";
831
- readonly 'status-error-dark': "#A4221C";
832
- readonly 'status-error-subtle': "#FFF4F4";
833
- readonly 'status-error-vivid': "#FF4757";
834
- readonly 'status-error-vivid-light': "#FF6070";
835
- readonly 'status-error-vivid-dark': "#C42539";
836
- readonly 'status-error-vivid-subtle': "rgba(255, 71, 87, 0.12)";
837
- readonly 'status-warning': "#F9B415";
838
- readonly 'status-warning-light': "#FFD352";
839
- readonly 'status-warning-dark': "#C27400";
840
- readonly 'status-warning-subtle': "#FFF7DD";
841
- readonly 'status-info': "#2196F3";
842
- readonly 'status-info-light': "#78C2FF";
843
- readonly 'status-info-dark': "#1072CB";
844
- readonly 'status-info-subtle': "#EFF8FF";
845
- readonly 'on-status-success': "#FFFFFF";
846
- readonly 'on-status-error': "#FFFFFF";
847
- readonly 'on-status-warning': "#FFFFFF";
848
- readonly 'on-status-info': "#FFFFFF";
849
- readonly 'result-improve': "#4caf50";
850
- readonly 'result-improve-light': "rgba(76, 175, 80, 0.12)";
851
- readonly 'result-improve-dark': "#248a24";
852
- readonly 'result-degrade': "#ef5350";
853
- readonly 'result-degrade-light': "rgba(239, 83, 80, 0.12)";
854
- readonly 'result-degrade-dark': "#b30000";
855
- readonly 'result-inconclusive': "#9E9A97";
856
- readonly 'result-inconclusive-light': "rgba(158, 154, 151, 0.12)";
857
- readonly 'result-neutral': "#6B7280";
858
- readonly 'on-result-improve': "#FFFFFF";
859
- readonly 'on-result-degrade': "#FFFFFF";
860
- readonly 'on-result-inconclusive': "#FFFFFF";
861
- readonly 'data-1': "#1965B0";
862
- readonly 'data-2': "#4EB265";
863
- readonly 'data-3': "#F7F056";
864
- readonly 'data-4': "#DC050C";
865
- readonly 'data-5': "#882E72";
866
- readonly 'data-6': "#F4A736";
867
- readonly 'data-7': "#7BAFDE";
868
- readonly 'data-8': "#90C987";
869
- readonly 'data-9': "#CAACCB";
870
- readonly 'data-10': "#EE8026";
871
- readonly 'text-primary': "#121828";
872
- readonly 'text-secondary': "#65748B";
873
- readonly 'text-tertiary': "#9CA3AF";
874
- readonly 'text-disabled': "rgba(55, 65, 81, 0.48)";
875
- readonly 'text-inverse': "#FFFFFF";
876
- readonly 'text-link': "#5048E5";
877
- readonly 'text-link-hover': "#3832A0";
878
- readonly 'surface-base': "#FFFFFF";
879
- readonly 'surface-elevated': "#FAFAFA";
880
- readonly 'surface-raised': "#F3F4F6";
881
- readonly 'surface-overlay': "#FFFFFF";
882
- readonly 'surface-input': "#FAFAFA";
883
- readonly 'background-base': "#EBEBEB";
884
- readonly 'background-default': "#FFFFFF";
885
- readonly 'background-subtle': "#FAFAFA";
886
- readonly 'border-default': "#E8E9EB";
887
- readonly 'border-subtle': "#F3F4F6";
888
- readonly 'border-strong': "#D1D5DB";
889
- readonly 'border-prominent': "#9CA3AF";
890
- readonly 'border-focus': "#5048E5";
891
- readonly 'border-input': "#D1D5DB";
892
- readonly 'border-input-hover': "#9CA3AF";
893
- readonly 'border-input-focus': "#5048E5";
894
- readonly 'border-input-error': "#D14343";
895
- readonly 'interactive-hover': "rgba(55, 65, 81, 0.04)";
896
- readonly 'interactive-focus': "rgba(55, 65, 81, 0.12)";
897
- readonly 'interactive-active': "rgba(55, 65, 81, 0.16)";
898
- readonly 'interactive-selected': "rgba(55, 65, 81, 0.08)";
899
- readonly 'interactive-disabled': "rgba(55, 65, 81, 0.12)";
900
- readonly 'interactive-disabled-text': "rgba(55, 65, 81, 0.26)";
901
- readonly divider: "#E8E9EB";
902
- readonly 'avatar-background': "#6B7280";
903
- readonly 'avatar-text': "#FFFFFF";
904
- } | {
905
- readonly 'brand-primary': "#FF7900";
906
- readonly 'brand-primary-light': "#FFA063";
907
- readonly 'brand-primary-dark': "#DA5F00";
908
- readonly 'brand-primary-subtle': "rgba(255, 121, 0, 0.12)";
909
- readonly 'brand-primary-hover': "#FFA063";
910
- readonly 'brand-primary-active': "#FFC7A2";
911
- readonly 'brand-secondary': "#307B9B";
912
- readonly 'brand-secondary-light': "#2697B7";
913
- readonly 'brand-secondary-dark': "#2A617F";
914
- readonly 'brand-secondary-subtle': "rgba(48, 123, 155, 0.12)";
915
- readonly 'brand-secondary-hover': "#2697B7";
916
- readonly 'brand-secondary-active': "#01B5D1";
917
- readonly 'on-brand-primary': "#FFFFFF";
918
- readonly 'on-brand-secondary': "#FFFFFF";
919
- readonly 'status-success': "#2ED573";
920
- readonly 'status-success-light': "#58F69E";
921
- readonly 'status-success-dark': "#298732";
922
- readonly 'status-success-subtle': "rgba(46, 213, 115, 0.12)";
923
- readonly 'status-live': "#2ED573";
924
- readonly 'status-live-muted': "#22A444";
925
- readonly 'status-error': "#D14343";
926
- readonly 'status-error-light': "#E05254";
927
- readonly 'status-error-dark': "#A4221C";
928
- readonly 'status-error-subtle': "rgba(209, 67, 67, 0.12)";
929
- readonly 'status-error-vivid': "#FF4757";
930
- readonly 'status-error-vivid-light': "#FF6070";
931
- readonly 'status-error-vivid-dark': "#C42539";
932
- readonly 'status-error-vivid-subtle': "rgba(255, 71, 87, 0.12)";
933
- readonly 'status-warning': "#F9B415";
934
- readonly 'status-warning-light': "#FFD352";
935
- readonly 'status-warning-dark': "#C27400";
936
- readonly 'status-warning-subtle': "rgba(249, 180, 21, 0.12)";
937
- readonly 'status-info': "#2196F3";
938
- readonly 'status-info-light': "#78C2FF";
939
- readonly 'status-info-dark': "#1072CB";
940
- readonly 'status-info-subtle': "rgba(33, 150, 243, 0.12)";
941
- readonly 'on-status-success': "#FFFFFF";
942
- readonly 'on-status-error': "#FFFFFF";
943
- readonly 'on-status-warning': "#FFFFFF";
944
- readonly 'on-status-info': "#FFFFFF";
945
- readonly 'result-improve': "#4caf50";
946
- readonly 'result-improve-light': "rgba(76, 175, 80, 0.16)";
947
- readonly 'result-improve-dark': "#248a24";
948
- readonly 'result-degrade': "#ef5350";
949
- readonly 'result-degrade-light': "rgba(239, 83, 80, 0.16)";
950
- readonly 'result-degrade-dark': "#b30000";
951
- readonly 'result-inconclusive': "#9E9A97";
952
- readonly 'result-inconclusive-light': "rgba(158, 154, 151, 0.16)";
953
- readonly 'result-neutral': "#9CA3AF";
954
- readonly 'on-result-improve': "#FFFFFF";
955
- readonly 'on-result-degrade': "#FFFFFF";
956
- readonly 'on-result-inconclusive': "#FFFFFF";
957
- readonly 'data-1': "#1965B0";
958
- readonly 'data-2': "#4EB265";
959
- readonly 'data-3': "#F7F056";
960
- readonly 'data-4': "#DC050C";
961
- readonly 'data-5': "#882E72";
962
- readonly 'data-6': "#F4A736";
963
- readonly 'data-7': "#7BAFDE";
964
- readonly 'data-8': "#90C987";
965
- readonly 'data-9': "#CAACCB";
966
- readonly 'data-10': "#EE8026";
967
- readonly 'text-primary': "#F3F4F6";
968
- readonly 'text-secondary': "#9CA3AF";
969
- readonly 'text-tertiary': "#6B7280";
970
- readonly 'text-disabled': "rgba(255, 255, 255, 0.38)";
971
- readonly 'text-inverse': "#111827";
972
- readonly 'text-link': "#828DF8";
973
- readonly 'text-link-hover': "#60A5FA";
974
- readonly 'surface-base': "#161616";
975
- readonly 'surface-elevated': "#191919";
976
- readonly 'surface-raised': "#1C1C1C";
977
- readonly 'surface-overlay': "#191919";
978
- readonly 'surface-input': "#191919";
979
- readonly 'background-base': "#101010";
980
- readonly 'background-default': "#161616";
981
- readonly 'background-subtle': "#1C1C1C";
982
- readonly 'border-default': "#1F1F1F";
983
- readonly 'border-subtle': "#1C1C1C";
984
- readonly 'border-strong': "#2C2C2C";
985
- readonly 'border-prominent': "#3C3C3C";
986
- readonly 'border-focus': "#828DF8";
987
- readonly 'border-input': "#4B5563";
988
- readonly 'border-input-hover': "#6B7280";
989
- readonly 'border-input-focus': "#828DF8";
990
- readonly 'border-input-error': "#EF4444";
991
- readonly 'interactive-hover': "rgba(255, 255, 255, 0.04)";
992
- readonly 'interactive-focus': "rgba(255, 255, 255, 0.12)";
993
- readonly 'interactive-active': "rgba(255, 255, 255, 0.16)";
994
- readonly 'interactive-selected': "rgba(255, 255, 255, 0.08)";
995
- readonly 'interactive-disabled': "rgba(255, 255, 255, 0.12)";
996
- readonly 'interactive-disabled-text': "rgba(255, 255, 255, 0.26)";
997
- readonly divider: "#1F1F1F";
998
- readonly 'avatar-background': "#4B5563";
999
- readonly 'avatar-text': "#FFFFFF";
931
+ declare const primitiveSpacing: {
932
+ readonly 0: "0";
933
+ readonly px: "1px";
934
+ readonly 0.5: "0.125rem";
935
+ readonly 1: "0.25rem";
936
+ readonly 1.5: "0.375rem";
937
+ readonly 2: "0.5rem";
938
+ readonly 2.5: "0.625rem";
939
+ readonly 3: "0.75rem";
940
+ readonly 3.5: "0.875rem";
941
+ readonly 4: "1rem";
942
+ readonly 5: "1.25rem";
943
+ readonly 6: "1.5rem";
944
+ readonly 7: "1.75rem";
945
+ readonly 8: "2rem";
946
+ readonly 9: "2.25rem";
947
+ readonly 10: "2.5rem";
948
+ readonly 11: "2.75rem";
949
+ readonly 12: "3rem";
950
+ readonly 14: "3.5rem";
951
+ readonly 16: "4rem";
952
+ readonly 20: "5rem";
953
+ readonly 24: "6rem";
954
+ readonly 28: "7rem";
955
+ readonly 32: "8rem";
956
+ };
957
+ declare const primitiveBorderRadius: {
958
+ readonly none: "0";
959
+ readonly sm: "4px";
960
+ readonly DEFAULT: "8px";
961
+ readonly md: "8px";
962
+ readonly lg: "12px";
963
+ readonly xl: "16px";
964
+ readonly '2xl': "24px";
965
+ readonly full: "9999px";
966
+ };
967
+ declare const primitiveShadows: {
968
+ readonly none: "none";
969
+ readonly sm: "0px 1px 2px rgba(100, 116, 139, 0.12)";
970
+ readonly DEFAULT: "0px 1px 3px rgba(100, 116, 139, 0.12), 0px 1px 2px rgba(100, 116, 139, 0.24)";
971
+ readonly md: "0px 4px 6px rgba(100, 116, 139, 0.12)";
972
+ readonly lg: "0px 10px 15px rgba(100, 116, 139, 0.12)";
973
+ readonly xl: "0px 20px 25px rgba(100, 116, 139, 0.12)";
974
+ readonly '2xl': "0px 25px 50px rgba(100, 116, 139, 0.25)";
975
+ readonly inner: "inset 0 2px 4px 0 rgba(0, 0, 0, 0.06)";
976
+ };
977
+ declare const primitiveBreakpoints: {
978
+ readonly xs: 0;
979
+ readonly sm: 600;
980
+ readonly md: 1000;
981
+ readonly lg: 1200;
982
+ readonly xl: 1920;
983
+ };
984
+ declare const primitiveZIndex: {
985
+ readonly hide: -1;
986
+ readonly auto: "auto";
987
+ readonly base: 0;
988
+ readonly docked: 10;
989
+ readonly dropdown: 1000;
990
+ readonly sticky: 1100;
991
+ readonly drawer: 1100;
992
+ readonly banner: 1200;
993
+ readonly appBar: 1200;
994
+ readonly overlay: 1300;
995
+ readonly modal: 1400;
996
+ readonly popover: 1500;
997
+ readonly skipLink: 1600;
998
+ readonly toast: 1700;
999
+ readonly tooltip: 1800;
1000
1000
  };
1001
1001
 
1002
1002
  /**
@@ -1825,9 +1825,14 @@ declare const surfaceGradient: {
1825
1825
  chrome: (mode?: ThemeMode) => GradientStyle;
1826
1826
  };
1827
1827
 
1828
- type ThemeProviderMode = 'dark' | 'light';
1828
+ /** `'system'` follows nativewind's `useColorScheme()` (mobile light/dark flip). */
1829
+ type ThemeProviderMode = 'dark' | 'light' | 'system';
1829
1830
  interface ThemeProviderProps extends ViewProps {
1830
- /** Theme mode to register. Mobile is dark-only today; defaults to `dark`. */
1831
+ /**
1832
+ * Theme mode to register. `'system'` bridges nativewind's `useColorScheme()`
1833
+ * so mobile follows the OS light/dark flip; `'dark'`/`'light'` pin it. Mobile
1834
+ * is dark-only today, so this defaults to `dark`.
1835
+ */
1831
1836
  mode?: ThemeProviderMode;
1832
1837
  }
1833
1838
  /**