@idealyst/components 1.1.7 → 1.1.8

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.
Files changed (105) hide show
  1. package/package.json +3 -3
  2. package/src/Accordion/Accordion.native.tsx +8 -6
  3. package/src/Accordion/Accordion.styles.old.tsx +298 -0
  4. package/src/Accordion/Accordion.styles.tsx +102 -236
  5. package/src/ActivityIndicator/ActivityIndicator.styles.old.tsx +94 -0
  6. package/src/ActivityIndicator/ActivityIndicator.styles.tsx +44 -74
  7. package/src/Alert/Alert.native.tsx +16 -6
  8. package/src/Alert/Alert.styles.old.tsx +209 -0
  9. package/src/Alert/Alert.styles.tsx +67 -149
  10. package/src/Avatar/Avatar.styles.old.tsx +99 -0
  11. package/src/Avatar/Avatar.styles.tsx +35 -80
  12. package/src/Badge/Badge.styles.old.tsx +157 -0
  13. package/src/Badge/Badge.styles.tsx +61 -121
  14. package/src/Breadcrumb/Breadcrumb.styles.old.tsx +231 -0
  15. package/src/Breadcrumb/Breadcrumb.styles.tsx +83 -200
  16. package/src/Breadcrumb/Breadcrumb.web.tsx +28 -23
  17. package/src/Button/Button.styles.tsx +89 -141
  18. package/src/Card/Card.native.tsx +7 -11
  19. package/src/Card/Card.styles.old.tsx +160 -0
  20. package/src/Card/Card.styles.tsx +105 -142
  21. package/src/Card/Card.web.tsx +5 -4
  22. package/src/Checkbox/Checkbox.native.tsx +9 -5
  23. package/src/Checkbox/Checkbox.styles.old.tsx +271 -0
  24. package/src/Checkbox/Checkbox.styles.tsx +104 -216
  25. package/src/Checkbox/Checkbox.web.tsx +6 -6
  26. package/src/Chip/Chip.styles.old.tsx +184 -0
  27. package/src/Chip/Chip.styles.tsx +34 -72
  28. package/src/Dialog/Dialog.native.tsx +7 -4
  29. package/src/Dialog/Dialog.styles.old.tsx +202 -0
  30. package/src/Dialog/Dialog.styles.tsx +69 -133
  31. package/src/Divider/Divider.styles.old.tsx +172 -0
  32. package/src/Divider/Divider.styles.tsx +62 -84
  33. package/src/Icon/Icon.native.tsx +8 -8
  34. package/src/Icon/Icon.styles.old.tsx +81 -0
  35. package/src/Icon/Icon.styles.tsx +52 -66
  36. package/src/Icon/Icon.web.tsx +43 -7
  37. package/src/Icon/IconSvg/IconSvg.web.tsx +2 -0
  38. package/src/Image/Image.styles.old.tsx +69 -0
  39. package/src/Image/Image.styles.tsx +46 -60
  40. package/src/Input/Input.native.tsx +138 -53
  41. package/src/Input/Input.styles.old.tsx +289 -0
  42. package/src/Input/Input.styles.tsx +127 -198
  43. package/src/List/List.native.tsx +5 -2
  44. package/src/List/List.styles.old.tsx +242 -0
  45. package/src/List/List.styles.tsx +179 -215
  46. package/src/List/ListItem.native.tsx +12 -6
  47. package/src/List/ListItem.web.tsx +23 -13
  48. package/src/Menu/Menu.styles.old.tsx +197 -0
  49. package/src/Menu/Menu.styles.tsx +68 -150
  50. package/src/Menu/MenuItem.native.tsx +5 -3
  51. package/src/Menu/MenuItem.styles.old.tsx +114 -0
  52. package/src/Menu/MenuItem.styles.tsx +57 -89
  53. package/src/Menu/MenuItem.web.tsx +8 -3
  54. package/src/Popover/Popover.native.tsx +10 -4
  55. package/src/Popover/Popover.styles.old.tsx +135 -0
  56. package/src/Popover/Popover.styles.tsx +51 -112
  57. package/src/Pressable/Pressable.styles.old.tsx +27 -0
  58. package/src/Pressable/Pressable.styles.tsx +35 -27
  59. package/src/Progress/Progress.styles.old.tsx +200 -0
  60. package/src/Progress/Progress.styles.tsx +75 -164
  61. package/src/RadioButton/RadioButton.native.tsx +4 -3
  62. package/src/RadioButton/RadioButton.styles.old.tsx +175 -0
  63. package/src/RadioButton/RadioButton.styles.tsx +83 -154
  64. package/src/RadioButton/RadioButton.web.tsx +2 -2
  65. package/src/SVGImage/SVGImage.styles.old.tsx +86 -0
  66. package/src/SVGImage/SVGImage.styles.tsx +35 -78
  67. package/src/Screen/Screen.native.tsx +18 -25
  68. package/src/Screen/Screen.styles.old.tsx +87 -0
  69. package/src/Screen/Screen.styles.tsx +105 -67
  70. package/src/Screen/Screen.web.tsx +1 -1
  71. package/src/Select/Select.native.tsx +42 -33
  72. package/src/Select/Select.styles.old.tsx +353 -0
  73. package/src/Select/Select.styles.tsx +223 -292
  74. package/src/Skeleton/Skeleton.styles.old.tsx +67 -0
  75. package/src/Skeleton/Skeleton.styles.tsx +29 -53
  76. package/src/Slider/Slider.styles.old.tsx +259 -0
  77. package/src/Slider/Slider.styles.tsx +153 -234
  78. package/src/Switch/Switch.native.tsx +7 -5
  79. package/src/Switch/Switch.styles.old.tsx +203 -0
  80. package/src/Switch/Switch.styles.tsx +101 -174
  81. package/src/Switch/Switch.web.tsx +5 -5
  82. package/src/TabBar/TabBar.native.tsx +3 -2
  83. package/src/TabBar/TabBar.styles.old.tsx +343 -0
  84. package/src/TabBar/TabBar.styles.tsx +145 -279
  85. package/src/Table/Table.native.tsx +18 -9
  86. package/src/Table/Table.styles.old.tsx +311 -0
  87. package/src/Table/Table.styles.tsx +152 -286
  88. package/src/Text/Text.native.tsx +1 -3
  89. package/src/Text/Text.style.demo.tsx +16 -0
  90. package/src/Text/Text.styles.old.tsx +219 -0
  91. package/src/Text/Text.styles.tsx +94 -84
  92. package/src/Text/Text.web.tsx +2 -2
  93. package/src/Text/index.ts +1 -0
  94. package/src/TextArea/TextArea.styles.old.tsx +213 -0
  95. package/src/TextArea/TextArea.styles.tsx +93 -181
  96. package/src/Tooltip/Tooltip.styles.old.tsx +82 -0
  97. package/src/Tooltip/Tooltip.styles.tsx +32 -56
  98. package/src/Video/Video.styles.old.tsx +51 -0
  99. package/src/Video/Video.styles.tsx +32 -44
  100. package/src/View/View.native.tsx +12 -14
  101. package/src/View/View.styles.old.tsx +125 -0
  102. package/src/View/View.styles.tsx +76 -106
  103. package/src/View/View.web.tsx +1 -0
  104. package/src/examples/CardExamples.tsx +0 -6
  105. package/src/extensions/extendComponent.ts +61 -0
@@ -1,157 +1,162 @@
1
+ /**
2
+ * Select styles using defineStyle with dynamic props.
3
+ */
1
4
  import { StyleSheet } from 'react-native-unistyles';
2
- import { Theme, StylesheetStyles, Intent, Size } from '@idealyst/theme';
3
- import { buildSizeVariants } from '../utils/buildSizeVariants';
4
- import {
5
- buildMarginVariants,
6
- buildMarginVerticalVariants,
7
- buildMarginHorizontalVariants,
8
- } from '../utils/buildViewStyleVariants';
9
- import { SelectIntentVariant } from './types';
10
- import { applyExtensions } from '../extensions/applyExtension';
5
+ import { defineStyle, ThemeStyleWrapper } from '@idealyst/theme';
6
+ import type { Theme as BaseTheme, Intent, Size } from '@idealyst/theme';
7
+ import { ViewStyleSize } from '../utils/viewStyleProps';
11
8
 
12
- // Type definitions
13
- type SelectSize = Size;
14
- type SelectType = 'outlined' | 'filled';
9
+ // Required: Unistyles must see StyleSheet usage in original source to process this file
10
+ void StyleSheet;
15
11
 
16
- type SelectTriggerVariants = {
17
- type: SelectType;
18
- size: SelectSize;
19
- intent: SelectIntentVariant;
20
- disabled: boolean;
21
- error: boolean;
22
- focused: boolean;
23
- }
12
+ // Wrap theme for $iterator support
13
+ type Theme = ThemeStyleWrapper<BaseTheme>;
24
14
 
15
+ type SelectType = 'outlined' | 'filled';
25
16
 
26
- export type ExpandedSelectTriggerStyles = StylesheetStyles<keyof SelectTriggerVariants>;
27
- export type ExpandedSelectStyles = StylesheetStyles<never>;
17
+ export type SelectDynamicProps = {
18
+ size?: Size;
19
+ intent?: Intent;
20
+ type?: SelectType;
21
+ disabled?: boolean;
22
+ error?: boolean;
23
+ focused?: boolean;
24
+ margin?: ViewStyleSize;
25
+ marginVertical?: ViewStyleSize;
26
+ marginHorizontal?: ViewStyleSize;
27
+ };
28
28
 
29
- function createTriggerTypeVariants(theme: Theme) {
30
- return {
31
- outlined: {
32
- backgroundColor: theme.colors.surface.primary,
33
- borderColor: theme.colors.border.primary,
34
- _web: {
35
- border: `1px solid ${theme.colors.border.primary}`,
29
+ /**
30
+ * Select styles with type/intent/error/focused handling.
31
+ */
32
+ export const selectStyles = defineStyle('Select', (theme: Theme) => ({
33
+ container: (_props: SelectDynamicProps) => ({
34
+ position: 'relative' as const,
35
+ variants: {
36
+ margin: {
37
+ margin: theme.sizes.$view.padding,
36
38
  },
37
- },
38
- filled: {
39
- backgroundColor: theme.colors.surface.secondary,
40
- borderColor: 'transparent',
41
- _web: {
42
- border: '1px solid transparent',
39
+ marginVertical: {
40
+ marginVertical: theme.sizes.$view.padding,
41
+ },
42
+ marginHorizontal: {
43
+ marginHorizontal: theme.sizes.$view.padding,
43
44
  },
44
45
  },
45
- } as const;
46
- }
46
+ }),
47
47
 
48
- function createTriggerSizeVariants(theme: Theme) {
49
- return buildSizeVariants(theme, 'select', (size) => ({
50
- paddingHorizontal: size.paddingHorizontal,
51
- minHeight: size.minHeight,
52
- }));
53
- }
48
+ label: (_props: SelectDynamicProps) => ({
49
+ fontSize: 14,
50
+ fontWeight: '500' as const,
51
+ color: theme.colors.text.primary,
52
+ marginBottom: 4,
53
+ }),
54
54
 
55
- function createIntentVariants(theme: Theme, type: SelectType, intent: SelectIntentVariant) {
56
- if (intent === 'neutral') {
57
- return {};
58
- }
55
+ trigger: ({ type = 'outlined', intent = 'neutral', disabled = false, error = false, focused = false }: SelectDynamicProps) => {
56
+ const intentValue = theme.intents[intent];
57
+ const primaryIntent = theme.intents.primary;
58
+ const errorColor = theme.intents.error.primary;
59
59
 
60
- const intentValue = (theme.intents as any)[intent];
60
+ // Background based on type
61
+ const backgroundColor = type === 'filled'
62
+ ? theme.colors.surface.secondary
63
+ : theme.colors.surface.primary;
61
64
 
62
- if (type === 'outlined') {
63
- return {
64
- borderColor: intentValue.primary,
65
- _web: {
66
- border: `1px solid ${intentValue.primary}`,
67
- },
68
- } as const;
69
- }
70
-
71
- return {} as const;
72
- }
73
-
74
- function buildDynamicTriggerStyles(theme: Theme) {
75
- return ({ type, intent }: Partial<SelectTriggerVariants>) => {
76
- const intentStyles = createIntentVariants(theme, type, intent);
65
+ // Border color based on state
66
+ let borderColor = type === 'filled' ? 'transparent' : theme.colors.border.primary;
67
+ if (error) {
68
+ borderColor = errorColor;
69
+ } else if (focused) {
70
+ borderColor = primaryIntent.primary;
71
+ } else if (intent !== 'neutral') {
72
+ borderColor = intentValue.primary;
73
+ }
77
74
 
78
75
  return {
79
- position: 'relative',
80
- flexDirection: 'row',
81
- alignItems: 'center',
82
- justifyContent: 'space-between',
76
+ position: 'relative' as const,
77
+ flexDirection: 'row' as const,
78
+ alignItems: 'center' as const,
79
+ justifyContent: 'space-between' as const,
83
80
  borderRadius: 8,
84
81
  borderWidth: 1,
85
- borderStyle: 'solid',
86
- ...intentStyles,
82
+ borderStyle: 'solid' as const,
83
+ backgroundColor,
84
+ borderColor,
85
+ opacity: disabled ? 0.6 : 1,
87
86
  variants: {
88
- type: createTriggerTypeVariants(theme),
89
- size: createTriggerSizeVariants(theme),
90
- disabled: {
91
- true: {
92
- opacity: 0.6,
93
- _web: {
94
- cursor: 'not-allowed',
95
- },
96
- },
97
- false: {
98
- _web: {
99
- cursor: 'pointer',
100
- _hover: {
101
- opacity: 0.9,
102
- },
103
- _active: {
104
- opacity: 0.8,
105
- },
106
- },
107
- },
108
- },
109
- error: {
110
- true: {
111
- borderColor: theme.intents.error.primary,
112
- _web: {
113
- border: `1px solid ${theme.intents.error.primary}`,
114
- },
115
- },
116
- false: {},
117
- },
118
- focused: {
119
- true: {
120
- borderColor: theme.intents.primary.primary,
121
- _web: {
122
- border: `1px solid ${theme.intents.primary.primary}`,
123
- boxShadow: `0 0 0 2px ${theme.intents.primary.primary}20`,
124
- outline: 'none',
125
- },
126
- },
127
- false: {},
87
+ size: {
88
+ paddingHorizontal: theme.sizes.$select.paddingHorizontal,
89
+ minHeight: theme.sizes.$select.minHeight,
128
90
  },
129
91
  },
130
92
  _web: {
131
93
  display: 'flex',
132
94
  boxSizing: 'border-box',
133
- _focus: {
134
- outline: 'none',
135
- },
95
+ cursor: disabled ? 'not-allowed' : 'pointer',
96
+ border: `1px solid ${borderColor}`,
97
+ boxShadow: focused ? `0 0 0 2px ${primaryIntent.primary}20` : 'none',
98
+ transition: 'border-color 0.2s ease, box-shadow 0.2s ease',
99
+ _hover: disabled ? {} : { opacity: 0.9 },
100
+ _active: disabled ? {} : { opacity: 0.8 },
101
+ _focus: { outline: 'none' },
136
102
  },
137
103
  } as const;
138
- }
139
- }
104
+ },
140
105
 
141
- // Main element style creators (wrapped for extension support)
142
- function createContainerStyles(theme: Theme) {
143
- return () => ({
144
- position: 'relative' as const,
106
+ triggerContent: (_props: SelectDynamicProps) => ({
107
+ flex: 1,
108
+ flexDirection: 'row' as const,
109
+ alignItems: 'center' as const,
110
+ }),
111
+
112
+ triggerText: (_props: SelectDynamicProps) => ({
113
+ color: theme.colors.text.primary,
114
+ flex: 1,
115
+ variants: {
116
+ size: {
117
+ fontSize: theme.sizes.$select.fontSize,
118
+ },
119
+ },
120
+ }),
121
+
122
+ placeholder: (_props: SelectDynamicProps) => ({
123
+ color: theme.colors.text.secondary,
124
+ variants: {
125
+ size: {
126
+ fontSize: theme.sizes.$select.fontSize,
127
+ },
128
+ },
129
+ }),
130
+
131
+ icon: (_props: SelectDynamicProps) => ({
132
+ marginLeft: 4,
133
+ color: theme.colors.text.secondary,
134
+ }),
135
+
136
+ chevron: (_props: SelectDynamicProps) => ({
137
+ display: 'flex' as const,
138
+ alignItems: 'center' as const,
139
+ justifyContent: 'center' as const,
140
+ marginLeft: 4,
141
+ color: theme.colors.text.secondary,
145
142
  variants: {
146
- margin: buildMarginVariants(theme),
147
- marginVertical: buildMarginVerticalVariants(theme),
148
- marginHorizontal: buildMarginHorizontalVariants(theme),
143
+ size: {
144
+ width: theme.sizes.$select.iconSize,
145
+ height: theme.sizes.$select.iconSize,
146
+ },
147
+ },
148
+ _web: {
149
+ transition: 'transform 0.2s ease',
150
+ },
151
+ }),
152
+
153
+ chevronOpen: (_props: SelectDynamicProps) => ({
154
+ _web: {
155
+ transform: 'rotate(180deg)',
149
156
  },
150
- });
151
- }
157
+ }),
152
158
 
153
- function createDropdownStyles(theme: Theme) {
154
- return () => ({
159
+ dropdown: (_props: SelectDynamicProps) => ({
155
160
  position: 'absolute' as const,
156
161
  top: '100%',
157
162
  left: 0,
@@ -175,185 +180,111 @@ function createDropdownStyles(theme: Theme) {
175
180
  boxShadow: '0 8px 24px rgba(0, 0, 0, 0.1), 0 4px 8px rgba(0, 0, 0, 0.06)',
176
181
  overflowY: 'auto',
177
182
  },
178
- });
179
- }
183
+ }),
180
184
 
181
- function createOptionStyles(theme: Theme) {
182
- return () => ({
183
- paddingHorizontal: 8,
184
- paddingVertical: 4,
185
- flexDirection: 'row' as const,
186
- alignItems: 'center' as const,
187
- minHeight: 36,
185
+ searchContainer: (_props: SelectDynamicProps) => ({
186
+ padding: 8,
187
+ borderBottomWidth: 1,
188
+ borderBottomColor: theme.colors.border.primary,
188
189
  _web: {
189
- display: 'flex',
190
- cursor: 'pointer',
191
- _hover: {
192
- backgroundColor: theme.colors.surface.secondary,
193
- },
194
- _active: {
195
- opacity: 0.8,
196
- },
190
+ borderBottom: `1px solid ${theme.colors.border.primary}`,
197
191
  },
198
- });
199
- }
200
-
201
- // Styles are inlined here instead of in @idealyst/theme because Unistyles' Babel
202
- // transform on native cannot resolve function calls to extract variant structures.
203
- export const selectStyles = StyleSheet.create((theme: Theme) => {
204
- // Apply extensions to main visual elements
205
- const extendedStyles = applyExtensions('Select', theme, {
206
- container: createContainerStyles(theme),
207
- trigger: buildDynamicTriggerStyles(theme),
208
- dropdown: createDropdownStyles(theme),
209
- option: createOptionStyles(theme),
210
- });
192
+ }),
211
193
 
212
- return {
213
- // Extended main elements
214
- ...extendedStyles,
215
- // Minor utility styles (not extended)
216
- label: {
217
- fontSize: 14,
218
- fontWeight: '500',
219
- color: theme.colors.text.primary,
220
- marginBottom: 4,
221
- },
222
- triggerContent: {
223
- flex: 1,
224
- flexDirection: 'row',
225
- alignItems: 'center',
226
- },
227
- triggerText: {
228
- color: theme.colors.text.primary,
229
- flex: 1,
230
- variants: {
231
- size: buildSizeVariants(theme, 'select', (size: any) => ({
232
- fontSize: size.fontSize,
233
- })),
194
+ searchInput: (_props: SelectDynamicProps) => ({
195
+ padding: 4,
196
+ borderRadius: 4,
197
+ borderWidth: 1,
198
+ borderStyle: 'solid' as const,
199
+ borderColor: theme.colors.border.primary,
200
+ backgroundColor: theme.colors.surface.primary,
201
+ variants: {
202
+ size: {
203
+ fontSize: theme.sizes.$select.fontSize,
234
204
  },
235
205
  },
236
- placeholder: {
237
- color: theme.colors.text.secondary,
238
- variants: {
239
- size: buildSizeVariants(theme, 'select', (size: any) => ({
240
- fontSize: size.fontSize,
241
- })),
206
+ _web: {
207
+ border: `1px solid ${theme.colors.border.primary}`,
208
+ outline: 'none',
209
+ _focus: {
210
+ borderColor: theme.intents.primary.primary,
242
211
  },
243
212
  },
244
- icon: {
245
- marginLeft: 4,
246
- color: theme.colors.text.secondary,
247
- },
248
- chevron: {
213
+ }),
214
+
215
+ optionsList: (_props: SelectDynamicProps) => ({
216
+ paddingVertical: 4,
217
+ }),
218
+
219
+ option: ({ disabled = false }: SelectDynamicProps) => ({
220
+ paddingHorizontal: 8,
221
+ paddingVertical: 4,
222
+ flexDirection: 'row' as const,
223
+ alignItems: 'center' as const,
224
+ minHeight: 36,
225
+ opacity: disabled ? theme.interaction.opacity.disabled : 1,
226
+ _web: {
249
227
  display: 'flex',
250
- alignItems: 'center',
251
- justifyContent: 'center',
252
- marginLeft: 4,
253
- color: theme.colors.text.secondary,
254
- variants: {
255
- size: buildSizeVariants(theme, 'select', (size: any) => ({
256
- width: size.iconSize,
257
- height: size.iconSize,
258
- })),
259
- },
260
- _web: {
261
- transition: 'transform 0.2s ease',
262
- },
263
- },
264
- chevronOpen: {
265
- _web: {
266
- transform: 'rotate(180deg)',
267
- }
268
- },
269
- searchContainer: {
270
- padding: 8,
271
- borderBottomWidth: 1,
272
- borderBottomStyle: 'solid',
273
- borderBottomColor: theme.colors.border.primary,
274
- _web: {
275
- borderBottom: `1px solid ${theme.colors.border.primary}`,
276
- },
277
- },
278
- searchInput: {
279
- padding: 4,
280
- borderRadius: 4,
281
- borderWidth: 1,
282
- borderStyle: 'solid',
283
- borderColor: theme.colors.border.primary,
284
- backgroundColor: theme.colors.surface.primary,
285
- variants: {
286
- size: buildSizeVariants(theme, 'select', (size: any) => ({
287
- fontSize: size.fontSize,
288
- })),
289
- },
290
- _web: {
291
- border: `1px solid ${theme.colors.border.primary}`,
292
- outline: 'none',
293
- _focus: {
294
- borderColor: theme.intents.primary.primary,
295
- },
296
- },
297
- },
298
- optionsList: {
299
- paddingVertical: 4,
300
- },
301
- optionFocused: {
302
- backgroundColor: theme.interaction.focusedBackground,
303
- _web: {
304
- outline: `1px solid ${theme.interaction.focusBorder}`,
305
- outlineOffset: -1,
306
- },
228
+ cursor: disabled ? 'not-allowed' : 'pointer',
229
+ _hover: disabled ? {} : { backgroundColor: theme.colors.surface.secondary },
230
+ _active: disabled ? {} : { opacity: 0.8 },
307
231
  },
308
- optionDisabled: {
309
- opacity: theme.interaction.opacity.disabled,
310
- _web: {
311
- cursor: 'not-allowed',
312
- },
313
- },
314
- optionContent: {
315
- flexDirection: 'row',
316
- alignItems: 'center',
317
- flex: 1,
318
- },
319
- optionIcon: {
320
- marginRight: 4,
321
- },
322
- optionText: {
323
- color: theme.colors.text.primary,
324
- flex: 1,
325
- variants: {
326
- size: buildSizeVariants(theme, 'select', (size: any) => ({
327
- fontSize: size.fontSize,
328
- })),
329
- },
232
+ }),
233
+
234
+ optionFocused: (_props: SelectDynamicProps) => ({
235
+ backgroundColor: theme.interaction.focusedBackground,
236
+ _web: {
237
+ outline: `1px solid ${theme.interaction.focusBorder}`,
238
+ outlineOffset: -1,
330
239
  },
331
- optionTextDisabled: {
332
- color: theme.colors.text.secondary,
240
+ }),
241
+
242
+ optionDisabled: (_props: SelectDynamicProps) => ({
243
+ opacity: theme.interaction.opacity.disabled,
244
+ _web: {
245
+ cursor: 'not-allowed',
333
246
  },
334
- helperText: {
335
- fontSize: 12,
336
- marginTop: 4,
337
- color: theme.colors.text.secondary,
338
- variants: {
339
- error: {
340
- true: {
341
- color: theme.intents.error.primary,
342
- },
343
- false: {},
344
- },
247
+ }),
248
+
249
+ optionContent: (_props: SelectDynamicProps) => ({
250
+ flexDirection: 'row' as const,
251
+ alignItems: 'center' as const,
252
+ flex: 1,
253
+ }),
254
+
255
+ optionIcon: (_props: SelectDynamicProps) => ({
256
+ marginRight: 4,
257
+ }),
258
+
259
+ optionText: (_props: SelectDynamicProps) => ({
260
+ color: theme.colors.text.primary,
261
+ flex: 1,
262
+ variants: {
263
+ size: {
264
+ fontSize: theme.sizes.$select.fontSize,
345
265
  },
346
266
  },
347
- overlay: {
348
- position: 'absolute',
349
- top: 0,
350
- left: 0,
351
- right: 0,
352
- bottom: 0,
353
- zIndex: 999,
354
- _web: {
355
- position: 'fixed',
356
- },
267
+ }),
268
+
269
+ optionTextDisabled: (_props: SelectDynamicProps) => ({
270
+ color: theme.colors.text.secondary,
271
+ }),
272
+
273
+ helperText: ({ error = false }: SelectDynamicProps) => ({
274
+ fontSize: 12,
275
+ marginTop: 4,
276
+ color: error ? theme.intents.error.primary : theme.colors.text.secondary,
277
+ }),
278
+
279
+ overlay: (_props: SelectDynamicProps) => ({
280
+ position: 'absolute' as const,
281
+ top: 0,
282
+ left: 0,
283
+ right: 0,
284
+ bottom: 0,
285
+ zIndex: 999,
286
+ _web: {
287
+ position: 'fixed',
357
288
  },
358
- } as const;
359
- });
289
+ }),
290
+ }));
@@ -0,0 +1,67 @@
1
+ import { StyleSheet } from 'react-native-unistyles';
2
+ import { Theme, StylesheetStyles } from '@idealyst/theme';
3
+ import { applyExtensions } from '../extensions/applyExtension';
4
+
5
+ type SkeletonShape = 'rectangle' | 'rounded' | 'circle';
6
+ type SkeletonAnimation = 'pulse' | 'wave' | 'none';
7
+
8
+ type SkeletonVariants = {
9
+ shape: SkeletonShape;
10
+ animation: SkeletonAnimation;
11
+ }
12
+
13
+ export type ExpandedSkeletonStyles = StylesheetStyles<keyof SkeletonVariants>;
14
+ export type ExpandedSkeletonGroupStyles = StylesheetStyles<never>;
15
+
16
+ export type SkeletonStylesheet = {
17
+ skeleton: ExpandedSkeletonStyles;
18
+ group: ExpandedSkeletonGroupStyles;
19
+ }
20
+
21
+ /**
22
+ * Create shape variants for skeleton
23
+ */
24
+ function createShapeVariants(theme: Theme) {
25
+ return {
26
+ rectangle: {
27
+ borderRadius: 0,
28
+ },
29
+ rounded: {
30
+ borderRadius: 8,
31
+ },
32
+ circle: {
33
+ borderRadius: 9999,
34
+ },
35
+ } as const;
36
+ }
37
+
38
+ // Style creators for extension support
39
+ function createSkeletonStyles(theme: Theme) {
40
+ return () => ({
41
+ backgroundColor: theme.colors.surface.tertiary,
42
+ overflow: 'hidden' as const,
43
+ variants: {
44
+ shape: createShapeVariants(theme),
45
+ animation: {
46
+ pulse: {},
47
+ wave: {},
48
+ none: {},
49
+ },
50
+ },
51
+ });
52
+ }
53
+
54
+ // Styles are inlined here instead of in @idealyst/theme because Unistyles' Babel
55
+ // transform on native cannot resolve function calls to extract variant structures.
56
+ // @ts-ignore - TS language server needs restart to pick up theme structure changes
57
+ export const skeletonStyles = StyleSheet.create((theme: Theme) => {
58
+ // Apply extensions to main visual elements
59
+
60
+ return applyExtensions('Skeleton', theme, {skeleton: createSkeletonStyles(theme),
61
+ // Additional styles (merged from return)
62
+ // Minor utility styles (not extended)
63
+ group: {
64
+ display: 'flex',
65
+ flexDirection: 'column',
66
+ }});
67
+ });