@byyuurin/ui 0.0.10 → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (289) hide show
  1. package/README.md +170 -58
  2. package/dist/module.d.mts +4 -13
  3. package/dist/module.json +4 -4
  4. package/dist/module.mjs +54 -20
  5. package/dist/runtime/components/Accordion.vue +48 -72
  6. package/dist/runtime/components/Accordion.vue.d.ts +74 -0
  7. package/dist/runtime/components/Alert.vue +65 -83
  8. package/dist/runtime/components/Alert.vue.d.ts +71 -0
  9. package/dist/runtime/components/App.vue +28 -42
  10. package/dist/runtime/components/App.vue.d.ts +26 -0
  11. package/dist/runtime/components/Avatar.vue +82 -58
  12. package/dist/runtime/components/Avatar.vue.d.ts +39 -0
  13. package/dist/runtime/components/AvatarGroup.vue +43 -70
  14. package/dist/runtime/components/AvatarGroup.vue.d.ts +30 -0
  15. package/dist/runtime/components/Badge.vue +70 -64
  16. package/dist/runtime/components/Badge.vue.d.ts +45 -0
  17. package/dist/runtime/components/Breadcrumb.vue +56 -76
  18. package/dist/runtime/components/Breadcrumb.vue.d.ts +79 -0
  19. package/dist/runtime/components/Button.vue +150 -78
  20. package/dist/runtime/components/Button.vue.d.ts +45 -0
  21. package/dist/runtime/components/Calendar.vue +99 -125
  22. package/dist/runtime/components/Calendar.vue.d.ts +102 -0
  23. package/dist/runtime/components/Card.vue +33 -46
  24. package/dist/runtime/components/Card.vue.d.ts +34 -0
  25. package/dist/runtime/components/Carousel.vue +164 -237
  26. package/dist/runtime/components/Carousel.vue.d.ts +125 -0
  27. package/dist/runtime/components/Checkbox.vue +86 -88
  28. package/dist/runtime/components/Checkbox.vue.d.ts +63 -0
  29. package/dist/runtime/components/Chip.vue +44 -58
  30. package/dist/runtime/components/Chip.vue.d.ts +48 -0
  31. package/dist/runtime/components/Collapsible.vue +29 -33
  32. package/dist/runtime/components/Collapsible.vue.d.ts +34 -0
  33. package/dist/runtime/components/Drawer.vue +110 -150
  34. package/dist/runtime/components/Drawer.vue.d.ts +103 -0
  35. package/dist/runtime/components/DropdownMenu.vue +49 -120
  36. package/dist/runtime/components/DropdownMenu.vue.d.ts +140 -0
  37. package/dist/runtime/components/DropdownMenuContent.vue +177 -143
  38. package/dist/runtime/components/DropdownMenuContent.vue.d.ts +51 -0
  39. package/dist/runtime/components/FieldGroup.vue +33 -0
  40. package/dist/runtime/components/FieldGroup.vue.d.ts +33 -0
  41. package/dist/runtime/components/Form.vue +245 -275
  42. package/dist/runtime/components/Form.vue.d.ts +103 -0
  43. package/dist/runtime/components/FormField.vue +108 -0
  44. package/dist/runtime/components/FormField.vue.d.ts +63 -0
  45. package/dist/runtime/components/Icon.vue +20 -0
  46. package/dist/runtime/components/Icon.vue.d.ts +9 -0
  47. package/dist/runtime/components/Input.vue +125 -156
  48. package/dist/runtime/components/Input.vue.d.ts +76 -0
  49. package/dist/runtime/components/InputNumber.vue +103 -130
  50. package/dist/runtime/components/InputNumber.vue.d.ts +191 -0
  51. package/dist/runtime/components/Kbd.vue +24 -39
  52. package/dist/runtime/components/Kbd.vue.d.ts +34 -0
  53. package/dist/runtime/components/Link.vue +105 -337
  54. package/dist/runtime/components/Link.vue.d.ts +95 -0
  55. package/dist/runtime/components/LinkBase.vue +31 -71
  56. package/dist/runtime/components/LinkBase.vue.d.ts +33 -0
  57. package/dist/runtime/components/Modal.vue +82 -103
  58. package/dist/runtime/components/Modal.vue.d.ts +96 -0
  59. package/dist/runtime/components/NavigationMenu.vue +336 -0
  60. package/dist/runtime/components/NavigationMenu.vue.d.ts +181 -0
  61. package/dist/runtime/components/OverlayProvider.vue +12 -16
  62. package/dist/runtime/components/OverlayProvider.vue.d.ts +3 -0
  63. package/dist/runtime/components/Pagination.vue +65 -139
  64. package/dist/runtime/components/Pagination.vue.d.ts +116 -0
  65. package/dist/runtime/components/PinInput.vue +78 -73
  66. package/dist/runtime/components/PinInput.vue.d.ts +54 -0
  67. package/dist/runtime/components/Popover.vue +60 -75
  68. package/dist/runtime/components/Popover.vue.d.ts +70 -0
  69. package/dist/runtime/components/Progress.vue +79 -126
  70. package/dist/runtime/components/Progress.vue.d.ts +63 -0
  71. package/dist/runtime/components/RadioGroup.vue +109 -140
  72. package/dist/runtime/components/RadioGroup.vue.d.ts +96 -0
  73. package/dist/runtime/components/ScrollArea.vue +50 -48
  74. package/dist/runtime/components/ScrollArea.vue.d.ts +21 -0
  75. package/dist/runtime/components/Select.vue +221 -221
  76. package/dist/runtime/components/Select.vue.d.ts +260 -0
  77. package/dist/runtime/components/Separator.vue +55 -47
  78. package/dist/runtime/components/Separator.vue.d.ts +48 -0
  79. package/dist/runtime/components/Skeleton.vue +25 -22
  80. package/dist/runtime/components/Skeleton.vue.d.ts +19 -0
  81. package/dist/runtime/components/Slider.vue +73 -77
  82. package/dist/runtime/components/Slider.vue.d.ts +52 -0
  83. package/dist/runtime/components/Switch.vue +66 -77
  84. package/dist/runtime/components/Switch.vue.d.ts +58 -0
  85. package/dist/runtime/components/Table.vue +357 -215
  86. package/dist/runtime/components/Table.vue.d.ts +234 -0
  87. package/dist/runtime/components/Tabs.vue +90 -88
  88. package/dist/runtime/components/Tabs.vue.d.ts +97 -0
  89. package/dist/runtime/components/Textarea.vue +147 -146
  90. package/dist/runtime/components/Textarea.vue.d.ts +76 -0
  91. package/dist/runtime/components/Toast.vue +108 -90
  92. package/dist/runtime/components/Toast.vue.d.ts +152 -0
  93. package/dist/runtime/components/ToastProvider.vue +82 -109
  94. package/dist/runtime/components/ToastProvider.vue.d.ts +51 -0
  95. package/dist/runtime/components/Tooltip.vue +54 -53
  96. package/dist/runtime/components/Tooltip.vue.d.ts +53 -0
  97. package/dist/runtime/composables/defineShortcuts.d.ts +16 -0
  98. package/dist/runtime/composables/defineShortcuts.js +129 -0
  99. package/dist/runtime/composables/useAvatarGroup.d.ts +8 -3
  100. package/dist/runtime/composables/useAvatarGroup.js +10 -3
  101. package/dist/runtime/composables/useComponentIcons.d.ts +9 -6
  102. package/dist/runtime/composables/useComponentIcons.js +4 -4
  103. package/dist/runtime/composables/useFieldGroup.d.ts +8 -0
  104. package/dist/runtime/composables/useFieldGroup.js +14 -0
  105. package/dist/runtime/composables/useFormField.d.ts +62 -0
  106. package/dist/runtime/composables/useFormField.js +99 -0
  107. package/dist/runtime/composables/useKbd.d.ts +3 -2
  108. package/dist/runtime/composables/useKbd.js +3 -2
  109. package/dist/runtime/composables/useLocale.d.ts +68 -5
  110. package/dist/runtime/composables/useLocale.js +11 -11
  111. package/dist/runtime/composables/useOverlay.d.ts +51 -15
  112. package/dist/runtime/composables/useOverlay.js +44 -30
  113. package/dist/runtime/composables/usePortal.d.ts +6 -0
  114. package/dist/runtime/composables/usePortal.js +17 -0
  115. package/dist/runtime/composables/useToast.d.ts +12 -5
  116. package/dist/runtime/composables/useToast.js +12 -7
  117. package/dist/runtime/locale/en.d.ts +30 -1
  118. package/dist/runtime/locale/en.js +2 -1
  119. package/dist/runtime/locale/index.d.ts +2 -2
  120. package/dist/runtime/locale/index.js +1 -1
  121. package/dist/runtime/locale/zh_tw.d.ts +31 -0
  122. package/dist/runtime/locale/{zh-tw.js → zh_tw.js} +2 -1
  123. package/dist/runtime/plugins/colors.d.ts +2 -0
  124. package/dist/runtime/plugins/colors.js +50 -0
  125. package/dist/runtime/types/app.config.d.ts +6 -0
  126. package/dist/runtime/types/form.d.ts +58 -17
  127. package/dist/runtime/types/form.js +11 -0
  128. package/dist/runtime/types/index.d.ts +51 -8
  129. package/dist/runtime/types/index.js +45 -2
  130. package/dist/runtime/types/input.d.ts +8 -0
  131. package/dist/runtime/types/locale.d.ts +5 -0
  132. package/dist/runtime/types/style.d.ts +33 -0
  133. package/dist/runtime/types/style.js +0 -0
  134. package/dist/runtime/types/unocss.d.ts +4 -0
  135. package/dist/runtime/types/utils.d.ts +38 -37
  136. package/dist/runtime/utils/form.d.ts +5 -1
  137. package/dist/runtime/utils/form.js +49 -0
  138. package/dist/runtime/utils/index.d.ts +10 -13
  139. package/dist/runtime/utils/index.js +41 -48
  140. package/dist/runtime/utils/link.d.ts +5 -6
  141. package/dist/runtime/utils/link.js +16 -2
  142. package/dist/runtime/utils/locale.d.ts +5 -0
  143. package/dist/runtime/utils/locale.js +10 -0
  144. package/dist/runtime/utils/style.d.ts +94 -0
  145. package/dist/runtime/utils/style.js +37 -0
  146. package/dist/runtime/vue/components/Icon.vue +15 -0
  147. package/dist/runtime/vue/components/Icon.vue.d.ts +7 -0
  148. package/dist/runtime/vue/components/Link.vue +163 -0
  149. package/dist/runtime/vue/components/Link.vue.d.ts +95 -0
  150. package/dist/runtime/vue/composables/useAppConfig.d.ts +1 -0
  151. package/dist/runtime/vue/composables/useAppConfig.js +4 -0
  152. package/dist/runtime/vue/plugins/color-mode.d.ts +4 -0
  153. package/dist/runtime/vue/plugins/color-mode.js +6 -0
  154. package/dist/runtime/vue/plugins/head.d.ts +4 -0
  155. package/dist/runtime/vue/plugins/head.js +9 -0
  156. package/dist/runtime/vue/stubs.d.ts +16 -1
  157. package/dist/runtime/vue/stubs.js +32 -1
  158. package/dist/setup.d.mts +13 -0
  159. package/dist/setup.mjs +12 -0
  160. package/dist/shared/ui.CzIlLITK.mjs +51 -0
  161. package/dist/shared/ui.DSyJHSTk.mjs +3787 -0
  162. package/dist/shared/ui.DpbffTXs.d.mts +84 -0
  163. package/dist/shared/ui.IulR-OYx.d.mts +64 -0
  164. package/dist/types.d.mts +3 -1
  165. package/dist/unocss.d.mts +12 -52
  166. package/dist/unocss.mjs +144 -253
  167. package/dist/unplugin.d.mts +13 -26
  168. package/dist/unplugin.mjs +193 -18
  169. package/dist/vite.d.mts +10 -1
  170. package/dist/vite.mjs +12 -3
  171. package/package.json +156 -87
  172. package/vue-plugin.d.ts +5 -0
  173. package/dist/module.cjs +0 -5
  174. package/dist/module.d.ts +0 -13
  175. package/dist/module.mjs.map +0 -1
  176. package/dist/runtime/app/injections.d.ts +0 -9307
  177. package/dist/runtime/app/injections.js +0 -61
  178. package/dist/runtime/components/ButtonGroup.vue +0 -46
  179. package/dist/runtime/components/FormItem.vue +0 -129
  180. package/dist/runtime/composables/useButtonGroup.d.ts +0 -5
  181. package/dist/runtime/composables/useButtonGroup.js +0 -9
  182. package/dist/runtime/composables/useFormItem.d.ts +0 -27
  183. package/dist/runtime/composables/useFormItem.js +0 -64
  184. package/dist/runtime/composables/useTheme.d.ts +0 -9
  185. package/dist/runtime/composables/useTheme.js +0 -23
  186. package/dist/runtime/index.d.ts +0 -44
  187. package/dist/runtime/index.js +0 -44
  188. package/dist/runtime/locale/zh-tw.d.ts +0 -2
  189. package/dist/runtime/theme/accordion.d.ts +0 -56
  190. package/dist/runtime/theme/accordion.js +0 -28
  191. package/dist/runtime/theme/alert.d.ts +0 -125
  192. package/dist/runtime/theme/alert.js +0 -47
  193. package/dist/runtime/theme/app.d.ts +0 -19
  194. package/dist/runtime/theme/app.js +0 -19
  195. package/dist/runtime/theme/avatar-group.d.ts +0 -52
  196. package/dist/runtime/theme/avatar-group.js +0 -32
  197. package/dist/runtime/theme/avatar.d.ts +0 -56
  198. package/dist/runtime/theme/avatar.js +0 -34
  199. package/dist/runtime/theme/badge.d.ts +0 -82
  200. package/dist/runtime/theme/badge.js +0 -92
  201. package/dist/runtime/theme/breadcrumb.d.ts +0 -67
  202. package/dist/runtime/theme/breadcrumb.js +0 -44
  203. package/dist/runtime/theme/button-group.d.ts +0 -66
  204. package/dist/runtime/theme/button-group.js +0 -42
  205. package/dist/runtime/theme/button.d.ts +0 -190
  206. package/dist/runtime/theme/button.js +0 -164
  207. package/dist/runtime/theme/calendar.d.ts +0 -56
  208. package/dist/runtime/theme/calendar.js +0 -69
  209. package/dist/runtime/theme/card.d.ts +0 -62
  210. package/dist/runtime/theme/card.js +0 -37
  211. package/dist/runtime/theme/carousel.d.ts +0 -113
  212. package/dist/runtime/theme/carousel.js +0 -43
  213. package/dist/runtime/theme/checkbox.d.ts +0 -88
  214. package/dist/runtime/theme/checkbox.js +0 -54
  215. package/dist/runtime/theme/chip.d.ts +0 -67
  216. package/dist/runtime/theme/chip.js +0 -66
  217. package/dist/runtime/theme/collapsible.d.ts +0 -38
  218. package/dist/runtime/theme/collapsible.js +0 -10
  219. package/dist/runtime/theme/drawer.d.ts +0 -148
  220. package/dist/runtime/theme/drawer.js +0 -113
  221. package/dist/runtime/theme/dropdown-menu.d.ts +0 -71
  222. package/dist/runtime/theme/dropdown-menu.js +0 -83
  223. package/dist/runtime/theme/form-item.d.ts +0 -76
  224. package/dist/runtime/theme/form-item.js +0 -34
  225. package/dist/runtime/theme/form.d.ts +0 -8
  226. package/dist/runtime/theme/form.js +0 -7
  227. package/dist/runtime/theme/index.d.ts +0 -41
  228. package/dist/runtime/theme/index.js +0 -41
  229. package/dist/runtime/theme/input-number.d.ts +0 -121
  230. package/dist/runtime/theme/input-number.js +0 -95
  231. package/dist/runtime/theme/input.d.ts +0 -178
  232. package/dist/runtime/theme/input.js +0 -151
  233. package/dist/runtime/theme/kbd.d.ts +0 -39
  234. package/dist/runtime/theme/kbd.js +0 -26
  235. package/dist/runtime/theme/link.d.ts +0 -44
  236. package/dist/runtime/theme/link.js +0 -26
  237. package/dist/runtime/theme/modal.d.ts +0 -48
  238. package/dist/runtime/theme/modal.js +0 -55
  239. package/dist/runtime/theme/pagination.d.ts +0 -80
  240. package/dist/runtime/theme/pagination.js +0 -17
  241. package/dist/runtime/theme/pinInput.d.ts +0 -100
  242. package/dist/runtime/theme/pinInput.js +0 -111
  243. package/dist/runtime/theme/popover.d.ts +0 -38
  244. package/dist/runtime/theme/popover.js +0 -13
  245. package/dist/runtime/theme/progress.d.ts +0 -186
  246. package/dist/runtime/theme/progress.js +0 -95
  247. package/dist/runtime/theme/radio-group.d.ts +0 -110
  248. package/dist/runtime/theme/radio-group.js +0 -61
  249. package/dist/runtime/theme/scroll-area.d.ts +0 -73
  250. package/dist/runtime/theme/scroll-area.js +0 -33
  251. package/dist/runtime/theme/select.d.ts +0 -192
  252. package/dist/runtime/theme/select.js +0 -173
  253. package/dist/runtime/theme/separator.d.ts +0 -80
  254. package/dist/runtime/theme/separator.js +0 -53
  255. package/dist/runtime/theme/skeleton.d.ts +0 -8
  256. package/dist/runtime/theme/skeleton.js +0 -7
  257. package/dist/runtime/theme/slider.d.ts +0 -76
  258. package/dist/runtime/theme/slider.js +0 -52
  259. package/dist/runtime/theme/switch.d.ts +0 -122
  260. package/dist/runtime/theme/switch.js +0 -78
  261. package/dist/runtime/theme/table.d.ts +0 -92
  262. package/dist/runtime/theme/table.js +0 -36
  263. package/dist/runtime/theme/tabs.d.ts +0 -135
  264. package/dist/runtime/theme/tabs.js +0 -146
  265. package/dist/runtime/theme/textarea.d.ts +0 -96
  266. package/dist/runtime/theme/textarea.js +0 -116
  267. package/dist/runtime/theme/toast-provider.d.ts +0 -122
  268. package/dist/runtime/theme/toast-provider.js +0 -97
  269. package/dist/runtime/theme/toast.d.ts +0 -89
  270. package/dist/runtime/theme/toast.js +0 -35
  271. package/dist/runtime/theme/tooltip.d.ts +0 -44
  272. package/dist/runtime/theme/tooltip.js +0 -11
  273. package/dist/runtime/types/components.d.ts +0 -42
  274. package/dist/runtime/utils/extend-theme.d.ts +0 -9
  275. package/dist/runtime/utils/extend-theme.js +0 -27
  276. package/dist/runtime/utils/styler.d.ts +0 -4
  277. package/dist/runtime/utils/styler.js +0 -10
  278. package/dist/runtime/utils/translator.d.ts +0 -18
  279. package/dist/runtime/utils/translator.js +0 -8
  280. package/dist/shared/ui.3e7fad19.mjs +0 -5
  281. package/dist/shared/ui.3e7fad19.mjs.map +0 -1
  282. package/dist/types.d.ts +0 -1
  283. package/dist/unocss.d.ts +0 -52
  284. package/dist/unocss.mjs.map +0 -1
  285. package/dist/unplugin.d.ts +0 -26
  286. package/dist/unplugin.mjs.map +0 -1
  287. package/dist/vite.d.ts +0 -9
  288. package/dist/vite.mjs.map +0 -1
  289. /package/dist/runtime/types/{components.js → input.js} +0 -0
@@ -1,273 +1,273 @@
1
- <script lang="ts">
2
- import type { VariantProps } from '@byyuurin/ui-kit'
3
- import type { SelectArrowProps, SelectContentEmits, SelectContentProps, SelectRootEmits, SelectRootProps } from 'reka-ui'
4
- import type { UseComponentIconsProps } from '../composables/useComponentIcons'
5
- import type { select } from '../theme'
6
- import type { AcceptableValue, ArrayOrNested, ComponentAttrs, EmitsToProps, GetItemKeys, GetItemValue, GetModelValue, GetModelValueEmits, MaybeArray, NestedItem } from '../types'
7
-
8
- interface SelectItemBase {
9
- label?: string
10
- icon?: string
11
- /**
12
- * The option type.
13
- * @default "option"
14
- */
15
- type?: 'label' | 'separator' | 'option'
16
- value?: AcceptableValue
17
- disabled?: boolean
18
- [key: string]: any
19
- }
20
-
21
- export type SelectItem = SelectItemBase | AcceptableValue | boolean
22
-
23
- export type SelectEmits<T extends ArrayOrNested<SelectItem>, VK extends GetItemKeys<T> | undefined, M extends boolean> = Omit<SelectRootEmits, 'update:modelValue'> & {
24
- change: [payload: Event]
25
- blur: [payload: FocusEvent]
26
- focus: [payload: FocusEvent]
27
- } & GetModelValueEmits<T, VK, M>
28
-
29
- type SlotProps<T extends SelectItem> = (props: { item: T, index: number }) => any
30
-
31
- export interface SelectSlots<
32
- T extends ArrayOrNested<SelectItem> = ArrayOrNested<SelectItem>,
33
- VK extends GetItemKeys<T> | undefined = undefined,
34
- M extends boolean = false,
35
- I extends NestedItem<T> = NestedItem<T>,
36
- > {
37
- 'leading'?: (props: { modelValue?: GetModelValue<T, VK, M>, open: boolean, ui: ComponentAttrs<typeof select>['ui'] }) => any
38
- 'default'?: (props: { modelValue?: GetModelValue<T, VK, M>, open: boolean }) => any
39
- 'trailing'?: (props: { modelValue?: GetModelValue<T, VK, M>, open: boolean, ui: ComponentAttrs<typeof select>['ui'] }) => any
40
- 'item'?: SlotProps<I>
41
- 'item-leading'?: SlotProps<I>
42
- 'item-label'?: SlotProps<I>
43
- 'item-trailing'?: SlotProps<I>
44
- }
45
-
46
- type SelectVariants = VariantProps<typeof select>
47
-
48
- export interface SelectProps<
49
- T extends ArrayOrNested<SelectItem> = ArrayOrNested<SelectItem>,
50
- VK extends GetItemKeys<T> = 'value',
51
- M extends boolean = false,
52
- > extends ComponentAttrs<typeof select>, UseComponentIconsProps, Omit<SelectRootProps<T>, 'dir' | 'multiple' | 'modelValue' | 'defaultValue' | 'by'> {
53
- id?: string
54
- /** The placeholder text when the select is empty. */
55
- placeholder?: string
56
- variant?: SelectVariants['variant']
57
- size?: SelectVariants['size']
58
- /**
59
- * The icon displayed to open the menu.
60
- * @default app.icons.chevronDown
61
- */
62
- trailingIcon?: string
63
- /**
64
- * The icon displayed when an item is selected.
65
- * @default app.icons.check
66
- */
67
- selectedIcon?: string
68
- /**
69
- * The content of the menu.
70
- * @default { side: 'bottom', sideOffset: 8, collisionPadding: 8, position: 'popper' }
71
- */
72
- content?: Omit<SelectContentProps, 'as' | 'asChild' | 'forceMount'> & Partial<EmitsToProps<SelectContentEmits>>
73
- /**
74
- * Display an arrow alongside the menu.
75
- * @default false
76
- */
77
- arrow?: boolean | Omit<SelectArrowProps, 'as' | 'asChild'>
78
- /**
79
- * Render the menu in a portal.
80
- * @default true
81
- */
82
- portal?: boolean
83
- /**
84
- * When `options` is an array of objects, select the field to use as the value.
85
- * @default "value"
86
- */
87
- valueKey?: VK
88
- /**
89
- * When `options` is an array of objects, select the field to use as the label.
90
- * @default "label"
91
- */
92
- labelKey?: VK
93
- options?: T
94
- /** The value of the Select when initially rendered. Use when you do not need to control the state of the Select. */
95
- defaultValue?: GetModelValue<T, VK, M>
96
- /** The controlled value of the Select. Can be bind as `v-model`. */
97
- modelValue?: GetModelValue<T, VK, M>
98
- /** Whether multiple options can be selected or not. */
99
- multiple?: M & boolean
100
- /** Highlight the ring color like a focus state. */
101
- highlight?: boolean
102
- underline?: boolean
103
- }
1
+ <script>
2
+ import theme from "#build/ui/select";
104
3
  </script>
105
4
 
106
- <script lang="ts" setup generic="T extends ArrayOrNested<SelectItem>, VK extends GetItemKeys<T> = 'value', M extends boolean = false">
107
- import { reactivePick } from '@vueuse/core'
108
- import { defu } from 'defu'
109
- import { SelectArrow, SelectContent, SelectGroup, SelectItem, SelectItemIndicator, SelectItemText, SelectLabel, SelectPortal, SelectRoot, SelectSeparator, SelectTrigger, SelectViewport, useForwardPropsEmits } from 'reka-ui'
110
- import { computed, toRef } from 'vue'
111
- import { useButtonGroup } from '../composables/useButtonGroup'
112
- import { useComponentIcons } from '../composables/useComponentIcons'
113
- import { useFormItem } from '../composables/useFormItem'
114
- import { useTheme } from '../composables/useTheme'
115
- import { compare, get, isArrayOfArray } from '../utils'
116
-
117
- defineOptions({
118
- inheritAttrs: false,
119
- })
120
-
121
- const props = withDefaults(defineProps<SelectProps<T, VK, M>>(), {
122
- valueKey: 'value' as never,
123
- labelKey: 'label' as never,
124
- portal: true,
125
- })
126
-
127
- const emit = defineEmits<SelectEmits<T, VK, M>>()
128
- const slots = defineSlots<SelectSlots<T, VK, M>>()
129
-
130
- const rootProps = useForwardPropsEmits(reactivePick(props, 'open', 'defaultOpen', 'disabled', 'autocomplete', 'required', 'multiple'), emit)
131
- const contentProps = toRef(() => defu(props.content, { side: 'bottom', sideOffset: 8, collisionPadding: 8, position: 'popper' }) as SelectContentProps)
132
- const arrowProps = toRef(() => props.arrow as SelectArrowProps)
133
-
134
- const { id, name, size: formItemSize, highlight, disabled, ariaAttrs, emitFormChange, emitFormInput, emitFormBlur, emitFormFocus } = useFormItem<SelectProps<T, VK, M>>(props)
135
- const { size: buttonGroupSize, orientation } = useButtonGroup(props)
136
-
137
- const { theme, generateStyle } = useTheme()
5
+ <script setup>
6
+ import { reactivePick } from "@vueuse/core";
7
+ import { defu } from "defu";
8
+ import { SelectArrow, SelectContent, SelectGroup, SelectItem as RekaSelectItem, SelectItemIndicator, SelectItemText, SelectLabel, SelectPortal, SelectRoot, SelectSeparator, SelectTrigger, useForwardPropsEmits } from "reka-ui";
9
+ import { computed, onMounted, shallowRef, toRef } from "vue";
10
+ import { useAppConfig } from "#imports";
11
+ import { useComponentIcons } from "../composables/useComponentIcons";
12
+ import { useFieldGroup } from "../composables/useFieldGroup";
13
+ import { useFormField } from "../composables/useFormField";
14
+ import { usePortal } from "../composables/usePortal";
15
+ import { get, getDisplayValue, isArrayOfArray } from "../utils";
16
+ import { cv, merge } from "../utils/style";
17
+ import Avatar from "./Avatar.vue";
18
+ import Chip from "./Chip.vue";
19
+ import Icon from "./Icon.vue";
20
+ defineOptions({ inheritAttrs: false });
21
+ const props = defineProps({
22
+ id: { type: String, required: false },
23
+ placeholder: { type: String, required: false },
24
+ variant: { type: null, required: false },
25
+ size: { type: null, required: false },
26
+ color: { type: null, required: false },
27
+ trailingIcon: { type: [String, Object], required: false },
28
+ selectedIcon: { type: [String, Object], required: false },
29
+ content: { type: Object, required: false },
30
+ arrow: { type: [Boolean, Object], required: false },
31
+ portal: { type: [Boolean, String], required: false, skipCheck: true, default: true },
32
+ valueKey: { type: null, required: false, default: "value" },
33
+ labelKey: { type: null, required: false, default: "label" },
34
+ descriptionKey: { type: null, required: false, default: "description" },
35
+ items: { type: null, required: false },
36
+ defaultValue: { type: null, required: false },
37
+ modelValue: { type: null, required: false },
38
+ multiple: { type: Boolean, required: false },
39
+ highlight: { type: Boolean, required: false },
40
+ autofocus: { type: Boolean, required: false },
41
+ autofocusDelay: { type: Number, required: false, default: 0 },
42
+ ui: { type: null, required: false },
43
+ class: { type: [Object, String, Number, Boolean, null, Array], required: false, skipCheck: true },
44
+ icon: { type: [String, Object], required: false },
45
+ avatar: { type: Object, required: false },
46
+ leading: { type: Boolean, required: false },
47
+ leadingIcon: { type: [String, Object], required: false },
48
+ trailing: { type: Boolean, required: false },
49
+ loading: { type: Boolean, required: false },
50
+ loadingIcon: { type: [String, Object], required: false },
51
+ open: { type: Boolean, required: false },
52
+ defaultOpen: { type: Boolean, required: false },
53
+ autocomplete: { type: String, required: false },
54
+ disabled: { type: Boolean, required: false },
55
+ name: { type: String, required: false },
56
+ required: { type: Boolean, required: false }
57
+ });
58
+ const emit = defineEmits(["update:open", "change", "blur", "focus", "update:modelValue"]);
59
+ const slots = defineSlots();
60
+ const rootProps = useForwardPropsEmits(reactivePick(props, "open", "defaultOpen", "disabled", "autocomplete", "required", "multiple"), emit);
61
+ const portalProps = usePortal(toRef(() => props.portal));
62
+ const contentProps = toRef(() => defu(props.content, { side: "bottom", sideOffset: 8, collisionPadding: 8, position: "popper" }));
63
+ const arrowProps = toRef(() => props.arrow);
64
+ const { id, name, size: formFieldSize, color, highlight, disabled, ariaAttrs, emitFormChange, emitFormInput, emitFormBlur, emitFormFocus } = useFormField(props);
65
+ const { size: fieldGroupSize, orientation } = useFieldGroup(props);
66
+ const appConfig = useAppConfig();
138
67
  const { isLeading, isTrailing, leadingIconName, trailingIconName } = useComponentIcons(toRef(() => defu(props, {
139
- trailingIcon: theme.value.app.icons.chevronDown,
140
- })))
141
-
142
- const style = computed(() => generateStyle('select', {
143
- ...props,
144
- groupOrientation: orientation.value,
145
- size: buttonGroupSize.value || formItemSize.value,
146
- highlight: highlight.value,
147
- leading: isLeading.value,
148
- trailing: isTrailing.value,
149
- }))
150
-
151
- const groups = computed<SelectItem[][]>(
152
- () => props.options?.length
153
- ? isArrayOfArray(props.options) ? props.options : [props.options]
154
- : [],
155
- )
156
-
157
- const items = computed(() => groups.value.flat() as T[])
158
-
159
- function displayValue(value?: MaybeArray<GetItemValue<T, VK>>): string {
160
- if (props.multiple && Array.isArray(value))
161
- return value.map((v) => displayValue(v)).filter(Boolean).join(', ')
162
-
163
- const item = items.value.find((item) => compare(typeof item === 'object' ? get(item as Record<string, any>, props.valueKey as string) : item, value))
164
- return (item != null) && (typeof item === 'object' ? get(item, props.labelKey as string) : String(item))
68
+ trailingIcon: appConfig.ui.icons.chevronDown
69
+ })));
70
+ const ui = computed(() => {
71
+ const styler = cv(merge(theme, appConfig.ui.select));
72
+ return styler({
73
+ ...props,
74
+ fieldGroup: orientation.value,
75
+ size: fieldGroupSize.value || formFieldSize.value,
76
+ color: color.value,
77
+ highlight: highlight.value,
78
+ leading: isLeading.value || !!props.avatar || !!slots.leading,
79
+ trailing: isTrailing.value || !!slots.trailing
80
+ });
81
+ });
82
+ const groups = computed(
83
+ () => props.items?.length ? isArrayOfArray(props.items) ? props.items : [props.items] : []
84
+ );
85
+ const items = computed(() => groups.value.flat());
86
+ function displayValue(value) {
87
+ if (props.multiple && Array.isArray(value)) {
88
+ const displayedValues = value.map((item) => getDisplayValue(items.value, item, {
89
+ labelKey: props.labelKey,
90
+ valueKey: props.valueKey
91
+ })).filter((v) => v != null && v !== "");
92
+ return displayedValues.length > 0 ? displayedValues.join(", ") : void 0;
93
+ }
94
+ return getDisplayValue(items.value, value, {
95
+ labelKey: props.labelKey,
96
+ valueKey: props.valueKey
97
+ });
165
98
  }
166
-
167
- function isSelectItem(item: SelectItem): item is SelectItemBase {
168
- return typeof item === 'object' && item !== null
99
+ const triggerRef = shallowRef(null);
100
+ function autoFocus() {
101
+ if (props.autofocus) {
102
+ triggerRef.value?.$el?.focus({
103
+ focusVisible: true
104
+ });
105
+ }
169
106
  }
170
-
171
- function onUpdate(value: any) {
172
- // @ts-expect-error - 'target' does not exist in type 'EventInit'
173
- const event = new Event('change', { target: { value } })
174
- emit('change', event)
175
- emitFormChange()
176
- emitFormInput()
107
+ onMounted(() => {
108
+ setTimeout(() => autoFocus(), props.autofocusDelay);
109
+ });
110
+ function onUpdate(value) {
111
+ const event = new Event("change", { target: { value } });
112
+ emit("change", event);
113
+ emitFormChange();
114
+ emitFormInput();
177
115
  }
178
-
179
- function onUpdateOpen(value: boolean) {
116
+ function onUpdateOpen(value) {
180
117
  if (value) {
181
- const event = new FocusEvent('focus')
182
- emit('focus', event)
183
- emitFormFocus()
184
- }
185
- else {
186
- const event = new FocusEvent('blur')
187
- emit('blur', event)
188
- emitFormBlur()
118
+ const event = new FocusEvent("focus");
119
+ emit("focus", event);
120
+ emitFormFocus();
121
+ } else {
122
+ const event = new FocusEvent("blur");
123
+ emit("blur", event);
124
+ emitFormBlur();
189
125
  }
190
126
  }
127
+ function isSelectItem(item) {
128
+ return typeof item === "object" && item !== null;
129
+ }
130
+ defineExpose({
131
+ triggerRef
132
+ });
191
133
  </script>
192
134
 
193
135
  <template>
194
136
  <SelectRoot
195
- v-slot="{ modelValue: innerValue, open }"
196
- v-bind="rootProps"
137
+ v-slot="{ modelValue, open }"
197
138
  :name="name"
139
+ v-bind="rootProps"
140
+ :default-value="defaultValue"
141
+ :model-value="modelValue"
198
142
  :autocomplete="props.autocomplete"
199
143
  :disabled="disabled"
200
- :default-value="(props.defaultValue as MaybeArray<AcceptableValue>)"
201
- :model-value="(props.modelValue as MaybeArray<AcceptableValue>)"
202
144
  @update:model-value="onUpdate"
203
145
  @update:open="onUpdateOpen"
204
146
  >
205
- <SelectTrigger v-bind="{ ...$attrs, ...ariaAttrs, id }" :class="style.base({ class: [props.class, props.ui?.base] })">
206
- <span v-if="isLeading || slots.leading" :class="style.leading({ class: props.ui?.leading })">
207
- <slot name="leading" :model-value="(innerValue as GetModelValue<T, VK, M>)" :open="open" :ui="props.ui">
208
- <span v-if="isLeading && leadingIconName" :class="style.leadingIcon({ class: [leadingIconName, props.ui?.leadingIcon] })"></span>
147
+ <SelectTrigger
148
+ ref="triggerRef"
149
+ v-bind="{ id, ...$attrs, ...ariaAttrs }"
150
+ :class="ui.base({ class: [props.ui?.base, props.class] })"
151
+ data-part="base"
152
+ >
153
+ <span v-if="isLeading || !!props.avatar || slots.leading" :class="ui.leading({ class: props.ui?.leading })" data-part="leading">
154
+ <slot name="leading" :model-value="modelValue" :open="open" :ui="ui">
155
+ <Icon
156
+ v-if="isLeading && leadingIconName"
157
+ :name="leadingIconName"
158
+ :class="ui.leadingIcon({ class: props.ui?.leadingIcon })"
159
+ data-part="leading-icon"
160
+ />
161
+ <Avatar
162
+ v-else-if="props.avatar"
163
+ :size="props.ui?.itemLeadingChipSize || ui.itemLeadingAvatarSize()"
164
+ v-bind="props.avatar"
165
+ :class="ui.leadingAvatar({ class: props.ui?.leadingAvatar })"
166
+ data-part="leading-avatar"
167
+ />
209
168
  </slot>
210
169
  </span>
211
170
 
212
- <slot :model-value="(innerValue as GetModelValue<T, VK, M>)" :open="open">
213
- <template v-for="displayedModelValue in [displayValue((innerValue as GetModelValue<T, VK, M>))]" :key="displayedModelValue">
214
- <span v-if="displayedModelValue" :class="style.value({ class: props.ui?.value })">
171
+ <slot :model-value="modelValue" :open="open" :ui="ui">
172
+ <template v-for="displayedModelValue in [displayValue(modelValue)]" :key="displayedModelValue">
173
+ <span v-if="displayedModelValue != null" :class="ui.value({ class: props.ui?.value })" data-part="value">
215
174
  {{ displayedModelValue }}
216
175
  </span>
217
- <span v-else :class="style.placeholder({ class: props.ui?.placeholder })">
218
- {{ placeholder }}&nbsp;
176
+ <span v-else :class="ui.placeholder({ class: props.ui?.placeholder })" data-part="placeholder">
177
+ <template v-if="props.placeholder">{{ props.placeholder }}</template>
178
+ <template v-else>&nbsp;</template>
219
179
  </span>
220
180
  </template>
221
181
  </slot>
222
182
 
223
- <span v-if="isTrailing || !!slots.trailing" :class="style.trailing({ class: props.ui?.trailing })">
224
- <slot name="trailing" :model-value="(innerValue as GetModelValue<T, VK, M>)" :open="open" :ui="props.ui">
225
- <span v-if="trailingIconName" :class="style.trailingIcon({ class: [trailingIconName, props.ui?.trailingIcon] })"></span>
183
+ <span v-if="isTrailing || !!slots.trailing" :class="ui.trailing({ class: props.ui?.trailing })" data-part="trailing">
184
+ <slot name="trailing" :model-value="modelValue" :open="open" :ui="ui">
185
+ <Icon v-if="trailingIconName" :name="trailingIconName" :class="ui.trailingIcon({ class: props.ui?.trailingIcon })" data-part="trailing-icon" />
226
186
  </slot>
227
187
  </span>
228
188
  </SelectTrigger>
229
189
 
230
- <SelectPortal :disabled="!props.portal">
231
- <SelectContent v-bind="contentProps" :class="style.content({ class: props.ui?.content })">
232
- <SelectViewport :class="style.viewport({ class: props.ui?.viewport })">
233
- <SelectGroup v-for="(group, groupIndex) in groups" :key="`group-${groupIndex}`" :class="style.group({ class: props.ui?.group })">
190
+ <SelectPortal v-bind="portalProps">
191
+ <SelectContent v-bind="contentProps" :class="ui.content({ class: props.ui?.content })" data-part="content">
192
+ <slot name="content-top"></slot>
193
+
194
+ <div role="presentation" :class="ui.viewport({ class: props.ui?.viewport })" data-part="viewport">
195
+ <SelectGroup v-for="(group, groupIndex) in groups" :key="`group-${groupIndex}`" :class="ui.group({ class: props.ui?.group })" data-part="group">
234
196
  <template v-for="(item, index) in group" :key="`group-${groupIndex}-${index}`">
235
- <SelectLabel v-if="isSelectItem(item) && item.type === 'label'" :class="style.label({ class: props.ui?.label })">
236
- {{ get(item, props.labelKey as string) }}
197
+ <SelectLabel v-if="isSelectItem(item) && item.type === 'label'" :class="ui.label({ class: [props.ui?.label, item.ui?.label, item.class] })" data-part="label">
198
+ {{ get(item, props.labelKey) }}
237
199
  </SelectLabel>
238
- <SelectSeparator v-else-if="isSelectItem(item) && item.type === 'separator'" :class="style.separator({ class: props.ui?.separator })" />
239
200
 
240
- <SelectItem
201
+ <SelectSeparator v-else-if="isSelectItem(item) && item.type === 'separator'" :class="ui.separator({ class: [props.ui?.separator, item.ui?.separator, item.class] })" data-part="separator" />
202
+
203
+ <RekaSelectItem
241
204
  v-else
242
- :class="style.item({ class: props.ui?.item })"
205
+ :value="isSelectItem(item) ? get(item, props.valueKey) : item"
243
206
  :disabled="isSelectItem(item) && item.disabled"
244
- :value="isSelectItem(item) ? get(item, props.valueKey as string) : item"
207
+ :class="ui.item({ class: [props.ui?.item, ...isSelectItem(item) ? [item.ui?.item, item.class] : []] })"
208
+ data-part="item"
209
+ @select="isSelectItem(item) && item.onSelect?.($event)"
245
210
  >
246
- <slot name="item" :item="(item as NestedItem<T>)" :index="index">
247
- <slot name="item-leading" :item="(item as NestedItem<T>)" :index="index">
248
- <span v-if="isSelectItem(item) && item.icon" :class="style.itemLeadingIcon({ class: [item.icon, props.ui?.itemLeadingIcon] })"></span>
211
+ <slot name="item" :item="item" :index="index" :ui="ui">
212
+ <slot name="item-leading" :item="item" :index="index" :ui="ui">
213
+ <Icon
214
+ v-if="isSelectItem(item) && item.icon"
215
+ :name="item.icon"
216
+ :class="ui.itemLeadingIcon({ class: [props.ui?.itemLeadingIcon, item.ui?.itemLeadingIcon] })"
217
+ data-part="item-leading-icon"
218
+ />
219
+ <Avatar
220
+ v-else-if="isSelectItem(item) && item.avatar"
221
+ :size="item.ui?.itemLeadingAvatarSize || props.ui?.itemLeadingAvatarSize || ui.itemLeadingAvatarSize()"
222
+ v-bind="item.avatar"
223
+ :class="ui.itemLeadingAvatar({ class: [props.ui?.leadingAvatar, item.ui?.itemLeadingAvatar] })"
224
+ data-part="item-leading-avatar"
225
+ />
226
+ <Chip
227
+ v-else-if="isSelectItem(item) && item.chip"
228
+ :size="item.ui?.itemLeadingChipSize || props.ui?.itemLeadingChipSize || ui.itemLeadingChipSize()"
229
+ inset
230
+ standalone
231
+ v-bind="item.chip"
232
+ :class="ui.itemLeadingChip({ class: [props.ui?.itemLeadingChip, item.ui?.itemLeadingChip] })"
233
+ data-part="item-leading-chip"
234
+ />
249
235
  </slot>
250
236
 
251
- <SelectItemText :class="style.itemLabel({ class: props.ui?.itemLabel })">
252
- <slot name="item-label" :item="(item as NestedItem<T>)" :index="index">
253
- {{ isSelectItem(item) ? get(item, props.labelKey as string) : item }}
254
- </slot>
255
- </SelectItemText>
237
+ <span :class="ui.itemWrapper({ class: [props.ui?.itemWrapper, ...isSelectItem(item) ? [item.ui?.itemWrapper] : []] })" data-part="item-wrapper">
238
+ <SelectItemText :class="ui.itemLabel({ class: [props.ui?.itemLabel, isSelectItem(item) && item.ui?.itemLabel] })" data-part="item-label">
239
+ <slot name="item-label" :item="item" :index="index">
240
+ {{ isSelectItem(item) ? get(item, props.labelKey) : item }}
241
+ </slot>
242
+ </SelectItemText>
243
+
244
+ <span
245
+ v-if="isSelectItem(item) && get(item, props.descriptionKey) || !!slots['item-description']"
246
+ :class="ui.itemDescription({ class: [props.ui?.itemDescription, ...isSelectItem(item) ? [item.ui?.itemDescription] : []] })"
247
+ data-part="item-description"
248
+ >
249
+ <slot name="item-description" :item="item" :index="index">
250
+ {{ isSelectItem(item) ? get(item, props.descriptionKey) : "" }}
251
+ </slot>
252
+ </span>
253
+ </span>
256
254
 
257
- <span :class="style.itemTrailing({ class: props.ui?.itemTrailing })">
258
- <slot name="item-trailing" :item="(item as NestedItem<T>)" :index="index"></slot>
255
+ <span :class="ui.itemTrailing({ class: [props.ui?.itemTrailing, isSelectItem(item) && item.ui?.itemTrailing] })" data-part="item-trailing">
256
+ <slot name="item-trailing" :item="item" :index="index" :ui="ui"></slot>
259
257
 
260
258
  <SelectItemIndicator as-child>
261
- <span :class="style.itemTrailingIcon({ class: [props.selectedIcon || theme.app.icons.check, props.ui?.itemTrailingIcon] })"></span>
259
+ <Icon :name="props.selectedIcon || appConfig.ui.icons.check" :class="ui.itemTrailingIcon({ class: [props.ui?.itemTrailingIcon, isSelectItem(item) && item.ui?.itemTrailingIcon] })" data-part="item-trailing-icon" />
262
260
  </SelectItemIndicator>
263
261
  </span>
264
262
  </slot>
265
- </SelectItem>
263
+ </RekaSelectItem>
266
264
  </template>
267
265
  </SelectGroup>
268
- </SelectViewport>
266
+ </div>
267
+
268
+ <slot name="content-bottom"></slot>
269
269
 
270
- <SelectArrow v-if="!!props.arrow" v-bind="arrowProps" :class="style.arrow({ class: props.ui?.arrow })" />
270
+ <SelectArrow v-if="props.arrow" v-bind="arrowProps" :class="ui.arrow({ class: props.ui?.arrow })" data-part="arrow" />
271
271
  </SelectContent>
272
272
  </SelectPortal>
273
273
  </SelectRoot>