@nuxt/ui 3.0.0-alpha.8 → 3.0.0-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.nuxt/ui/accordion.ts +2 -2
- package/.nuxt/ui/alert.ts +122 -95
- package/.nuxt/ui/avatar-group.ts +14 -2
- package/.nuxt/ui/avatar.ts +16 -4
- package/.nuxt/ui/badge.ts +139 -93
- package/.nuxt/ui/breadcrumb.ts +5 -5
- package/.nuxt/ui/button-group.ts +13 -0
- package/.nuxt/ui/button.ts +167 -136
- package/.nuxt/ui/calendar.ts +103 -0
- package/.nuxt/ui/card.ts +27 -1
- package/.nuxt/ui/carousel.ts +9 -7
- package/.nuxt/ui/checkbox.ts +45 -27
- package/.nuxt/ui/chip.ts +44 -15
- package/.nuxt/ui/color-picker.ts +47 -0
- package/.nuxt/ui/command-palette.ts +28 -18
- package/.nuxt/ui/container.ts +1 -1
- package/.nuxt/ui/context-menu.ts +64 -46
- package/.nuxt/ui/drawer.ts +83 -15
- package/.nuxt/ui/dropdown-menu.ts +65 -47
- package/.nuxt/ui/form-field.ts +15 -7
- package/.nuxt/ui/index.ts +7 -1
- package/.nuxt/ui/input-menu.ts +150 -116
- package/.nuxt/ui/input-number.ts +235 -0
- package/.nuxt/ui/input.ts +111 -76
- package/.nuxt/ui/kbd.ts +18 -6
- package/.nuxt/ui/link.ts +3 -3
- package/.nuxt/ui/modal.ts +8 -7
- package/.nuxt/ui/navigation-menu.ts +244 -131
- package/.nuxt/ui/pin-input.ts +171 -0
- package/.nuxt/ui/popover.ts +2 -2
- package/.nuxt/ui/progress.ts +111 -72
- package/.nuxt/ui/radio-group.ts +45 -22
- package/.nuxt/ui/select-menu.ts +127 -96
- package/.nuxt/ui/select.ts +120 -84
- package/.nuxt/ui/separator.ts +60 -31
- package/.nuxt/ui/skeleton.ts +1 -1
- package/.nuxt/ui/slideover.ts +17 -9
- package/.nuxt/ui/slider.ts +61 -38
- package/.nuxt/ui/stepper.ts +202 -0
- package/.nuxt/ui/switch.ts +40 -22
- package/.nuxt/ui/table.ts +49 -31
- package/.nuxt/ui/tabs.ts +101 -73
- package/.nuxt/ui/textarea.ts +111 -76
- package/.nuxt/ui/toast.ts +53 -33
- package/.nuxt/ui/toaster.ts +31 -15
- package/.nuxt/ui/tooltip.ts +2 -2
- package/.nuxt/ui/tree.ts +154 -0
- package/.nuxt/ui.css +92 -0
- package/README.md +69 -18
- package/cli/commands/{init.mjs → make/component.mjs} +16 -4
- package/cli/commands/make/index.mjs +14 -0
- package/cli/commands/make/locale.mjs +64 -0
- package/cli/index.mjs +2 -2
- package/cli/package.json +2 -2
- package/cli/templates.mjs +62 -12
- package/cli/utils.mjs +14 -0
- package/dist/module.cjs +9 -170
- package/dist/module.d.cts +5 -15
- package/dist/module.d.mts +5 -15
- package/dist/module.d.ts +5 -15
- package/dist/module.json +2 -2
- package/dist/module.mjs +12 -167
- package/dist/runtime/components/Accordion.vue +8 -39
- package/dist/runtime/components/Alert.vue +25 -21
- package/dist/runtime/components/App.vue +15 -15
- package/dist/runtime/components/Avatar.vue +33 -21
- package/dist/runtime/components/AvatarGroup.vue +5 -7
- package/dist/runtime/components/Badge.vue +10 -8
- package/dist/runtime/components/Breadcrumb.vue +13 -34
- package/dist/runtime/components/Button.vue +5 -8
- package/dist/runtime/components/ButtonGroup.vue +5 -7
- package/dist/runtime/components/Calendar.vue +194 -0
- package/dist/runtime/components/Card.vue +10 -9
- package/dist/runtime/components/Carousel.vue +26 -17
- package/dist/runtime/components/Checkbox.vue +32 -38
- package/dist/runtime/components/Chip.vue +6 -8
- package/dist/runtime/components/Collapsible.vue +10 -11
- package/dist/runtime/components/ColorPicker.vue +297 -0
- package/dist/runtime/components/CommandPalette.vue +114 -98
- package/dist/runtime/components/Container.vue +4 -7
- package/dist/runtime/components/ContextMenu.vue +16 -69
- package/dist/runtime/components/ContextMenuContent.vue +14 -10
- package/dist/runtime/components/Drawer.vue +23 -12
- package/dist/runtime/components/DropdownMenu.vue +18 -59
- package/dist/runtime/components/DropdownMenuContent.vue +14 -10
- package/dist/runtime/components/Form.vue +78 -49
- package/dist/runtime/components/FormField.vue +28 -15
- package/dist/runtime/components/Icon.vue +1 -1
- package/dist/runtime/components/Input.vue +15 -7
- package/dist/runtime/components/InputMenu.vue +133 -66
- package/dist/runtime/components/InputNumber.vue +197 -0
- package/dist/runtime/components/Kbd.vue +5 -6
- package/dist/runtime/components/Link.vue +24 -13
- package/dist/runtime/components/LinkBase.vue +1 -1
- package/dist/runtime/components/Modal.vue +56 -34
- package/dist/runtime/components/NavigationMenu.vue +129 -112
- package/dist/runtime/components/OverlayProvider.vue +28 -0
- package/dist/runtime/components/Pagination.vue +18 -14
- package/dist/runtime/components/PinInput.vue +95 -0
- package/dist/runtime/components/Popover.vue +28 -14
- package/dist/runtime/components/Progress.vue +28 -12
- package/dist/runtime/components/RadioGroup.vue +9 -12
- package/dist/runtime/components/Select.vue +61 -35
- package/dist/runtime/components/SelectMenu.vue +201 -130
- package/dist/runtime/components/Separator.vue +6 -5
- package/dist/runtime/components/Skeleton.vue +4 -7
- package/dist/runtime/components/Slideover.vue +56 -33
- package/dist/runtime/components/Slider.vue +8 -7
- package/dist/runtime/components/Stepper.vue +170 -0
- package/dist/runtime/components/Switch.vue +19 -23
- package/dist/runtime/components/Table.vue +157 -32
- package/dist/runtime/components/Tabs.vue +12 -31
- package/dist/runtime/components/Textarea.vue +18 -9
- package/dist/runtime/components/Toast.vue +39 -25
- package/dist/runtime/components/Toaster.vue +31 -24
- package/dist/runtime/components/Tooltip.vue +9 -12
- package/dist/runtime/components/Tree.vue +196 -0
- package/dist/runtime/composables/defineLocale.d.ts +9 -0
- package/dist/runtime/composables/defineLocale.js +4 -0
- package/dist/runtime/composables/defineShortcuts.d.ts +1 -1
- package/dist/runtime/composables/defineShortcuts.js +2 -2
- package/dist/runtime/composables/useFormField.d.ts +11 -4
- package/dist/runtime/composables/useFormField.js +19 -9
- package/dist/runtime/composables/useLocale.d.ts +4 -0
- package/dist/runtime/composables/useLocale.js +10 -0
- package/dist/runtime/composables/useOverlay.d.ts +30 -0
- package/dist/runtime/composables/useOverlay.js +70 -0
- package/dist/runtime/composables/useToast.d.ts +4 -3
- package/dist/runtime/composables/useToast.js +20 -6
- package/dist/runtime/index.css +1 -1
- package/dist/runtime/keyframes.css +1 -1
- package/dist/runtime/locale/ar.d.ts +2 -0
- package/dist/runtime/locale/ar.js +55 -0
- package/dist/runtime/locale/az.d.ts +2 -0
- package/dist/runtime/locale/az.js +54 -0
- package/dist/runtime/locale/bn.d.ts +2 -0
- package/dist/runtime/locale/bn.js +54 -0
- package/dist/runtime/locale/cs.d.ts +2 -0
- package/dist/runtime/locale/cs.js +54 -0
- package/dist/runtime/locale/da.d.ts +2 -0
- package/dist/runtime/locale/da.js +54 -0
- package/dist/runtime/locale/de.d.ts +2 -0
- package/dist/runtime/locale/de.js +54 -0
- package/dist/runtime/locale/el.d.ts +2 -0
- package/dist/runtime/locale/el.js +54 -0
- package/dist/runtime/locale/en.d.ts +2 -0
- package/dist/runtime/locale/en.js +54 -0
- package/dist/runtime/locale/es.d.ts +2 -0
- package/dist/runtime/locale/es.js +54 -0
- package/dist/runtime/locale/et.d.ts +2 -0
- package/dist/runtime/locale/et.js +54 -0
- package/dist/runtime/locale/fa_ir.d.ts +2 -0
- package/dist/runtime/locale/fa_ir.js +55 -0
- package/dist/runtime/locale/fi.d.ts +2 -0
- package/dist/runtime/locale/fi.js +54 -0
- package/dist/runtime/locale/fr.d.ts +2 -0
- package/dist/runtime/locale/fr.js +54 -0
- package/dist/runtime/locale/he.d.ts +2 -0
- package/dist/runtime/locale/he.js +53 -0
- package/dist/runtime/locale/hi.d.ts +2 -0
- package/dist/runtime/locale/hi.js +54 -0
- package/dist/runtime/locale/hu.d.ts +2 -0
- package/dist/runtime/locale/hu.js +54 -0
- package/dist/runtime/locale/id.d.ts +2 -0
- package/dist/runtime/locale/id.js +54 -0
- package/dist/runtime/locale/index.d.ts +34 -0
- package/dist/runtime/locale/index.js +34 -0
- package/dist/runtime/locale/it.d.ts +2 -0
- package/dist/runtime/locale/it.js +54 -0
- package/dist/runtime/locale/ja.d.ts +2 -0
- package/dist/runtime/locale/ja.js +54 -0
- package/dist/runtime/locale/km.d.ts +2 -0
- package/dist/runtime/locale/km.js +54 -0
- package/dist/runtime/locale/ko.d.ts +2 -0
- package/dist/runtime/locale/ko.js +54 -0
- package/dist/runtime/locale/nb_no.d.ts +2 -0
- package/dist/runtime/locale/nb_no.js +54 -0
- package/dist/runtime/locale/nl.d.ts +2 -0
- package/dist/runtime/locale/nl.js +54 -0
- package/dist/runtime/locale/pl.d.ts +2 -0
- package/dist/runtime/locale/pl.js +54 -0
- package/dist/runtime/locale/pt.d.ts +2 -0
- package/dist/runtime/locale/pt.js +54 -0
- package/dist/runtime/locale/pt_br.d.ts +2 -0
- package/dist/runtime/locale/pt_br.js +54 -0
- package/dist/runtime/locale/ru.d.ts +2 -0
- package/dist/runtime/locale/ru.js +54 -0
- package/dist/runtime/locale/sk.d.ts +2 -0
- package/dist/runtime/locale/sk.js +54 -0
- package/dist/runtime/locale/sv.d.ts +2 -0
- package/dist/runtime/locale/sv.js +54 -0
- package/dist/runtime/locale/th.d.ts +2 -0
- package/dist/runtime/locale/th.js +54 -0
- package/dist/runtime/locale/tr.d.ts +2 -0
- package/dist/runtime/locale/tr.js +54 -0
- package/dist/runtime/locale/uk.d.ts +2 -0
- package/dist/runtime/locale/uk.js +54 -0
- package/dist/runtime/locale/vi.d.ts +2 -0
- package/dist/runtime/locale/vi.js +54 -0
- package/dist/runtime/locale/zh_cn.d.ts +2 -0
- package/dist/runtime/locale/zh_cn.js +54 -0
- package/dist/runtime/locale/zh_tw.d.ts +2 -0
- package/dist/runtime/locale/zh_tw.js +54 -0
- package/dist/runtime/plugins/colors.js +8 -5
- package/dist/runtime/types/form.d.ts +29 -15
- package/dist/runtime/types/form.js +2 -2
- package/dist/runtime/types/index.d.ts +8 -0
- package/dist/runtime/types/index.js +8 -0
- package/dist/runtime/types/locale.d.ts +56 -0
- package/dist/runtime/types/locale.js +0 -0
- package/dist/runtime/types/utils.d.ts +7 -3
- package/dist/runtime/utils/form.d.ts +5 -9
- package/dist/runtime/utils/form.js +113 -50
- package/dist/runtime/utils/index.d.ts +1 -1
- package/dist/runtime/utils/index.js +15 -2
- package/dist/runtime/utils/link.d.ts +1 -1
- package/dist/runtime/utils/locale.d.ts +15 -0
- package/dist/runtime/utils/locale.js +25 -0
- package/dist/runtime/utils/tv.d.ts +1 -0
- package/dist/runtime/utils/tv.js +4 -0
- package/dist/runtime/vue/components/Icon.vue +2 -2
- package/dist/runtime/vue/components/Link.vue +87 -23
- package/dist/runtime/vue/composables/useAppConfig.d.ts +1 -0
- package/dist/runtime/vue/composables/useAppConfig.js +2 -0
- package/dist/runtime/vue/plugins/head.d.ts +1 -1
- package/dist/runtime/vue/plugins/head.js +3 -3
- package/dist/runtime/vue/stubs.d.ts +19 -0
- package/dist/runtime/vue/stubs.js +37 -0
- package/dist/shared/{ui.BufKhDiD.mjs → ui.DSPu6Y8j.mjs} +1071 -409
- package/dist/shared/{ui.BU7wzH0D.cjs → ui.DfK2RX6G.cjs} +1074 -409
- package/dist/unplugin.cjs +62 -26
- package/dist/unplugin.d.cts +17 -3
- package/dist/unplugin.d.mts +17 -3
- package/dist/unplugin.d.ts +17 -3
- package/dist/unplugin.mjs +61 -25
- package/dist/vite.cjs +3 -2
- package/dist/vite.d.cts +2 -0
- package/dist/vite.d.mts +2 -0
- package/dist/vite.d.ts +2 -0
- package/dist/vite.mjs +3 -2
- package/package.json +110 -67
- package/dist/chunks/component-meta.cjs +0 -73264
- package/dist/chunks/component-meta.mjs +0 -73262
- package/dist/client/devtools/200.html +0 -1
- package/dist/client/devtools/404.html +0 -1
- package/dist/client/devtools/_fonts/rP2Wp2ywxg089UriCZaSExd86J3t9jz86MvyyKK58UfivUw4aw-SK92LTmKP0.woff2 +0 -0
- package/dist/client/devtools/_fonts/rP2Wp2ywxg089UriCZaSExd86J3t9jz86MvyyKy58UfivUw-9uYm8d48E4.woff2 +0 -0
- package/dist/client/devtools/_fonts/rP2Yp2ywxg089UriI5-g4vlH9VoD8Cmcqbu0-K6z9mXg-VNw7NHvqnp.woff2 +0 -0
- package/dist/client/devtools/_fonts/rP2Yp2ywxg089UriI5-g4vlH9VoD8Cmcqbu6-K6z9mXgjU0-EkYdMs3MAX.woff2 +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat-7DW3w-R7n06NbhGy.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat-JDG3w-leGNfkTmsj.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat-JDW3w-ciElMF03ku.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat8JCm3w-sB722Uoa0f.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat8JDW3w-PBDI1JDjwV.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat8gCm3w-0q1hqVn09O.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat9XCm3w-ByvzuLy2fa.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat9uCm3w-5TKCIs6EEw.woff +0 -0
- package/dist/client/devtools/_fonts/rP2rp2ywxg089UriCZaSExd86J3t9jz86Mvy4qCRAL19DksVat_XDW3w-r2swRDGfn2.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAC5thTQ-ldB60l5U8r.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAIpthTQ-wbFKGFDrgo.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAIpxhTQ-LLUBv5jskj.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwARZthTQ-F71RdTRbNg.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwA_JxhTQ-6nh65gZkc0.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAfJthTQ-aMoWEJLmTt.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAkJxhTQ-WMBvmLOgKm.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAop1hTQ-utGC2hnWq2.woff +0 -0
- package/dist/client/devtools/_fonts/rP2tp2ywxg089UriI5-g4vlH9VoD8CmcqZG40F9JadbnoEwAopxhTQ-YpyTieVa5B.woff +0 -0
- package/dist/client/devtools/_nuxt/Bj9hdafK.js +0 -1
- package/dist/client/devtools/_nuxt/DM3_wAgz.js +0 -62
- package/dist/client/devtools/_nuxt/builds/latest.json +0 -1
- package/dist/client/devtools/_nuxt/builds/meta/e6b425f7-b919-4014-915b-0ea07c316790.json +0 -1
- package/dist/client/devtools/_nuxt/entry.DaJP-ZMB.css +0 -24
- package/dist/client/devtools/_nuxt/error-404.B0Nmv3fV.css +0 -1
- package/dist/client/devtools/_nuxt/error-500.C8fgTxVz.css +0 -1
- package/dist/client/devtools/_nuxt/hKiujHsR.js +0 -1
- package/dist/client/devtools/favicon.svg +0 -1
- package/dist/client/devtools/index.html +0 -1
- package/dist/devtools/runtime/DevtoolsRenderer.vue +0 -53
- package/dist/devtools/runtime/examples/AvatarGroupExample.vue +0 -7
- package/dist/devtools/runtime/examples/ButtonGroupExample.vue +0 -8
- package/dist/devtools/runtime/examples/CardExample.vue +0 -13
- package/dist/devtools/runtime/examples/CarouselExample.vue +0 -13
- package/dist/devtools/runtime/examples/ChipExample.vue +0 -5
- package/dist/devtools/runtime/examples/CollapsibleExample.vue +0 -8
- package/dist/devtools/runtime/examples/CommandPaletteExample.vue +0 -29
- package/dist/devtools/runtime/examples/ContainerExample.vue +0 -5
- package/dist/devtools/runtime/examples/ContextMenuExample.vue +0 -5
- package/dist/devtools/runtime/examples/DrawerExample.vue +0 -8
- package/dist/devtools/runtime/examples/DropdownMenuExample.vue +0 -5
- package/dist/devtools/runtime/examples/FormExample.vue +0 -30
- package/dist/devtools/runtime/examples/FormFieldExample.vue +0 -5
- package/dist/devtools/runtime/examples/LinkExample.vue +0 -5
- package/dist/devtools/runtime/examples/ModalExample.vue +0 -8
- package/dist/devtools/runtime/examples/PopoverExample.vue +0 -8
- package/dist/devtools/runtime/examples/SkeletonExample.vue +0 -3
- package/dist/devtools/runtime/examples/SlideoverExample.vue +0 -8
- package/dist/devtools/runtime/examples/ToasterExample.vue +0 -11
- package/dist/devtools/runtime/examples/TooltipExample.vue +0 -5
- package/dist/runtime/components/ModalProvider.vue +0 -12
- package/dist/runtime/components/SlideoverProvider.vue +0 -12
- package/dist/runtime/composables/extendDevtoolsMeta.d.ts +0 -7
- package/dist/runtime/composables/extendDevtoolsMeta.js +0 -2
- package/dist/runtime/composables/useModal.d.ts +0 -17
- package/dist/runtime/composables/useModal.js +0 -46
- package/dist/runtime/composables/useSlideover.d.ts +0 -17
- package/dist/runtime/composables/useSlideover.js +0 -46
- package/dist/runtime/plugins/modal.d.ts +0 -2
- package/dist/runtime/plugins/modal.js +0 -10
- package/dist/runtime/plugins/slideover.d.ts +0 -2
- package/dist/runtime/plugins/slideover.js +0 -10
|
@@ -1,17 +1,17 @@
|
|
|
1
1
|
<script lang="ts">
|
|
2
|
-
import {
|
|
3
|
-
import type { ComboboxRootProps, ComboboxRootEmits, ComboboxContentProps, ComboboxArrowProps } from '
|
|
2
|
+
import type { VariantProps } from 'tailwind-variants'
|
|
3
|
+
import type { ComboboxRootProps, ComboboxRootEmits, ComboboxContentProps, ComboboxArrowProps, AcceptableValue } from 'reka-ui'
|
|
4
4
|
import type { AppConfig } from '@nuxt/schema'
|
|
5
5
|
import _appConfig from '#build/app.config'
|
|
6
6
|
import theme from '#build/ui/select-menu'
|
|
7
7
|
import type { UseComponentIconsProps } from '../composables/useComponentIcons'
|
|
8
|
-
import {
|
|
8
|
+
import { tv } from '../utils/tv'
|
|
9
9
|
import type { AvatarProps, ChipProps, InputProps } from '../types'
|
|
10
|
-
import type {
|
|
10
|
+
import type { PartialString, MaybeArrayOfArray, MaybeArrayOfArrayItem, SelectModelValue, SelectModelValueEmits, SelectItemKey } from '../types/utils'
|
|
11
11
|
|
|
12
|
-
const
|
|
12
|
+
const appConfigSelectMenu = _appConfig as AppConfig & { ui: { selectMenu: Partial<typeof theme> } }
|
|
13
13
|
|
|
14
|
-
const selectMenu = tv({ extend: tv(theme), ...(
|
|
14
|
+
const selectMenu = tv({ extend: tv(theme), ...(appConfigSelectMenu.ui?.selectMenu || {}) })
|
|
15
15
|
|
|
16
16
|
export interface SelectMenuItem {
|
|
17
17
|
label?: string
|
|
@@ -29,16 +29,17 @@ export interface SelectMenuItem {
|
|
|
29
29
|
|
|
30
30
|
type SelectMenuVariants = VariantProps<typeof selectMenu>
|
|
31
31
|
|
|
32
|
-
export interface SelectMenuProps<T extends MaybeArrayOfArrayItem<I>, I extends MaybeArrayOfArray<SelectMenuItem | AcceptableValue> = MaybeArrayOfArray<SelectMenuItem | AcceptableValue>, V extends SelectItemKey<T> | undefined = undefined, M extends boolean = false> extends Pick<ComboboxRootProps<T>, '
|
|
32
|
+
export interface SelectMenuProps<T extends MaybeArrayOfArrayItem<I>, I extends MaybeArrayOfArray<SelectMenuItem | AcceptableValue | boolean> = MaybeArrayOfArray<SelectMenuItem | AcceptableValue | boolean>, V extends SelectItemKey<T> | undefined = undefined, M extends boolean = false> extends Pick<ComboboxRootProps<T>, 'open' | 'defaultOpen' | 'disabled' | 'name' | 'resetSearchTermOnBlur' | 'highlightOnHover'>, UseComponentIconsProps {
|
|
33
33
|
id?: string
|
|
34
34
|
/** The placeholder text when the select is empty. */
|
|
35
35
|
placeholder?: string
|
|
36
36
|
/**
|
|
37
|
-
*
|
|
37
|
+
* Whether to display the search input or not.
|
|
38
38
|
* Can be an object to pass additional props to the input.
|
|
39
|
-
*
|
|
39
|
+
* `{ placeholder: 'Search...', variant: 'none' }`{lang="ts-type"}
|
|
40
|
+
* @defaultValue true
|
|
40
41
|
*/
|
|
41
|
-
searchInput?: boolean |
|
|
42
|
+
searchInput?: boolean | InputProps
|
|
42
43
|
color?: SelectMenuVariants['color']
|
|
43
44
|
variant?: SelectMenuVariants['variant']
|
|
44
45
|
size?: SelectMenuVariants['size']
|
|
@@ -55,7 +56,7 @@ export interface SelectMenuProps<T extends MaybeArrayOfArrayItem<I>, I extends M
|
|
|
55
56
|
selectedIcon?: string
|
|
56
57
|
/**
|
|
57
58
|
* The content of the menu.
|
|
58
|
-
* @defaultValue { side: 'bottom', sideOffset: 8, position: 'popper' }
|
|
59
|
+
* @defaultValue { side: 'bottom', sideOffset: 8, collisionPadding: 8, position: 'popper' }
|
|
59
60
|
*/
|
|
60
61
|
content?: Omit<ComboboxContentProps, 'as' | 'asChild' | 'forceMount'>
|
|
61
62
|
/**
|
|
@@ -68,12 +69,6 @@ export interface SelectMenuProps<T extends MaybeArrayOfArrayItem<I>, I extends M
|
|
|
68
69
|
* @defaultValue true
|
|
69
70
|
*/
|
|
70
71
|
portal?: boolean
|
|
71
|
-
/**
|
|
72
|
-
* Whether to filter items or not, can be an array of fields to filter.
|
|
73
|
-
* When `false`, items will not be filtered which is useful for custom filtering (useAsyncData, useFetch, etc.).
|
|
74
|
-
* @defaultValue ['label']
|
|
75
|
-
*/
|
|
76
|
-
filter?: boolean | string[]
|
|
77
72
|
/**
|
|
78
73
|
* When `items` is an array of objects, select the field to use as the value instead of the object itself.
|
|
79
74
|
* @defaultValue undefined
|
|
@@ -83,80 +78,103 @@ export interface SelectMenuProps<T extends MaybeArrayOfArrayItem<I>, I extends M
|
|
|
83
78
|
* When `items` is an array of objects, select the field to use as the label.
|
|
84
79
|
* @defaultValue 'label'
|
|
85
80
|
*/
|
|
86
|
-
labelKey?:
|
|
81
|
+
labelKey?: V
|
|
87
82
|
items?: I
|
|
83
|
+
/** The value of the SelectMenu when initially rendered. Use when you do not need to control the state of the SelectMenu. */
|
|
84
|
+
defaultValue?: SelectModelValue<T, V, M>
|
|
85
|
+
/** The controlled value of the SelectMenu. Can be binded-with with `v-model`. */
|
|
86
|
+
modelValue?: SelectModelValue<T, V, M>
|
|
87
|
+
/** Whether multiple options can be selected or not. */
|
|
88
|
+
multiple?: M & boolean
|
|
88
89
|
/** Highlight the ring color like a focus state. */
|
|
89
90
|
highlight?: boolean
|
|
91
|
+
/**
|
|
92
|
+
* Determines if custom user input that does not exist in options can be added.
|
|
93
|
+
* @defaultValue false
|
|
94
|
+
*/
|
|
95
|
+
createItem?: boolean | 'always' | { position?: 'top' | 'bottom', when?: 'empty' | 'always' }
|
|
96
|
+
/**
|
|
97
|
+
* Fields to filter items by.
|
|
98
|
+
* @defaultValue [labelKey]
|
|
99
|
+
*/
|
|
100
|
+
filterFields?: string[]
|
|
101
|
+
/**
|
|
102
|
+
* When `true`, disable the default filters, useful for custom filtering (useAsyncData, useFetch, etc.).
|
|
103
|
+
* @defaultValue false
|
|
104
|
+
*/
|
|
105
|
+
ignoreFilter?: boolean
|
|
90
106
|
class?: any
|
|
91
107
|
ui?: PartialString<typeof selectMenu.slots>
|
|
92
|
-
/** The controlled value of the Combobox. Can be binded-with with `v-model`. */
|
|
93
|
-
modelValue?: SelectModelValue<T, V, M>
|
|
94
|
-
/** Whether multiple options can be selected or not. */
|
|
95
|
-
multiple?: M
|
|
96
108
|
}
|
|
97
109
|
|
|
98
110
|
export type SelectMenuEmits<T, V, M extends boolean> = Omit<ComboboxRootEmits<T>, 'update:modelValue'> & {
|
|
99
111
|
change: [payload: Event]
|
|
100
112
|
blur: [payload: FocusEvent]
|
|
101
113
|
focus: [payload: FocusEvent]
|
|
114
|
+
create: [item: string]
|
|
102
115
|
} & SelectModelValueEmits<T, V, M>
|
|
103
116
|
|
|
104
117
|
type SlotProps<T> = (props: { item: T, index: number }) => any
|
|
105
118
|
|
|
106
|
-
export interface SelectMenuSlots<T> {
|
|
107
|
-
'leading'(props: { modelValue: T, open: boolean, ui: any }): any
|
|
108
|
-
'default'(props: { modelValue: T, open: boolean }): any
|
|
109
|
-
'trailing'(props: { modelValue: T, open: boolean, ui: any }): any
|
|
119
|
+
export interface SelectMenuSlots<T, M extends boolean> {
|
|
120
|
+
'leading'(props: { modelValue?: M extends true ? T[] : T, open: boolean, ui: any }): any
|
|
121
|
+
'default'(props: { modelValue?: M extends true ? T[] : T, open: boolean }): any
|
|
122
|
+
'trailing'(props: { modelValue?: M extends true ? T[] : T, open: boolean, ui: any }): any
|
|
110
123
|
'empty'(props: { searchTerm?: string }): any
|
|
111
124
|
'item': SlotProps<T>
|
|
112
125
|
'item-leading': SlotProps<T>
|
|
113
126
|
'item-label': SlotProps<T>
|
|
114
127
|
'item-trailing': SlotProps<T>
|
|
128
|
+
'create-item-label'(props: { item: string }): any
|
|
115
129
|
}
|
|
116
|
-
|
|
117
|
-
extendDevtoolsMeta({ defaultProps: { items: ['Option 1', 'Option 2', 'Option 3'] } })
|
|
118
130
|
</script>
|
|
119
131
|
|
|
120
|
-
<script setup lang="ts" generic="T extends MaybeArrayOfArrayItem<I>, I extends MaybeArrayOfArray<SelectMenuItem | AcceptableValue> = MaybeArrayOfArray<SelectMenuItem | AcceptableValue>, V extends SelectItemKey<T> | undefined = undefined, M extends boolean = false">
|
|
121
|
-
import { computed, toRef } from 'vue'
|
|
122
|
-
import { ComboboxRoot, ComboboxArrow, ComboboxAnchor, ComboboxInput, ComboboxTrigger, ComboboxPortal, ComboboxContent, ComboboxViewport, ComboboxEmpty, ComboboxGroup, ComboboxLabel, ComboboxSeparator, ComboboxItem, ComboboxItemIndicator, useForwardPropsEmits } from '
|
|
132
|
+
<script setup lang="ts" generic="T extends MaybeArrayOfArrayItem<I>, I extends MaybeArrayOfArray<SelectMenuItem | AcceptableValue | boolean> = MaybeArrayOfArray<SelectMenuItem | AcceptableValue | boolean>, V extends SelectItemKey<T> | undefined = undefined, M extends boolean = false">
|
|
133
|
+
import { computed, toRef, toRaw } from 'vue'
|
|
134
|
+
import { ComboboxRoot, ComboboxArrow, ComboboxAnchor, ComboboxInput, ComboboxTrigger, ComboboxPortal, ComboboxContent, ComboboxViewport, ComboboxEmpty, ComboboxGroup, ComboboxLabel, ComboboxSeparator, ComboboxItem, ComboboxItemIndicator, FocusScope, useForwardPropsEmits, useFilter } from 'reka-ui'
|
|
123
135
|
import { defu } from 'defu'
|
|
124
|
-
import
|
|
125
|
-
import { reactivePick } from '@vueuse/core'
|
|
136
|
+
import { reactivePick, createReusableTemplate } from '@vueuse/core'
|
|
126
137
|
import { useAppConfig } from '#imports'
|
|
127
138
|
import { useButtonGroup } from '../composables/useButtonGroup'
|
|
128
139
|
import { useComponentIcons } from '../composables/useComponentIcons'
|
|
129
140
|
import { useFormField } from '../composables/useFormField'
|
|
130
|
-
import {
|
|
141
|
+
import { useLocale } from '../composables/useLocale'
|
|
142
|
+
import { get, compare } from '../utils'
|
|
131
143
|
import UIcon from './Icon.vue'
|
|
132
144
|
import UAvatar from './Avatar.vue'
|
|
133
145
|
import UChip from './Chip.vue'
|
|
146
|
+
import UInput from './Input.vue'
|
|
147
|
+
|
|
148
|
+
defineOptions({ inheritAttrs: false })
|
|
134
149
|
|
|
135
150
|
const props = withDefaults(defineProps<SelectMenuProps<T, I, V, M>>(), {
|
|
136
|
-
search: true,
|
|
137
151
|
portal: true,
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
labelKey: 'label' as never
|
|
152
|
+
searchInput: true,
|
|
153
|
+
labelKey: 'label' as never,
|
|
154
|
+
resetSearchTermOnBlur: true
|
|
142
155
|
})
|
|
143
|
-
|
|
144
156
|
const emits = defineEmits<SelectMenuEmits<T, V, M>>()
|
|
145
|
-
const slots = defineSlots<SelectMenuSlots<T>>()
|
|
157
|
+
const slots = defineSlots<SelectMenuSlots<T, M>>()
|
|
146
158
|
|
|
147
159
|
const searchTerm = defineModel<string>('searchTerm', { default: '' })
|
|
148
160
|
|
|
161
|
+
const { t } = useLocale()
|
|
149
162
|
const appConfig = useAppConfig()
|
|
150
|
-
const
|
|
151
|
-
|
|
163
|
+
const { contains } = useFilter({ sensitivity: 'base' })
|
|
164
|
+
|
|
165
|
+
const rootProps = useForwardPropsEmits(reactivePick(props, 'modelValue', 'defaultValue', 'open', 'defaultOpen', 'multiple', 'resetSearchTermOnBlur', 'highlightOnHover'), emits)
|
|
166
|
+
const contentProps = toRef(() => defu(props.content, { side: 'bottom', sideOffset: 8, collisionPadding: 8, position: 'popper' }) as ComboboxContentProps)
|
|
152
167
|
const arrowProps = toRef(() => props.arrow as ComboboxArrowProps)
|
|
168
|
+
const searchInputProps = toRef(() => defu(props.searchInput, { placeholder: t('selectMenu.search'), variant: 'none' }) as InputProps)
|
|
153
169
|
|
|
154
|
-
const { emitFormBlur, emitFormInput, emitFormChange, size: formGroupSize, color, id, name, highlight, disabled } = useFormField<InputProps>(props)
|
|
170
|
+
const { emitFormBlur, emitFormFocus, emitFormInput, emitFormChange, size: formGroupSize, color, id, name, highlight, disabled, ariaAttrs } = useFormField<InputProps>(props)
|
|
155
171
|
const { orientation, size: buttonGroupSize } = useButtonGroup<InputProps>(props)
|
|
156
172
|
const { isLeading, isTrailing, leadingIconName, trailingIconName } = useComponentIcons(toRef(() => defu(props, { trailingIcon: appConfig.ui.icons.chevronDown })))
|
|
157
173
|
|
|
158
174
|
const selectSize = computed(() => buttonGroupSize.value || formGroupSize.value)
|
|
159
175
|
|
|
176
|
+
const [DefineCreateItemTemplate, ReuseCreateItemTemplate] = createReusableTemplate()
|
|
177
|
+
|
|
160
178
|
const ui = computed(() => selectMenu({
|
|
161
179
|
color: color.value,
|
|
162
180
|
variant: props.variant,
|
|
@@ -170,40 +188,61 @@ const ui = computed(() => selectMenu({
|
|
|
170
188
|
|
|
171
189
|
function displayValue(value: T | T[]): string {
|
|
172
190
|
if (props.multiple && Array.isArray(value)) {
|
|
173
|
-
return value.map(v => displayValue(v)).join(', ')
|
|
191
|
+
return value.map(v => displayValue(v)).filter(Boolean).join(', ')
|
|
174
192
|
}
|
|
175
193
|
|
|
176
|
-
|
|
194
|
+
if (!props.valueKey) {
|
|
195
|
+
return value && (typeof value === 'object' ? get(value, props.labelKey as string) : value)
|
|
196
|
+
}
|
|
177
197
|
|
|
198
|
+
const item = items.value.find(item => compare(typeof item === 'object' ? get(item as Record<string, any>, props.valueKey as string) : item, value))
|
|
178
199
|
return item && (typeof item === 'object' ? get(item, props.labelKey as string) : item)
|
|
179
200
|
}
|
|
180
201
|
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
202
|
+
const groups = computed(() => props.items?.length ? (Array.isArray(props.items[0]) ? props.items : [props.items]) as SelectMenuItem[][] : [])
|
|
203
|
+
// eslint-disable-next-line vue/no-dupe-keys
|
|
204
|
+
const items = computed(() => groups.value.flatMap(group => group) as T[])
|
|
205
|
+
|
|
206
|
+
const filteredGroups = computed(() => {
|
|
207
|
+
if (props.ignoreFilter || !searchTerm.value) {
|
|
208
|
+
return groups.value
|
|
184
209
|
}
|
|
185
210
|
|
|
186
|
-
const fields = Array.isArray(props.
|
|
187
|
-
const escapedSearchTerm = escapeRegExp(searchTerm)
|
|
211
|
+
const fields = Array.isArray(props.filterFields) ? props.filterFields : [props.labelKey] as string[]
|
|
188
212
|
|
|
189
|
-
return items.filter((item
|
|
213
|
+
return groups.value.map(items => items.filter((item) => {
|
|
190
214
|
if (typeof item !== 'object') {
|
|
191
|
-
return
|
|
215
|
+
return contains(item, searchTerm.value)
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
if (item.type && ['label', 'separator'].includes(item.type)) {
|
|
219
|
+
return true
|
|
192
220
|
}
|
|
193
221
|
|
|
194
|
-
return fields.some((field)
|
|
195
|
-
|
|
222
|
+
return fields.some(field => contains(get(item, field), searchTerm.value))
|
|
223
|
+
})).filter(group => group.filter(item => !item.type || !['label', 'separator'].includes(item.type)).length > 0)
|
|
224
|
+
})
|
|
225
|
+
const filteredItems = computed(() => filteredGroups.value.flatMap(group => group) as T[])
|
|
196
226
|
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
}
|
|
227
|
+
const createItem = computed(() => {
|
|
228
|
+
if (!props.createItem || !searchTerm.value) {
|
|
229
|
+
return false
|
|
230
|
+
}
|
|
201
231
|
|
|
202
|
-
const
|
|
203
|
-
|
|
204
|
-
|
|
232
|
+
const newItem = props.valueKey ? { [props.valueKey]: searchTerm.value } as T : searchTerm.value
|
|
233
|
+
|
|
234
|
+
if ((typeof props.createItem === 'object' && props.createItem.when === 'always') || props.createItem === 'always') {
|
|
235
|
+
return !filteredItems.value.find(item => compare(item, newItem, props.valueKey))
|
|
236
|
+
}
|
|
237
|
+
|
|
238
|
+
return !filteredItems.value.length
|
|
239
|
+
})
|
|
240
|
+
const createItemPosition = computed(() => typeof props.createItem === 'object' ? props.createItem.position : 'bottom')
|
|
205
241
|
|
|
206
242
|
function onUpdate(value: any) {
|
|
243
|
+
if (toRaw(props.modelValue) === value) {
|
|
244
|
+
return
|
|
245
|
+
}
|
|
207
246
|
// @ts-expect-error - 'target' does not exist in type 'EventInit'
|
|
208
247
|
const event = new Event('change', { target: { value } })
|
|
209
248
|
emits('change', event)
|
|
@@ -212,42 +251,72 @@ function onUpdate(value: any) {
|
|
|
212
251
|
}
|
|
213
252
|
|
|
214
253
|
function onUpdateOpen(value: boolean) {
|
|
254
|
+
let timeoutId
|
|
255
|
+
|
|
215
256
|
if (!value) {
|
|
216
257
|
const event = new FocusEvent('blur')
|
|
258
|
+
|
|
217
259
|
emits('blur', event)
|
|
218
260
|
emitFormBlur()
|
|
261
|
+
|
|
262
|
+
// Since we use `displayValue` prop inside ComboboxInput we should reset searchTerm manually
|
|
263
|
+
// https://reka-ui.com/docs/components/combobox#api-reference
|
|
264
|
+
if (props.resetSearchTermOnBlur) {
|
|
265
|
+
const STATE_ANIMATION_DELAY_MS = 100
|
|
266
|
+
|
|
267
|
+
timeoutId = setTimeout(() => {
|
|
268
|
+
searchTerm.value = ''
|
|
269
|
+
}, STATE_ANIMATION_DELAY_MS)
|
|
270
|
+
}
|
|
219
271
|
} else {
|
|
220
272
|
const event = new FocusEvent('focus')
|
|
221
273
|
emits('focus', event)
|
|
274
|
+
emitFormFocus()
|
|
275
|
+
clearTimeout(timeoutId)
|
|
222
276
|
}
|
|
223
277
|
}
|
|
224
278
|
</script>
|
|
225
279
|
|
|
280
|
+
<!-- eslint-disable vue/no-template-shadow -->
|
|
226
281
|
<template>
|
|
282
|
+
<DefineCreateItemTemplate>
|
|
283
|
+
<ComboboxGroup :class="ui.group({ class: props.ui?.group })">
|
|
284
|
+
<ComboboxItem
|
|
285
|
+
:class="ui.item({ class: props.ui?.item })"
|
|
286
|
+
:value="searchTerm"
|
|
287
|
+
@select.prevent="emits('create', searchTerm)"
|
|
288
|
+
>
|
|
289
|
+
<span :class="ui.itemLabel({ class: props.ui?.itemLabel })">
|
|
290
|
+
<slot name="create-item-label" :item="searchTerm">
|
|
291
|
+
{{ t('selectMenu.create', { label: searchTerm }) }}
|
|
292
|
+
</slot>
|
|
293
|
+
</span>
|
|
294
|
+
</ComboboxItem>
|
|
295
|
+
</ComboboxGroup>
|
|
296
|
+
</DefineCreateItemTemplate>
|
|
297
|
+
|
|
227
298
|
<ComboboxRoot
|
|
228
299
|
:id="id"
|
|
229
300
|
v-slot="{ modelValue, open }"
|
|
230
|
-
v-bind="rootProps"
|
|
231
|
-
|
|
301
|
+
v-bind="{ ...rootProps, ...$attrs, ...ariaAttrs }"
|
|
302
|
+
ignore-filter
|
|
232
303
|
as-child
|
|
233
304
|
:name="name"
|
|
234
305
|
:disabled="disabled"
|
|
235
|
-
:display-value="() => searchTerm"
|
|
236
|
-
:filter-function="filterFunction"
|
|
237
306
|
@update:model-value="onUpdate"
|
|
238
307
|
@update:open="onUpdateOpen"
|
|
239
308
|
>
|
|
240
309
|
<ComboboxAnchor as-child>
|
|
241
310
|
<ComboboxTrigger :class="ui.base({ class: [props.class, props.ui?.base] })" tabindex="0">
|
|
242
311
|
<span v-if="isLeading || !!avatar || !!slots.leading" :class="ui.leading({ class: props.ui?.leading })">
|
|
243
|
-
<slot name="leading" :model-value="(modelValue as T)" :open="open" :ui="ui">
|
|
312
|
+
<slot name="leading" :model-value="(modelValue as M extends true ? T[] : T)" :open="open" :ui="ui">
|
|
244
313
|
<UIcon v-if="isLeading && leadingIconName" :name="leadingIconName" :class="ui.leadingIcon({ class: props.ui?.leadingIcon })" />
|
|
245
314
|
<UAvatar v-else-if="!!avatar" :size="((props.ui?.itemLeadingAvatarSize || ui.itemLeadingAvatarSize()) as AvatarProps['size'])" v-bind="avatar" :class="ui.itemLeadingAvatar({ class: props.ui?.itemLeadingAvatar })" />
|
|
246
315
|
</slot>
|
|
247
316
|
</span>
|
|
248
317
|
|
|
249
|
-
<slot :model-value="(modelValue as T)" :open="open">
|
|
250
|
-
<template v-for="displayedModelValue in [displayValue(modelValue)]" :key="displayedModelValue">
|
|
318
|
+
<slot :model-value="(modelValue as M extends true ? T[] : T)" :open="open">
|
|
319
|
+
<template v-for="displayedModelValue in [displayValue(modelValue as M extends true ? T[] : T)]" :key="displayedModelValue">
|
|
251
320
|
<span v-if="displayedModelValue" :class="ui.value({ class: props.ui?.value })">
|
|
252
321
|
{{ displayedModelValue }}
|
|
253
322
|
</span>
|
|
@@ -258,7 +327,7 @@ function onUpdateOpen(value: boolean) {
|
|
|
258
327
|
</slot>
|
|
259
328
|
|
|
260
329
|
<span v-if="isTrailing || !!slots.trailing" :class="ui.trailing({ class: props.ui?.trailing })">
|
|
261
|
-
<slot name="trailing" :model-value="(modelValue as T)" :open="open" :ui="ui">
|
|
330
|
+
<slot name="trailing" :model-value="(modelValue as M extends true ? T[] : T)" :open="open" :ui="ui">
|
|
262
331
|
<UIcon v-if="trailingIconName" :name="trailingIconName" :class="ui.trailingIcon({ class: props.ui?.trailingIcon })" />
|
|
263
332
|
</slot>
|
|
264
333
|
</span>
|
|
@@ -267,68 +336,70 @@ function onUpdateOpen(value: boolean) {
|
|
|
267
336
|
|
|
268
337
|
<ComboboxPortal :disabled="!portal">
|
|
269
338
|
<ComboboxContent :class="ui.content({ class: props.ui?.content })" v-bind="contentProps">
|
|
270
|
-
<
|
|
271
|
-
v-if="!!searchInput"
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
:class="ui.
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
339
|
+
<FocusScope trapped :class="ui.focusScope({ class: props.ui?.focusScope })">
|
|
340
|
+
<ComboboxInput v-if="!!searchInput" v-model="searchTerm" :display-value="() => searchTerm" as-child>
|
|
341
|
+
<UInput autofocus autocomplete="off" v-bind="searchInputProps" :class="ui.input({ class: props.ui?.input })" />
|
|
342
|
+
</ComboboxInput>
|
|
343
|
+
|
|
344
|
+
<ComboboxEmpty :class="ui.empty({ class: props.ui?.empty })">
|
|
345
|
+
<slot name="empty" :search-term="searchTerm">
|
|
346
|
+
{{ searchTerm ? t('selectMenu.noMatch', { searchTerm }) : t('selectMenu.noData') }}
|
|
347
|
+
</slot>
|
|
348
|
+
</ComboboxEmpty>
|
|
349
|
+
|
|
350
|
+
<ComboboxViewport :class="ui.viewport({ class: props.ui?.viewport })">
|
|
351
|
+
<ReuseCreateItemTemplate v-if="createItem && createItemPosition === 'top'" />
|
|
352
|
+
|
|
353
|
+
<ComboboxGroup v-for="(group, groupIndex) in filteredGroups" :key="`group-${groupIndex}`" :class="ui.group({ class: props.ui?.group })">
|
|
354
|
+
<template v-for="(item, index) in group" :key="`group-${groupIndex}-${index}`">
|
|
355
|
+
<ComboboxLabel v-if="item?.type === 'label'" :class="ui.label({ class: props.ui?.label })">
|
|
356
|
+
{{ get(item, props.labelKey as string) }}
|
|
357
|
+
</ComboboxLabel>
|
|
358
|
+
|
|
359
|
+
<ComboboxSeparator v-else-if="item?.type === 'separator'" :class="ui.separator({ class: props.ui?.separator })" />
|
|
360
|
+
|
|
361
|
+
<ComboboxItem
|
|
362
|
+
v-else
|
|
363
|
+
:class="ui.item({ class: props.ui?.item })"
|
|
364
|
+
:disabled="item.disabled"
|
|
365
|
+
:value="valueKey && typeof item === 'object' ? get(item, props.valueKey as string) : item"
|
|
366
|
+
@select="item.onSelect"
|
|
367
|
+
>
|
|
368
|
+
<slot name="item" :item="(item as T)" :index="index">
|
|
369
|
+
<slot name="item-leading" :item="(item as T)" :index="index">
|
|
370
|
+
<UIcon v-if="item.icon" :name="item.icon" :class="ui.itemLeadingIcon({ class: props.ui?.itemLeadingIcon })" />
|
|
371
|
+
<UAvatar v-else-if="item.avatar" :size="((props.ui?.itemLeadingAvatarSize || ui.itemLeadingAvatarSize()) as AvatarProps['size'])" v-bind="item.avatar" :class="ui.itemLeadingAvatar({ class: props.ui?.itemLeadingAvatar })" />
|
|
372
|
+
<UChip
|
|
373
|
+
v-else-if="item.chip"
|
|
374
|
+
:size="((props.ui?.itemLeadingChipSize || ui.itemLeadingChipSize()) as ChipProps['size'])"
|
|
375
|
+
inset
|
|
376
|
+
standalone
|
|
377
|
+
v-bind="item.chip"
|
|
378
|
+
:class="ui.itemLeadingChip({ class: props.ui?.itemLeadingChip })"
|
|
379
|
+
/>
|
|
380
|
+
</slot>
|
|
381
|
+
|
|
382
|
+
<span :class="ui.itemLabel({ class: props.ui?.itemLabel })">
|
|
383
|
+
<slot name="item-label" :item="(item as T)" :index="index">
|
|
384
|
+
{{ typeof item === 'object' ? get(item, props.labelKey as string) : item }}
|
|
385
|
+
</slot>
|
|
386
|
+
</span>
|
|
387
|
+
|
|
388
|
+
<span :class="ui.itemTrailing({ class: props.ui?.itemTrailing })">
|
|
389
|
+
<slot name="item-trailing" :item="(item as T)" :index="index" />
|
|
390
|
+
|
|
391
|
+
<ComboboxItemIndicator as-child>
|
|
392
|
+
<UIcon :name="selectedIcon || appConfig.ui.icons.check" :class="ui.itemTrailingIcon({ class: props.ui?.itemTrailingIcon })" />
|
|
393
|
+
</ComboboxItemIndicator>
|
|
394
|
+
</span>
|
|
312
395
|
</slot>
|
|
396
|
+
</ComboboxItem>
|
|
397
|
+
</template>
|
|
398
|
+
</ComboboxGroup>
|
|
313
399
|
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
</slot>
|
|
318
|
-
</span>
|
|
319
|
-
|
|
320
|
-
<span :class="ui.itemTrailing({ class: props.ui?.itemTrailing })">
|
|
321
|
-
<slot name="item-trailing" :item="(item as T)" :index="index" />
|
|
322
|
-
|
|
323
|
-
<ComboboxItemIndicator as-child>
|
|
324
|
-
<UIcon :name="selectedIcon || appConfig.ui.icons.check" :class="ui.itemTrailingIcon({ class: props.ui?.itemTrailingIcon })" />
|
|
325
|
-
</ComboboxItemIndicator>
|
|
326
|
-
</span>
|
|
327
|
-
</slot>
|
|
328
|
-
</ComboboxItem>
|
|
329
|
-
</template>
|
|
330
|
-
</ComboboxGroup>
|
|
331
|
-
</ComboboxViewport>
|
|
400
|
+
<ReuseCreateItemTemplate v-if="createItem && createItemPosition === 'bottom'" />
|
|
401
|
+
</ComboboxViewport>
|
|
402
|
+
</FocusScope>
|
|
332
403
|
|
|
333
404
|
<ComboboxArrow v-if="!!arrow" v-bind="arrowProps" :class="ui.arrow({ class: props.ui?.arrow })" />
|
|
334
405
|
</ComboboxContent>
|
|
@@ -1,14 +1,15 @@
|
|
|
1
1
|
<script lang="ts">
|
|
2
|
-
import {
|
|
3
|
-
import type { SeparatorProps as _SeparatorProps } from '
|
|
2
|
+
import type { VariantProps } from 'tailwind-variants'
|
|
3
|
+
import type { SeparatorProps as _SeparatorProps } from 'reka-ui'
|
|
4
4
|
import type { AppConfig } from '@nuxt/schema'
|
|
5
5
|
import _appConfig from '#build/app.config'
|
|
6
6
|
import theme from '#build/ui/separator'
|
|
7
|
+
import { tv } from '../utils/tv'
|
|
7
8
|
import type { AvatarProps } from '../types'
|
|
8
9
|
|
|
9
|
-
const
|
|
10
|
+
const appConfigSeparator = _appConfig as AppConfig & { ui: { separator: Partial<typeof theme> } }
|
|
10
11
|
|
|
11
|
-
const separator = tv({ extend: tv(theme), ...(
|
|
12
|
+
const separator = tv({ extend: tv(theme), ...(appConfigSeparator.ui?.separator || {}) })
|
|
12
13
|
|
|
13
14
|
type SeparatorVariants = VariantProps<typeof separator>
|
|
14
15
|
|
|
@@ -43,7 +44,7 @@ export interface SeparatorSlots {
|
|
|
43
44
|
|
|
44
45
|
<script setup lang="ts">
|
|
45
46
|
import { computed } from 'vue'
|
|
46
|
-
import { Separator, useForwardProps } from '
|
|
47
|
+
import { Separator, useForwardProps } from 'reka-ui'
|
|
47
48
|
import { reactivePick } from '@vueuse/core'
|
|
48
49
|
import UIcon from './Icon.vue'
|
|
49
50
|
import UAvatar from './Avatar.vue'
|
|
@@ -1,13 +1,12 @@
|
|
|
1
1
|
<script lang="ts">
|
|
2
|
-
import { tv } from 'tailwind-variants'
|
|
3
2
|
import type { AppConfig } from '@nuxt/schema'
|
|
4
3
|
import _appConfig from '#build/app.config'
|
|
5
4
|
import theme from '#build/ui/skeleton'
|
|
6
|
-
import {
|
|
5
|
+
import { tv } from '../utils/tv'
|
|
7
6
|
|
|
8
|
-
const
|
|
7
|
+
const appConfigSkeleton = _appConfig as AppConfig & { ui: { skeleton: Partial<typeof theme> } }
|
|
9
8
|
|
|
10
|
-
const skeleton = tv({ extend: tv(theme), ...(
|
|
9
|
+
const skeleton = tv({ extend: tv(theme), ...(appConfigSkeleton.ui?.skeleton || {}) })
|
|
11
10
|
|
|
12
11
|
export interface SkeletonProps {
|
|
13
12
|
/**
|
|
@@ -17,12 +16,10 @@ export interface SkeletonProps {
|
|
|
17
16
|
as?: any
|
|
18
17
|
class?: any
|
|
19
18
|
}
|
|
20
|
-
|
|
21
|
-
extendDevtoolsMeta({ example: 'SkeletonExample' })
|
|
22
19
|
</script>
|
|
23
20
|
|
|
24
21
|
<script setup lang="ts">
|
|
25
|
-
import { Primitive } from '
|
|
22
|
+
import { Primitive } from 'reka-ui'
|
|
26
23
|
|
|
27
24
|
const props = defineProps<SkeletonProps>()
|
|
28
25
|
</script>
|