@cdx-ui/components 0.0.1-beta.4 → 0.0.1-beta.40

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 (283) hide show
  1. package/README.md +18 -11
  2. package/lib/commonjs/components/Avatar/index.js +1 -1
  3. package/lib/commonjs/components/Avatar/styles.js +36 -29
  4. package/lib/commonjs/components/Avatar/styles.js.map +1 -1
  5. package/lib/commonjs/components/Button/styles.js +2 -2
  6. package/lib/commonjs/components/Button/styles.js.map +1 -1
  7. package/lib/commonjs/components/CLAUDE.md +90 -0
  8. package/lib/commonjs/components/Card/index.js +22 -4
  9. package/lib/commonjs/components/Card/index.js.map +1 -1
  10. package/lib/commonjs/components/Card/styles.js +27 -5
  11. package/lib/commonjs/components/Card/styles.js.map +1 -1
  12. package/lib/commonjs/components/Checkbox/index.js +5 -29
  13. package/lib/commonjs/components/Checkbox/index.js.map +1 -1
  14. package/lib/commonjs/components/Checkbox/styles.js +39 -47
  15. package/lib/commonjs/components/Checkbox/styles.js.map +1 -1
  16. package/lib/commonjs/components/Chip/index.js +78 -9
  17. package/lib/commonjs/components/Chip/index.js.map +1 -1
  18. package/lib/commonjs/components/Chip/styles.js +207 -21
  19. package/lib/commonjs/components/Chip/styles.js.map +1 -1
  20. package/lib/commonjs/components/Field/index.js +8 -2
  21. package/lib/commonjs/components/Field/index.js.map +1 -1
  22. package/lib/commonjs/components/Field/styles.js +4 -4
  23. package/lib/commonjs/components/Field/styles.js.map +1 -1
  24. package/lib/commonjs/components/Heading/styles.js +1 -1
  25. package/lib/commonjs/components/Heading/styles.js.map +1 -1
  26. package/lib/commonjs/components/Icon/index.js +1 -2
  27. package/lib/commonjs/components/Icon/index.js.map +1 -1
  28. package/lib/commonjs/components/IconButton/index.js +6 -1
  29. package/lib/commonjs/components/IconButton/index.js.map +1 -1
  30. package/lib/commonjs/components/IconButton/styles.js +135 -10
  31. package/lib/commonjs/components/IconButton/styles.js.map +1 -1
  32. package/lib/commonjs/components/Input/styles.js +7 -6
  33. package/lib/commonjs/components/Input/styles.js.map +1 -1
  34. package/lib/commonjs/components/ListItem/index.js +283 -0
  35. package/lib/commonjs/components/ListItem/index.js.map +1 -0
  36. package/lib/commonjs/components/ListItem/styles.js +130 -0
  37. package/lib/commonjs/components/ListItem/styles.js.map +1 -0
  38. package/lib/commonjs/components/ProgressSegmented/index.js +22 -10
  39. package/lib/commonjs/components/ProgressSegmented/index.js.map +1 -1
  40. package/lib/commonjs/components/Radio/index.js +167 -0
  41. package/lib/commonjs/components/Radio/index.js.map +1 -0
  42. package/lib/commonjs/components/Radio/styles.js +31 -0
  43. package/lib/commonjs/components/Radio/styles.js.map +1 -0
  44. package/lib/commonjs/components/Text/styles.js +2 -2
  45. package/lib/commonjs/components/Text/styles.js.map +1 -1
  46. package/lib/commonjs/components/Tile/index.js +251 -0
  47. package/lib/commonjs/components/Tile/index.js.map +1 -0
  48. package/lib/commonjs/components/Tile/styles.js +52 -0
  49. package/lib/commonjs/components/Tile/styles.js.map +1 -0
  50. package/lib/commonjs/components/index.js +36 -0
  51. package/lib/commonjs/components/index.js.map +1 -1
  52. package/lib/commonjs/figma/Avatar.figma.js +54 -0
  53. package/lib/commonjs/figma/Avatar.figma.js.map +1 -0
  54. package/lib/commonjs/figma/Button.figma.js +28 -11
  55. package/lib/commonjs/figma/Button.figma.js.map +1 -1
  56. package/lib/commonjs/figma/CLAUDE.md +30 -0
  57. package/lib/commonjs/figma/Card.Header.figma.js +28 -0
  58. package/lib/commonjs/figma/Card.Header.figma.js.map +1 -0
  59. package/lib/commonjs/figma/Card.figma.js +42 -0
  60. package/lib/commonjs/figma/Card.figma.js.map +1 -0
  61. package/lib/commonjs/figma/Checkbox.figma.js +55 -0
  62. package/lib/commonjs/figma/Checkbox.figma.js.map +1 -0
  63. package/lib/commonjs/figma/Chip.figma.js +68 -0
  64. package/lib/commonjs/figma/Chip.figma.js.map +1 -0
  65. package/lib/commonjs/figma/Field.Input.figma.js +57 -0
  66. package/lib/commonjs/figma/Field.Input.figma.js.map +1 -0
  67. package/lib/commonjs/figma/Field.Select.figma.js +57 -0
  68. package/lib/commonjs/figma/Field.Select.figma.js.map +1 -0
  69. package/lib/commonjs/figma/Heading.figma.js +30 -0
  70. package/lib/commonjs/figma/Heading.figma.js.map +1 -0
  71. package/lib/commonjs/figma/Icon.figma.js +20 -0
  72. package/lib/commonjs/figma/Icon.figma.js.map +1 -0
  73. package/lib/commonjs/figma/IconButton.figma.js +47 -0
  74. package/lib/commonjs/figma/IconButton.figma.js.map +1 -0
  75. package/lib/commonjs/figma/Input.figma.js +52 -0
  76. package/lib/commonjs/figma/Input.figma.js.map +1 -0
  77. package/lib/commonjs/figma/ProgressSegmented.figma.js +39 -0
  78. package/lib/commonjs/figma/ProgressSegmented.figma.js.map +1 -0
  79. package/lib/commonjs/figma/Radio.figma.js +38 -0
  80. package/lib/commonjs/figma/Radio.figma.js.map +1 -0
  81. package/lib/commonjs/figma/Select.figma.js +53 -0
  82. package/lib/commonjs/figma/Select.figma.js.map +1 -0
  83. package/lib/commonjs/figma/Text.figma.js +29 -0
  84. package/lib/commonjs/figma/Text.figma.js.map +1 -0
  85. package/lib/commonjs/figma/icons.figma.batch.js +27 -0
  86. package/lib/commonjs/figma/icons.figma.batch.js.map +1 -0
  87. package/lib/commonjs/figma/icons.figma.batch.json +17705 -0
  88. package/lib/commonjs/styles/primitives.js +42 -5
  89. package/lib/commonjs/styles/primitives.js.map +1 -1
  90. package/lib/module/components/Avatar/index.js +1 -1
  91. package/lib/module/components/Avatar/styles.js +36 -29
  92. package/lib/module/components/Avatar/styles.js.map +1 -1
  93. package/lib/module/components/Button/styles.js +2 -2
  94. package/lib/module/components/Button/styles.js.map +1 -1
  95. package/lib/module/components/CLAUDE.md +90 -0
  96. package/lib/module/components/Card/index.js +23 -4
  97. package/lib/module/components/Card/index.js.map +1 -1
  98. package/lib/module/components/Card/styles.js +27 -5
  99. package/lib/module/components/Card/styles.js.map +1 -1
  100. package/lib/module/components/Checkbox/index.js +6 -30
  101. package/lib/module/components/Checkbox/index.js.map +1 -1
  102. package/lib/module/components/Checkbox/styles.js +40 -48
  103. package/lib/module/components/Checkbox/styles.js.map +1 -1
  104. package/lib/module/components/Chip/index.js +82 -13
  105. package/lib/module/components/Chip/index.js.map +1 -1
  106. package/lib/module/components/Chip/styles.js +206 -20
  107. package/lib/module/components/Chip/styles.js.map +1 -1
  108. package/lib/module/components/Field/index.js +9 -3
  109. package/lib/module/components/Field/index.js.map +1 -1
  110. package/lib/module/components/Field/styles.js +4 -4
  111. package/lib/module/components/Field/styles.js.map +1 -1
  112. package/lib/module/components/Heading/styles.js +1 -1
  113. package/lib/module/components/Heading/styles.js.map +1 -1
  114. package/lib/module/components/Icon/index.js +1 -2
  115. package/lib/module/components/Icon/index.js.map +1 -1
  116. package/lib/module/components/IconButton/index.js +6 -1
  117. package/lib/module/components/IconButton/index.js.map +1 -1
  118. package/lib/module/components/IconButton/styles.js +135 -10
  119. package/lib/module/components/IconButton/styles.js.map +1 -1
  120. package/lib/module/components/Input/styles.js +7 -6
  121. package/lib/module/components/Input/styles.js.map +1 -1
  122. package/lib/module/components/ListItem/index.js +226 -0
  123. package/lib/module/components/ListItem/index.js.map +1 -0
  124. package/lib/module/components/ListItem/styles.js +127 -0
  125. package/lib/module/components/ListItem/styles.js.map +1 -0
  126. package/lib/module/components/ProgressSegmented/index.js +23 -11
  127. package/lib/module/components/ProgressSegmented/index.js.map +1 -1
  128. package/lib/module/components/Radio/index.js +164 -0
  129. package/lib/module/components/Radio/index.js.map +1 -0
  130. package/lib/module/components/Radio/styles.js +27 -0
  131. package/lib/module/components/Radio/styles.js.map +1 -0
  132. package/lib/module/components/Text/styles.js +2 -2
  133. package/lib/module/components/Text/styles.js.map +1 -1
  134. package/lib/module/components/Tile/index.js +243 -0
  135. package/lib/module/components/Tile/index.js.map +1 -0
  136. package/lib/module/components/Tile/styles.js +48 -0
  137. package/lib/module/components/Tile/styles.js.map +1 -0
  138. package/lib/module/components/index.js +3 -0
  139. package/lib/module/components/index.js.map +1 -1
  140. package/lib/module/figma/Avatar.figma.js +48 -0
  141. package/lib/module/figma/Avatar.figma.js.map +1 -0
  142. package/lib/module/figma/Button.figma.js +28 -11
  143. package/lib/module/figma/Button.figma.js.map +1 -1
  144. package/lib/module/figma/CLAUDE.md +30 -0
  145. package/lib/module/figma/Card.Header.figma.js +22 -0
  146. package/lib/module/figma/Card.Header.figma.js.map +1 -0
  147. package/lib/module/figma/Card.figma.js +36 -0
  148. package/lib/module/figma/Card.figma.js.map +1 -0
  149. package/lib/module/figma/Checkbox.figma.js +49 -0
  150. package/lib/module/figma/Checkbox.figma.js.map +1 -0
  151. package/lib/module/figma/Chip.figma.js +62 -0
  152. package/lib/module/figma/Chip.figma.js.map +1 -0
  153. package/lib/module/figma/Field.Input.figma.js +51 -0
  154. package/lib/module/figma/Field.Input.figma.js.map +1 -0
  155. package/lib/module/figma/Field.Select.figma.js +51 -0
  156. package/lib/module/figma/Field.Select.figma.js.map +1 -0
  157. package/lib/module/figma/Heading.figma.js +24 -0
  158. package/lib/module/figma/Heading.figma.js.map +1 -0
  159. package/lib/module/figma/Icon.figma.js +14 -0
  160. package/lib/module/figma/Icon.figma.js.map +1 -0
  161. package/lib/module/figma/IconButton.figma.js +41 -0
  162. package/lib/module/figma/IconButton.figma.js.map +1 -0
  163. package/lib/module/figma/Input.figma.js +46 -0
  164. package/lib/module/figma/Input.figma.js.map +1 -0
  165. package/lib/module/figma/ProgressSegmented.figma.js +33 -0
  166. package/lib/module/figma/ProgressSegmented.figma.js.map +1 -0
  167. package/lib/module/figma/Radio.figma.js +32 -0
  168. package/lib/module/figma/Radio.figma.js.map +1 -0
  169. package/lib/module/figma/Select.figma.js +47 -0
  170. package/lib/module/figma/Select.figma.js.map +1 -0
  171. package/lib/module/figma/Text.figma.js +23 -0
  172. package/lib/module/figma/Text.figma.js.map +1 -0
  173. package/lib/module/figma/icons.figma.batch.js +22 -0
  174. package/lib/module/figma/icons.figma.batch.js.map +1 -0
  175. package/lib/module/figma/icons.figma.batch.json +17705 -0
  176. package/lib/module/styles/primitives.js +42 -5
  177. package/lib/module/styles/primitives.js.map +1 -1
  178. package/lib/typescript/components/Avatar/styles.d.ts +4 -4
  179. package/lib/typescript/components/Avatar/styles.d.ts.map +1 -1
  180. package/lib/typescript/components/Card/index.d.ts +4 -3
  181. package/lib/typescript/components/Card/index.d.ts.map +1 -1
  182. package/lib/typescript/components/Card/styles.d.ts +13 -3
  183. package/lib/typescript/components/Card/styles.d.ts.map +1 -1
  184. package/lib/typescript/components/Checkbox/index.d.ts +1 -2
  185. package/lib/typescript/components/Checkbox/index.d.ts.map +1 -1
  186. package/lib/typescript/components/Checkbox/styles.d.ts +4 -14
  187. package/lib/typescript/components/Checkbox/styles.d.ts.map +1 -1
  188. package/lib/typescript/components/Chip/index.d.ts +19 -6
  189. package/lib/typescript/components/Chip/index.d.ts.map +1 -1
  190. package/lib/typescript/components/Chip/styles.d.ts +13 -4
  191. package/lib/typescript/components/Chip/styles.d.ts.map +1 -1
  192. package/lib/typescript/components/Field/FieldLabel.web.d.ts +2 -2
  193. package/lib/typescript/components/Field/FieldLabel.web.d.ts.map +1 -1
  194. package/lib/typescript/components/Field/index.d.ts.map +1 -1
  195. package/lib/typescript/components/Field/styles.d.ts.map +1 -1
  196. package/lib/typescript/components/Heading/styles.d.ts +1 -1
  197. package/lib/typescript/components/Icon/index.d.ts.map +1 -1
  198. package/lib/typescript/components/IconButton/index.d.ts.map +1 -1
  199. package/lib/typescript/components/IconButton/styles.d.ts +6 -2
  200. package/lib/typescript/components/IconButton/styles.d.ts.map +1 -1
  201. package/lib/typescript/components/Input/styles.d.ts.map +1 -1
  202. package/lib/typescript/components/ListItem/index.d.ts +49 -0
  203. package/lib/typescript/components/ListItem/index.d.ts.map +1 -0
  204. package/lib/typescript/components/ListItem/styles.d.ts +30 -0
  205. package/lib/typescript/components/ListItem/styles.d.ts.map +1 -0
  206. package/lib/typescript/components/ProgressSegmented/index.d.ts +14 -3
  207. package/lib/typescript/components/ProgressSegmented/index.d.ts.map +1 -1
  208. package/lib/typescript/components/Radio/index.d.ts +40 -0
  209. package/lib/typescript/components/Radio/index.d.ts.map +1 -0
  210. package/lib/typescript/components/Radio/styles.d.ts +8 -0
  211. package/lib/typescript/components/Radio/styles.d.ts.map +1 -0
  212. package/lib/typescript/components/Stack/styles.d.ts +2 -2
  213. package/lib/typescript/components/Text/styles.d.ts +1 -1
  214. package/lib/typescript/components/Tile/index.d.ts +70 -0
  215. package/lib/typescript/components/Tile/index.d.ts.map +1 -0
  216. package/lib/typescript/components/Tile/styles.d.ts +18 -0
  217. package/lib/typescript/components/Tile/styles.d.ts.map +1 -0
  218. package/lib/typescript/components/index.d.ts +3 -0
  219. package/lib/typescript/components/index.d.ts.map +1 -1
  220. package/lib/typescript/figma/Avatar.figma.d.ts +8 -0
  221. package/lib/typescript/figma/Avatar.figma.d.ts.map +1 -0
  222. package/lib/typescript/figma/Button.figma.d.ts.map +1 -1
  223. package/lib/typescript/figma/Card.Header.figma.d.ts +8 -0
  224. package/lib/typescript/figma/Card.Header.figma.d.ts.map +1 -0
  225. package/lib/typescript/figma/Card.figma.d.ts +8 -0
  226. package/lib/typescript/figma/Card.figma.d.ts.map +1 -0
  227. package/lib/typescript/figma/Checkbox.figma.d.ts +8 -0
  228. package/lib/typescript/figma/Checkbox.figma.d.ts.map +1 -0
  229. package/lib/typescript/figma/Chip.figma.d.ts +8 -0
  230. package/lib/typescript/figma/Chip.figma.d.ts.map +1 -0
  231. package/lib/typescript/figma/Field.Input.figma.d.ts +8 -0
  232. package/lib/typescript/figma/Field.Input.figma.d.ts.map +1 -0
  233. package/lib/typescript/figma/Field.Select.figma.d.ts +8 -0
  234. package/lib/typescript/figma/Field.Select.figma.d.ts.map +1 -0
  235. package/lib/typescript/figma/Heading.figma.d.ts +8 -0
  236. package/lib/typescript/figma/Heading.figma.d.ts.map +1 -0
  237. package/lib/typescript/figma/Icon.figma.d.ts +8 -0
  238. package/lib/typescript/figma/Icon.figma.d.ts.map +1 -0
  239. package/lib/typescript/figma/IconButton.figma.d.ts +8 -0
  240. package/lib/typescript/figma/IconButton.figma.d.ts.map +1 -0
  241. package/lib/typescript/figma/Input.figma.d.ts +8 -0
  242. package/lib/typescript/figma/Input.figma.d.ts.map +1 -0
  243. package/lib/typescript/figma/ProgressSegmented.figma.d.ts +8 -0
  244. package/lib/typescript/figma/ProgressSegmented.figma.d.ts.map +1 -0
  245. package/lib/typescript/figma/Radio.figma.d.ts +8 -0
  246. package/lib/typescript/figma/Radio.figma.d.ts.map +1 -0
  247. package/lib/typescript/figma/Select.figma.d.ts +8 -0
  248. package/lib/typescript/figma/Select.figma.d.ts.map +1 -0
  249. package/lib/typescript/figma/Text.figma.d.ts +8 -0
  250. package/lib/typescript/figma/Text.figma.d.ts.map +1 -0
  251. package/lib/typescript/figma/icons.figma.batch.d.ts +14 -0
  252. package/lib/typescript/figma/icons.figma.batch.d.ts.map +1 -0
  253. package/lib/typescript/styles/primitives.d.ts +38 -0
  254. package/lib/typescript/styles/primitives.d.ts.map +1 -1
  255. package/package.json +4 -4
  256. package/src/components/Avatar/index.tsx +1 -1
  257. package/src/components/Avatar/styles.ts +49 -34
  258. package/src/components/Button/styles.ts +2 -2
  259. package/src/components/CLAUDE.md +90 -0
  260. package/src/components/Card/index.tsx +41 -16
  261. package/src/components/Card/styles.ts +43 -23
  262. package/src/components/Checkbox/index.tsx +8 -19
  263. package/src/components/Checkbox/styles.ts +82 -86
  264. package/src/components/Chip/index.tsx +104 -27
  265. package/src/components/Chip/styles.ts +232 -18
  266. package/src/components/Field/FieldLabel.web.tsx +1 -1
  267. package/src/components/Field/index.tsx +10 -3
  268. package/src/components/Field/styles.ts +5 -4
  269. package/src/components/Heading/styles.ts +1 -1
  270. package/src/components/Icon/index.tsx +1 -2
  271. package/src/components/IconButton/index.tsx +3 -2
  272. package/src/components/IconButton/styles.ts +136 -10
  273. package/src/components/Input/styles.ts +14 -9
  274. package/src/components/ListItem/index.tsx +285 -0
  275. package/src/components/ListItem/styles.ts +153 -0
  276. package/src/components/ProgressSegmented/index.tsx +49 -14
  277. package/src/components/Radio/index.tsx +192 -0
  278. package/src/components/Radio/styles.ts +59 -0
  279. package/src/components/Text/styles.ts +2 -2
  280. package/src/components/Tile/index.tsx +296 -0
  281. package/src/components/Tile/styles.ts +82 -0
  282. package/src/components/index.ts +3 -0
  283. package/src/styles/primitives.ts +42 -5
@@ -8,7 +8,7 @@ import {
8
8
  IFieldLabelProps,
9
9
  type IFieldRootProps,
10
10
  } from '@cdx-ui/primitives';
11
- import { cn } from '@cdx-ui/utils';
11
+ import { cn, useFormControlContext } from '@cdx-ui/utils';
12
12
  import { Icon } from '../Icon';
13
13
  import { BaseFieldLabel } from './FieldLabel';
14
14
  import {
@@ -70,7 +70,14 @@ export interface FieldLabelProps extends IFieldLabelProps, FieldLabelVariantProp
70
70
 
71
71
  const FieldLabel = forwardRef<View, FieldLabelProps>(
72
72
  ({ className, children, style, htmlFor, ...props }, ref) => {
73
- const labelClassName = cn(fieldLabelVariants(), className);
73
+ const { isLabelFocused, isInvalid } = useFormControlContext();
74
+ // Native: inject text-content-action via context (group-has CSS handles web).
75
+ // native: prefix keeps this class inert on web so it never conflicts with text-content-primary.
76
+ const labelClassName = cn(
77
+ fieldLabelVariants(),
78
+ isLabelFocused && !isInvalid && 'native:text-content-action',
79
+ className,
80
+ );
74
81
 
75
82
  return (
76
83
  <FieldPrimitive.Label
@@ -79,7 +86,7 @@ const FieldLabel = forwardRef<View, FieldLabelProps>(
79
86
  style={style}
80
87
  htmlFor={htmlFor}
81
88
  requiredIndicator={
82
- <Text className="text-red-500" aria-hidden>
89
+ <Text className="text-content-danger" aria-hidden>
83
90
  {' *'}
84
91
  </Text>
85
92
  }
@@ -1,23 +1,24 @@
1
1
  import { cva, type VariantProps } from 'class-variance-authority';
2
2
  import { DISABLED_OPACITY } from '../../styles/primitives';
3
3
 
4
- export const fieldRootVariants = cva(['flex-col gap-2', 'web:last:mb-0', DISABLED_OPACITY]);
4
+ export const fieldRootVariants = cva(['group flex-col gap-2', 'web:last:mb-0', DISABLED_OPACITY]);
5
5
 
6
6
  export const fieldLabelVariants = cva([
7
7
  'body-md',
8
8
  'font-medium',
9
9
  'text-content-primary',
10
10
  'flex-row items-center',
11
- DISABLED_OPACITY,
11
+ 'overflow-hidden',
12
12
  'web:cursor-pointer',
13
+ 'web:group-has-[[data-focus=true]]:data-[invalid=false]:text-content-action',
13
14
  'data-[invalid=true]:text-content-danger',
14
15
  ]);
15
16
 
16
- export const fieldHelperVariants = cva(['flex-row items-center']);
17
+ export const fieldHelperVariants = cva(['flex-row items-center min-h-4']);
17
18
 
18
19
  export const fieldHelperTextVariants = cva(['body-sm', 'text-content-tertiary']);
19
20
 
20
- export const fieldErrorVariants = cva(['flex-row items-center gap-1']);
21
+ export const fieldErrorVariants = cva(['flex-row items-center gap-0.5 min-h-4']);
21
22
 
22
23
  export const fieldErrorTextVariants = cva(['body-sm', 'text-content-danger']);
23
24
 
@@ -5,7 +5,7 @@ export const headingStyle = cva(
5
5
  [
6
6
  `text-content-primary my-0`,
7
7
  Platform.select({
8
- web: 'bg-transparent display-inline no-underline',
8
+ web: 'bg-transparent no-underline',
9
9
  default: '',
10
10
  }),
11
11
  ],
@@ -1,7 +1,6 @@
1
1
  import { withUniwind } from 'uniwind';
2
2
  import { cn } from '@cdx-ui/utils';
3
3
  import type { CdxIcon, CdxIconProps } from '@cdx-ui/icons';
4
- import { COLOR_TEXT_PRIMARY } from '../../styles/primitives';
5
4
 
6
5
  export type IconProps = CdxIconProps & {
7
6
  className?: string; // TODO: Why does this need to specified manually?
@@ -47,7 +46,7 @@ export function Icon({ as: IconComponent, className, ...props }: IconProps) {
47
46
  return (
48
47
  <StyledIcon
49
48
  as={IconComponent}
50
- className={cn(COLOR_TEXT_PRIMARY, 'size-5', className)}
49
+ className={cn('text-content-primary size-5', className)}
51
50
  {...props}
52
51
  />
53
52
  );
@@ -53,6 +53,7 @@ const IconButtonRoot = forwardRef<View, IconButtonProps>(
53
53
  (
54
54
  {
55
55
  variant = 'solid',
56
+ color = 'neutral',
56
57
  size = 'default',
57
58
  className,
58
59
  style,
@@ -63,11 +64,11 @@ const IconButtonRoot = forwardRef<View, IconButtonProps>(
63
64
  },
64
65
  ref,
65
66
  ) => {
66
- const rootClassName = cn(iconButtonRootVariants({ variant, size }), className);
67
+ const rootClassName = cn(iconButtonRootVariants({ variant, color, size }), className);
67
68
 
68
69
  const glyphClassName = cn(
69
70
  iconButtonGlyphVariants({ size }),
70
- iconButtonIconColorVariants(),
71
+ iconButtonIconColorVariants({ variant, color }),
71
72
  iconClassName,
72
73
  );
73
74
 
@@ -8,35 +8,133 @@ export const iconButtonRootVariants = cva(
8
8
  'rounded-[var(--border-radius-round)]',
9
9
  'web:outline-none web:focus:outline-none web:focus-visible:outline-none',
10
10
  TRANSITION_COLORS,
11
- 'data-[disabled=true]:opacity-[--opacity-disabled]',
11
+ 'data-[disabled=true]:opacity-[var(--opacity-disabled)]',
12
12
  DISABLED_CURSOR,
13
- 'web:data-[focus-visible=true]:ring-2 web:data-[focus-visible=true]:ring-[--color-stroke-ring] web:data-[focus-visible=true]:ring-offset-2',
13
+ 'web:data-[focus-visible=true]:ring-2 web:data-[focus-visible=true]:ring-[var(--color-stroke-ring)] web:data-[focus-visible=true]:ring-offset-2',
14
14
  ],
15
15
  {
16
16
  variants: {
17
17
  variant: {
18
- solid: [
18
+ solid: [],
19
+ tint: [],
20
+ ghost: ['bg-transparent'],
21
+ },
22
+ color: {
23
+ neutral: [],
24
+ action: [],
25
+ danger: [],
26
+ },
27
+ size: {
28
+ default: 'h-11 w-11 min-w-11 shrink-0 p-2.5',
29
+ small: 'h-8 w-8 min-w-8 shrink-0 p-1.5',
30
+ },
31
+ },
32
+ compoundVariants: [
33
+ // ── solid × color ───────────────────────────────────────────────────
34
+ {
35
+ variant: 'solid',
36
+ color: 'neutral',
37
+ className: [
19
38
  'bg-surface-primary border border-stroke-secondary',
20
39
  Platform.select({
21
40
  default: 'data-[active=true]:bg-surface-primary-active',
22
41
  web: 'data-[hover=true]:bg-surface-primary-hover data-[active=true]:data-[hover=true]:bg-surface-secondary-active',
23
42
  }),
24
43
  ],
25
- ghost: [
26
- 'bg-transparent',
44
+ },
45
+ {
46
+ variant: 'solid',
47
+ color: 'action',
48
+ className: [
49
+ 'bg-surface-action-strong',
50
+ Platform.select({
51
+ default: 'data-[active=true]:bg-surface-action-strong-active',
52
+ web: 'data-[hover=true]:bg-surface-action-strong-hover data-[active=true]:data-[hover=true]:bg-surface-action-strong-active',
53
+ }),
54
+ ],
55
+ },
56
+ {
57
+ variant: 'solid',
58
+ color: 'danger',
59
+ className: [
60
+ 'bg-surface-danger-strong',
61
+ Platform.select({
62
+ default: 'data-[active=true]:bg-surface-danger-strong-active',
63
+ web: 'data-[hover=true]:bg-surface-danger-strong-hover data-[active=true]:data-[hover=true]:bg-surface-danger-strong-active',
64
+ }),
65
+ ],
66
+ },
67
+
68
+ // ── tint × color ─────────────────────────────────────────────────
69
+ {
70
+ variant: 'tint',
71
+ color: 'neutral',
72
+ className: [
73
+ 'bg-surface-neutral-tint',
74
+ Platform.select({
75
+ default: 'data-[active=true]:bg-surface-neutral-tint-active',
76
+ web: 'data-[hover=true]:bg-surface-neutral-tint-hover data-[active=true]:data-[hover=true]:bg-surface-neutral-tint-active',
77
+ }),
78
+ ],
79
+ },
80
+ {
81
+ variant: 'tint',
82
+ color: 'action',
83
+ className: [
84
+ 'bg-surface-action-tint',
85
+ Platform.select({
86
+ default: 'data-[active=true]:bg-surface-action-tint-active',
87
+ web: 'data-[hover=true]:bg-surface-action-tint-hover data-[active=true]:data-[hover=true]:bg-surface-action-tint-active',
88
+ }),
89
+ ],
90
+ },
91
+ {
92
+ variant: 'tint',
93
+ color: 'danger',
94
+ className: [
95
+ 'bg-surface-danger-tint',
96
+ Platform.select({
97
+ default: 'data-[active=true]:bg-surface-danger-tint-active',
98
+ web: 'data-[hover=true]:bg-surface-danger-tint-hover data-[active=true]:data-[hover=true]:bg-surface-danger-tint-active',
99
+ }),
100
+ ],
101
+ },
102
+
103
+ // ── ghost × color ──────────────────────────────────────────────────
104
+ {
105
+ variant: 'ghost',
106
+ color: 'neutral',
107
+ className: [
27
108
  Platform.select({
28
109
  default: 'data-[active=true]:bg-surface-primary-active',
29
110
  web: 'data-[hover=true]:bg-surface-primary-hover data-[active=true]:data-[hover=true]:bg-surface-secondary-active',
30
111
  }),
31
112
  ],
32
113
  },
33
- size: {
34
- default: 'h-11 w-11 min-w-11 shrink-0 p-2.5',
35
- small: 'h-8 w-8 min-w-8 shrink-0 p-1.5',
114
+ {
115
+ variant: 'ghost',
116
+ color: 'action',
117
+ className: [
118
+ Platform.select({
119
+ default: 'data-[active=true]:bg-surface-action-tint-active',
120
+ web: 'data-[hover=true]:bg-surface-action-tint-hover data-[active=true]:data-[hover=true]:bg-surface-action-tint-active',
121
+ }),
122
+ ],
36
123
  },
37
- },
124
+ {
125
+ variant: 'ghost',
126
+ color: 'danger',
127
+ className: [
128
+ Platform.select({
129
+ default: 'data-[active=true]:bg-surface-danger-tint-active',
130
+ web: 'data-[hover=true]:bg-surface-danger-tint-hover data-[active=true]:data-[hover=true]:bg-surface-danger-tint-active',
131
+ }),
132
+ ],
133
+ },
134
+ ],
38
135
  defaultVariants: {
39
136
  variant: 'solid',
137
+ color: 'neutral',
40
138
  size: 'default',
41
139
  },
42
140
  },
@@ -54,6 +152,34 @@ export const iconButtonGlyphVariants = cva([], {
54
152
  },
55
153
  });
56
154
 
57
- export const iconButtonIconColorVariants = cva(['text-content-primary']);
155
+ export const iconButtonIconColorVariants = cva([], {
156
+ variants: {
157
+ variant: {
158
+ solid: [],
159
+ tint: [],
160
+ ghost: [],
161
+ },
162
+ color: {
163
+ neutral: [],
164
+ action: [],
165
+ danger: [],
166
+ },
167
+ },
168
+ compoundVariants: [
169
+ { variant: 'solid', color: 'neutral', className: 'text-content-primary' },
170
+ { variant: 'solid', color: 'action', className: 'text-content-action-on-strong' },
171
+ { variant: 'solid', color: 'danger', className: 'text-content-danger-on-strong' },
172
+ { variant: 'tint', color: 'neutral', className: 'text-content-primary' },
173
+ { variant: 'tint', color: 'action', className: 'text-content-action-on-subtle' },
174
+ { variant: 'tint', color: 'danger', className: 'text-content-danger-on-subtle' },
175
+ { variant: 'ghost', color: 'neutral', className: 'text-content-primary' },
176
+ { variant: 'ghost', color: 'action', className: 'text-content-action' },
177
+ { variant: 'ghost', color: 'danger', className: 'text-content-danger' },
178
+ ],
179
+ defaultVariants: {
180
+ variant: 'solid',
181
+ color: 'neutral',
182
+ },
183
+ });
58
184
 
59
185
  export type IconButtonVariantProps = VariantProps<typeof iconButtonRootVariants>;
@@ -3,13 +3,13 @@ import { DISABLED_CURSOR, TRANSITION_COLORS } from '../../styles/primitives';
3
3
 
4
4
  export const inputRootVariants = cva(
5
5
  [
6
- 'w-full flex-row items-stretch overflow-hidden',
6
+ 'w-full flex-row items-center overflow-hidden',
7
7
  'bg-surface-primary',
8
- 'border-solid border-[length:var(--border-width-default)] border-stroke-primary',
8
+ 'border-solid border-2 border-stroke-primary',
9
9
  'rounded-[var(--border-radius-default)]',
10
10
  TRANSITION_COLORS,
11
11
  'data-[disabled=true]:bg-surface-secondary',
12
- 'data-[disabled=true]:opacity-[--opacity-disabled]',
12
+ 'data-[disabled=true]:opacity-[var(--opacity-disabled)]',
13
13
  DISABLED_CURSOR,
14
14
  'data-[readonly=true]:cursor-default',
15
15
  'data-[readonly=true]:bg-surface-secondary',
@@ -24,11 +24,16 @@ export const inputRootVariants = cva(
24
24
  outline: [],
25
25
  },
26
26
  size: {
27
- // TODO: Find a cleaner approach to preventing layout shift when focus border is applied.
28
- default: ['h-10 px-4 py-2 gap-2', 'data-[focus=true]:px-[15px] data-[focus=true]:py-[7px]'],
27
+ default: [
28
+ 'h-11 min-h-11 px-4 py-3 gap-4',
29
+ // Subtract one hairline from padding when focused so the wider focus border doesn’t shift layout.
30
+ 'data-[focus=true]:px-[calc(var(--spacing-4)-var(--spacing-px))]',
31
+ 'data-[focus=true]:py-[calc(var(--spacing-3)-var(--spacing-px))]',
32
+ ],
29
33
  small: [
30
- 'h-8 px-3 py-1.5 gap-1.5',
31
- 'data-[focus=true]:px-[11px] data-[focus=true]:py-[5px]',
34
+ 'h-8 min-h-8 px-3 py-2 gap-1.5',
35
+ 'data-[focus=true]:px-[calc(var(--spacing-3)-var(--spacing-px))]',
36
+ 'data-[focus=true]:py-[calc(var(--spacing-2)-var(--spacing-px))]',
32
37
  ],
33
38
  },
34
39
  },
@@ -42,7 +47,7 @@ export const inputRootVariants = cva(
42
47
  export const inputFieldVariants = cva(
43
48
  [
44
49
  'flex-1 justify-center bg-transparent p-0',
45
- 'font-body text-content-primary',
50
+ 'text-content-primary',
46
51
  'placeholder:text-content-tertiary',
47
52
  'web:outline-none',
48
53
  'tracking-normal',
@@ -60,7 +65,7 @@ export const inputFieldVariants = cva(
60
65
  },
61
66
  );
62
67
 
63
- export const inputSlotVariants = cva(['items-center justify-center self-center']);
68
+ export const inputSlotVariants = cva(['items-center justify-center self-center shrink-0']);
64
69
 
65
70
  export const inputIconVariants = cva(['text-content-tertiary'], {
66
71
  variants: {
@@ -0,0 +1,285 @@
1
+ import { forwardRef, type ReactNode } from 'react';
2
+ import { Pressable, Text, View, type TextProps, type ViewProps } from 'react-native';
3
+ import {
4
+ createListItem,
5
+ type IListItemLeadingSlotProps,
6
+ type IListItemProps,
7
+ type IListItemSectionHeaderProps,
8
+ type ListItemCrossAlign,
9
+ } from '@cdx-ui/primitives';
10
+ import { cn, useStyleContext, withStyleContext, type WithStyleContextProps } from '@cdx-ui/utils';
11
+ import {
12
+ listItemContentVariants,
13
+ listItemDescriptionVariants,
14
+ listItemLeadingSlotVariants,
15
+ listItemMetaVariants,
16
+ listItemRootVariants,
17
+ listItemSectionHeaderLabelVariants,
18
+ listItemSectionHeaderVariants,
19
+ listItemTitleVariants,
20
+ listItemTrailingSlotVariants,
21
+ type ListItemVariantProps,
22
+ } from './styles';
23
+
24
+ const SCOPE = 'LIST_ITEM';
25
+
26
+ const RootView = withStyleContext(View, SCOPE);
27
+ const RootPressable = withStyleContext(Pressable, SCOPE);
28
+
29
+ const ListItemPrimitive = createListItem({
30
+ View: RootView,
31
+ Pressable: RootPressable,
32
+ LeadingSlot: View,
33
+ Content: View,
34
+ Title: Text,
35
+ Description: Text,
36
+ Meta: Text,
37
+ TrailingSlot: View,
38
+ SectionHeader: View,
39
+ });
40
+
41
+ const useListItemStyleContext = (): Pick<ListItemVariantProps, 'size' | 'crossAlign'> => {
42
+ const ctx = useStyleContext(SCOPE) as ListItemVariantProps | undefined;
43
+ return { size: ctx?.size ?? 'default', crossAlign: ctx?.crossAlign ?? 'center' };
44
+ };
45
+
46
+ // =============================================================================
47
+ // ROOT
48
+ // =============================================================================
49
+
50
+ export interface ListItemProps extends IListItemProps, WithStyleContextProps {
51
+ className?: string;
52
+ }
53
+
54
+ const ListItemRoot = forwardRef<View, ListItemProps>(
55
+ (
56
+ {
57
+ size = 'default',
58
+ surface = 'default',
59
+ showSeparator = true,
60
+ crossAlign = 'center',
61
+ className,
62
+ style,
63
+ ...props
64
+ },
65
+ ref,
66
+ ) => {
67
+ const computedClassName = cn(
68
+ listItemRootVariants({ size, surface, showSeparator, crossAlign }),
69
+ className,
70
+ );
71
+
72
+ return (
73
+ <ListItemPrimitive
74
+ ref={ref as never}
75
+ className={computedClassName}
76
+ context={{ size, surface, showSeparator, crossAlign }}
77
+ crossAlign={crossAlign}
78
+ showSeparator={showSeparator}
79
+ size={size}
80
+ style={style}
81
+ surface={surface}
82
+ {...props}
83
+ />
84
+ );
85
+ },
86
+ );
87
+
88
+ ListItemRoot.displayName = 'ListItem';
89
+
90
+ // =============================================================================
91
+ // SLOTS & TEXT
92
+ // =============================================================================
93
+
94
+ export interface ListItemLeadingSlotProps extends IListItemLeadingSlotProps {
95
+ className?: string;
96
+ }
97
+
98
+ const ListItemLeadingSlot = forwardRef<View, ListItemLeadingSlotProps>(
99
+ ({ className, style, ...props }, ref) => (
100
+ <ListItemPrimitive.LeadingSlot
101
+ ref={ref as never}
102
+ className={cn(listItemLeadingSlotVariants(), className)}
103
+ style={style}
104
+ {...props}
105
+ />
106
+ ),
107
+ );
108
+
109
+ ListItemLeadingSlot.displayName = 'ListItem.LeadingSlot';
110
+
111
+ export interface ListItemContentProps extends ViewProps {
112
+ className?: string;
113
+ }
114
+
115
+ const ListItemContent = forwardRef<View, ListItemContentProps>(
116
+ ({ className, style, ...props }, ref) => {
117
+ const { crossAlign } = useListItemStyleContext();
118
+
119
+ return (
120
+ <ListItemPrimitive.Content
121
+ ref={ref as never}
122
+ className={cn(listItemContentVariants({ crossAlign }), className)}
123
+ style={style}
124
+ {...props}
125
+ />
126
+ );
127
+ },
128
+ );
129
+
130
+ ListItemContent.displayName = 'ListItem.Content';
131
+
132
+ export interface ListItemTitleProps extends TextProps {
133
+ className?: string;
134
+ }
135
+
136
+ const ListItemTitle = forwardRef<Text, ListItemTitleProps>(
137
+ ({ className, numberOfLines = 1, style, ...props }, ref) => {
138
+ const { size } = useListItemStyleContext();
139
+
140
+ return (
141
+ <ListItemPrimitive.Title
142
+ ref={ref as never}
143
+ className={cn(listItemTitleVariants({ size }), className)}
144
+ numberOfLines={numberOfLines}
145
+ style={style}
146
+ {...props}
147
+ />
148
+ );
149
+ },
150
+ );
151
+
152
+ ListItemTitle.displayName = 'ListItem.Title';
153
+
154
+ export interface ListItemDescriptionProps extends TextProps {
155
+ className?: string;
156
+ }
157
+
158
+ const ListItemDescription = forwardRef<Text, ListItemDescriptionProps>(
159
+ ({ className, style, ...props }, ref) => {
160
+ const { size } = useListItemStyleContext();
161
+
162
+ return (
163
+ <ListItemPrimitive.Description
164
+ ref={ref as never}
165
+ className={cn(listItemDescriptionVariants({ size }), className)}
166
+ style={style}
167
+ {...props}
168
+ />
169
+ );
170
+ },
171
+ );
172
+
173
+ ListItemDescription.displayName = 'ListItem.Description';
174
+
175
+ export interface ListItemMetaProps extends TextProps {
176
+ className?: string;
177
+ }
178
+
179
+ const ListItemMeta = forwardRef<Text, ListItemMetaProps>(
180
+ ({ className, numberOfLines = 1, style, ...props }, ref) => {
181
+ const { size } = useListItemStyleContext();
182
+
183
+ return (
184
+ <ListItemPrimitive.Meta
185
+ ref={ref as never}
186
+ className={cn(listItemMetaVariants({ size }), className)}
187
+ numberOfLines={numberOfLines}
188
+ style={style}
189
+ {...props}
190
+ />
191
+ );
192
+ },
193
+ );
194
+
195
+ ListItemMeta.displayName = 'ListItem.Meta';
196
+
197
+ export interface ListItemTrailingSlotProps extends ViewProps {
198
+ className?: string;
199
+ }
200
+
201
+ const ListItemTrailingSlot = forwardRef<View, ListItemTrailingSlotProps>(
202
+ ({ className, style, ...props }, ref) => {
203
+ const { crossAlign } = useListItemStyleContext();
204
+
205
+ return (
206
+ <ListItemPrimitive.TrailingSlot
207
+ ref={ref as never}
208
+ className={cn(listItemTrailingSlotVariants({ crossAlign }), className)}
209
+ style={style}
210
+ {...props}
211
+ />
212
+ );
213
+ },
214
+ );
215
+
216
+ ListItemTrailingSlot.displayName = 'ListItem.TrailingSlot';
217
+
218
+ const wrapSectionHeaderLabel = (children: ReactNode): ReactNode => {
219
+ if (typeof children === 'string' || typeof children === 'number') {
220
+ return <Text className={cn(listItemSectionHeaderLabelVariants())}>{children}</Text>;
221
+ }
222
+ return children;
223
+ };
224
+
225
+ // =============================================================================
226
+ // SECTION HEADER
227
+ // =============================================================================
228
+
229
+ export interface ListItemSectionHeaderComponentProps extends IListItemSectionHeaderProps {
230
+ className?: string;
231
+ }
232
+
233
+ const ListItemSectionHeader = forwardRef<View, ListItemSectionHeaderComponentProps>(
234
+ ({ children, className, showDivider = true, style, trailing, ...props }, ref) => (
235
+ <ListItemPrimitive.SectionHeader
236
+ ref={ref as never}
237
+ className={cn(listItemSectionHeaderVariants({ showDivider }), className)}
238
+ showDivider={showDivider}
239
+ style={style}
240
+ trailing={trailing}
241
+ {...props}
242
+ >
243
+ {wrapSectionHeaderLabel(children)}
244
+ </ListItemPrimitive.SectionHeader>
245
+ ),
246
+ );
247
+
248
+ ListItemSectionHeader.displayName = 'ListItem.SectionHeader';
249
+
250
+ // =============================================================================
251
+ // COMPOUND EXPORT
252
+ // =============================================================================
253
+
254
+ type ListItemCompound = typeof ListItemRoot & {
255
+ LeadingSlot: typeof ListItemLeadingSlot;
256
+ Content: typeof ListItemContent;
257
+ Title: typeof ListItemTitle;
258
+ Description: typeof ListItemDescription;
259
+ Meta: typeof ListItemMeta;
260
+ TrailingSlot: typeof ListItemTrailingSlot;
261
+ SectionHeader: typeof ListItemSectionHeader;
262
+ };
263
+
264
+ export const ListItem = Object.assign(ListItemRoot, {
265
+ LeadingSlot: ListItemLeadingSlot,
266
+ Content: ListItemContent,
267
+ Title: ListItemTitle,
268
+ Description: ListItemDescription,
269
+ Meta: ListItemMeta,
270
+ TrailingSlot: ListItemTrailingSlot,
271
+ SectionHeader: ListItemSectionHeader,
272
+ }) as ListItemCompound;
273
+
274
+ export type { ListItemCrossAlign, ListItemVariantProps };
275
+ export {
276
+ listItemContentVariants,
277
+ listItemDescriptionVariants,
278
+ listItemLeadingSlotVariants,
279
+ listItemMetaVariants,
280
+ listItemRootVariants,
281
+ listItemSectionHeaderLabelVariants,
282
+ listItemSectionHeaderVariants,
283
+ listItemTitleVariants,
284
+ listItemTrailingSlotVariants,
285
+ } from './styles';