Skip to content

Commit 70cf05f

Browse files
feat(components): handle description in items (#5193)
Co-authored-by: Benjamin Canac <canacb1@gmail.com>
1 parent 309e618 commit 70cf05f

40 files changed

+8031
-2613
lines changed

playgrounds/nuxt/app/pages/components/command-palette.vue

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,14 @@ const groups = computed(() => [{
7575
toast.add({ title: 'Label added!' })
7676
},
7777
kbds: ['meta', 'L']
78+
}, {
79+
label: 'Add label',
80+
description: 'Add a label to the current item.',
81+
icon: 'i-lucide-tag',
82+
onSelect(e: Event) {
83+
e.preventDefault()
84+
},
85+
kbds: ['meta', 'L']
7886
}, {
7987
label: 'More actions',
8088
placeholder: 'Search actions...',

playgrounds/nuxt/app/pages/components/context-menu.vue

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ const items = computed(() => [
1313
}],
1414
[{
1515
label: 'Appearance',
16+
description: 'Change the appearance of the app',
1617
children: [{
1718
label: 'System',
1819
icon: 'i-lucide-monitor'
@@ -62,6 +63,7 @@ const items = computed(() => [
6263
label: 'Developer',
6364
children: [[{
6465
label: 'View Source',
66+
description: 'View the source code of the app',
6567
kbds: ['option', 'meta', 'U'],
6668
onSelect() {
6769
console.log('View Source clicked')

playgrounds/nuxt/app/pages/components/dropdown-menu.vue

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ const items = computed(() => [
1313
}],
1414
[{
1515
label: 'Profile',
16+
description: 'View your profile',
1617
icon: 'i-lucide-user',
1718
slot: 'custom' as const,
1819
onSelect(e: Event) {
@@ -21,6 +22,7 @@ const items = computed(() => [
2122
}
2223
}, {
2324
label: 'Billing',
25+
description: 'Manage billing',
2426
icon: 'i-lucide-credit-card',
2527
kbds: ['meta', 'b'],
2628
onSelect() {
@@ -52,6 +54,7 @@ const items = computed(() => [
5254
}
5355
}], [{
5456
label: 'More',
57+
description: 'Import from more sources',
5558
icon: 'i-lucide-circle-plus',
5659
children: [{
5760
label: 'Import from Slack',

playgrounds/nuxt/app/pages/components/input-menu.vue

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,22 +22,27 @@ const items = [[{ label: 'Fruits', type: 'label' as const }, ...fruits], [{ labe
2222
const statuses = [{
2323
label: 'Backlog',
2424
value: 'backlog',
25+
description: 'Issues that have been identified but not yet prioritized',
2526
icon: 'i-lucide-circle-help'
2627
}, {
2728
label: 'Todo',
2829
value: 'todo',
30+
description: 'Issues that are ready to be worked on',
2931
icon: 'i-lucide-circle-plus'
3032
}, {
3133
label: 'In Progress',
3234
value: 'in_progress',
35+
description: 'Issues that are currently being worked on',
3336
icon: 'i-lucide-circle-arrow-up'
3437
}, {
3538
label: 'Done',
3639
value: 'done',
40+
description: 'Issues that have been completed successfully',
3741
icon: 'i-lucide-circle-check'
3842
}, {
3943
label: 'Canceled',
4044
value: 'canceled',
45+
description: 'Issues that have been cancelled or rejected',
4146
icon: 'i-lucide-circle-x'
4247
}] satisfies InputMenuItem[]
4348

playgrounds/nuxt/app/pages/components/select-menu.vue

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,22 +22,27 @@ const items = [[{ label: 'Fruits', type: 'label' }, ...fruits], [{ label: 'Veget
2222
const statuses = [{
2323
label: 'Backlog',
2424
value: 'backlog',
25+
description: 'Issues that have been identified but not yet prioritized',
2526
icon: 'i-lucide-circle-help'
2627
}, {
2728
label: 'Todo',
2829
value: 'todo',
30+
description: 'Issues that are ready to be worked on',
2931
icon: 'i-lucide-circle-plus'
3032
}, {
3133
label: 'In Progress',
3234
value: 'in_progress',
35+
description: 'Issues that are currently being worked on',
3336
icon: 'i-lucide-circle-arrow-up'
3437
}, {
3538
label: 'Done',
3639
value: 'done',
40+
description: 'Issues that have been completed successfully',
3741
icon: 'i-lucide-circle-check'
3842
}, {
3943
label: 'Canceled',
4044
value: 'canceled',
45+
description: 'Issues that have been cancelled or rejected',
4146
icon: 'i-lucide-circle-x'
4247
}] satisfies SelectMenuItem[]
4348

playgrounds/nuxt/app/pages/components/select.vue

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,22 +21,27 @@ const items = [[{ label: 'Fruits', type: 'label' as const }, ...fruits], [{ labe
2121
const statuses = [{
2222
label: 'Backlog',
2323
value: 'backlog',
24+
description: 'Issues that have been identified but not yet prioritized',
2425
icon: 'i-lucide-circle-help'
2526
}, {
2627
label: 'Todo',
2728
value: 'todo',
29+
description: 'Issues that are ready to be worked on',
2830
icon: 'i-lucide-circle-plus'
2931
}, {
3032
label: 'In Progress',
3133
value: 'in_progress',
34+
description: 'Issues that are currently being worked on',
3235
icon: 'i-lucide-circle-arrow-up'
3336
}, {
3437
label: 'Done',
3538
value: 'done',
39+
description: 'Issues that have been completed successfully',
3640
icon: 'i-lucide-circle-check'
3741
}, {
3842
label: 'Canceled',
3943
value: 'canceled',
44+
description: 'Issues that have been cancelled or rejected',
4045
icon: 'i-lucide-circle-x'
4146
}] satisfies SelectItem[]
4247

src/runtime/components/CommandPalette.vue

Lines changed: 23 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ export interface CommandPaletteItem extends Omit<LinkProps, 'type' | 'raw' | 'cu
1616
prefix?: string
1717
label?: string
1818
suffix?: string
19+
description?: string
1920
/**
2021
* @IconifyIcon
2122
*/
@@ -34,7 +35,7 @@ export interface CommandPaletteItem extends Omit<LinkProps, 'type' | 'raw' | 'cu
3435
children?: CommandPaletteItem[]
3536
onSelect?: (e: Event) => void
3637
class?: any
37-
ui?: Pick<CommandPalette['slots'], 'item' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemLeadingChipSize' | 'itemLeadingChip' | 'itemLabel' | 'itemLabelPrefix' | 'itemLabelBase' | 'itemLabelSuffix' | 'itemTrailing' | 'itemTrailingKbds' | 'itemTrailingKbdsSize' | 'itemTrailingHighlightedIcon' | 'itemTrailingIcon'>
38+
ui?: Pick<CommandPalette['slots'], 'item' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemLeadingChipSize' | 'itemLeadingChip' | 'itemWrapper' | 'itemLabel' | 'itemDescription' | 'itemLabelPrefix' | 'itemLabelBase' | 'itemLabelSuffix' | 'itemTrailing' | 'itemTrailingKbds' | 'itemTrailingKbdsSize' | 'itemTrailingHighlightedIcon' | 'itemTrailingIcon'>
3839
[key: string]: any
3940
}
4041
@@ -153,6 +154,11 @@ export interface CommandPaletteProps<G extends CommandPaletteGroup<T> = CommandP
153154
* @defaultValue 'label'
154155
*/
155156
labelKey?: GetItemKeys<T>
157+
/**
158+
* The key used to get the description from the item.
159+
* @defaultValue 'description'
160+
*/
161+
descriptionKey?: GetItemKeys<T>
156162
class?: any
157163
ui?: CommandPalette['slots']
158164
}
@@ -171,6 +177,7 @@ export type CommandPaletteSlots<G extends CommandPaletteGroup<T> = CommandPalett
171177
'item': SlotProps<T>
172178
'item-leading': SlotProps<T>
173179
'item-label': SlotProps<T>
180+
'item-description': SlotProps<T>
174181
'item-trailing': SlotProps<T>
175182
} & Record<string, SlotProps<G>> & Record<string, SlotProps<T>>
176183
@@ -200,6 +207,7 @@ import UKbd from './Kbd.vue'
200207
const props = withDefaults(defineProps<CommandPaletteProps<G, T>>(), {
201208
modelValue: '',
202209
labelKey: 'label',
210+
descriptionKey: 'description',
203211
autofocus: true,
204212
back: true,
205213
virtualize: false
@@ -393,14 +401,22 @@ function onSelect(e: Event, item: T) {
393401
/>
394402
</slot>
395403

396-
<span v-if="item.labelHtml || get(item, props.labelKey as string) || !!slots[(item.slot ? `${item.slot}-label` : group?.slot ? `${group.slot}-label` : `item-label`) as keyof CommandPaletteSlots<G, T>]" :class="ui.itemLabel({ class: [props.ui?.itemLabel, item.ui?.itemLabel], active: active || item.active })">
397-
<slot :name="((item.slot ? `${item.slot}-label` : group?.slot ? `${group.slot}-label` : `item-label`) as keyof CommandPaletteSlots<G, T>)" :item="(item as any)" :index="index" :ui="ui">
398-
<span v-if="item.prefix" :class="ui.itemLabelPrefix({ class: [props.ui?.itemLabelPrefix, item.ui?.itemLabelPrefix] })">{{ item.prefix }}</span>
404+
<span v-if="(item.prefix || (item.labelHtml || get(item, props.labelKey as string)) || (item.suffixHtml || item.suffix) || !!slots[(item.slot ? `${item.slot}-label` : group?.slot ? `${group.slot}-label` : `item-label`) as keyof CommandPaletteSlots<G, T>]) || (get(item, props.descriptionKey as string) || !!slots[(item.slot ? `${item.slot}-description` : group?.slot ? `${group.slot}-description` : `item-description`) as keyof CommandPaletteSlots<G, T>])" :class="ui.itemWrapper({ class: [props.ui?.itemWrapper, item.ui?.itemWrapper] })">
405+
<span :class="ui.itemLabel({ class: [props.ui?.itemLabel, item.ui?.itemLabel], active: active || item.active })">
406+
<slot :name="((item.slot ? `${item.slot}-label` : group?.slot ? `${group.slot}-label` : `item-label`) as keyof CommandPaletteSlots<G, T>)" :item="(item as any)" :index="index" :ui="ui">
407+
<span v-if="item.prefix" :class="ui.itemLabelPrefix({ class: [props.ui?.itemLabelPrefix, item.ui?.itemLabelPrefix] })">{{ item.prefix }}</span>
399408

400-
<span :class="ui.itemLabelBase({ class: [props.ui?.itemLabelBase, item.ui?.itemLabelBase], active: active || item.active })" v-html="item.labelHtml || get(item, props.labelKey as string)" />
409+
<span :class="ui.itemLabelBase({ class: [props.ui?.itemLabelBase, item.ui?.itemLabelBase], active: active || item.active })" v-html="item.labelHtml || get(item, props.labelKey as string)" />
401410

402-
<span :class="ui.itemLabelSuffix({ class: [props.ui?.itemLabelSuffix, item.ui?.itemLabelSuffix], active: active || item.active })" v-html="item.suffixHtml || item.suffix" />
403-
</slot>
411+
<span :class="ui.itemLabelSuffix({ class: [props.ui?.itemLabelSuffix, item.ui?.itemLabelSuffix], active: active || item.active })" v-html="item.suffixHtml || item.suffix" />
412+
</slot>
413+
</span>
414+
415+
<span v-if="get(item, props.descriptionKey as string)" :class="ui.itemDescription({ class: [props.ui?.itemDescription, item.ui?.itemDescription] })">
416+
<slot :name="((item.slot ? `${item.slot}-description` : group?.slot ? `${group.slot}-description` : `item-description`) as keyof CommandPaletteSlots<G, T>)" :item="(item as any)" :index="index" :ui="ui">
417+
{{ get(item, props.descriptionKey as string) }}
418+
</slot>
419+
</span>
404420
</span>
405421

406422
<span :class="ui.itemTrailing({ class: [props.ui?.itemTrailing, item.ui?.itemTrailing] })">

src/runtime/components/ContextMenu.vue

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ type ContextMenu = ComponentConfig<typeof theme, AppConfig, 'contextMenu'>
1111
1212
export interface ContextMenuItem extends Omit<LinkProps, 'type' | 'raw' | 'custom'> {
1313
label?: string
14+
description?: string
1415
/**
1516
* @IconifyIcon
1617
*/
@@ -34,7 +35,7 @@ export interface ContextMenuItem extends Omit<LinkProps, 'type' | 'raw' | 'custo
3435
onSelect?: (e: Event) => void
3536
onUpdateChecked?: (checked: boolean) => void
3637
class?: any
37-
ui?: Pick<ContextMenu['slots'], 'item' | 'label' | 'separator' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemLabel' | 'itemLabelExternalIcon' | 'itemTrailing' | 'itemTrailingIcon' | 'itemTrailingKbds' | 'itemTrailingKbdsSize'>
38+
ui?: Pick<ContextMenu['slots'], 'item' | 'label' | 'separator' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemWrapper' | 'itemLabel' | 'itemDescription' | 'itemLabelExternalIcon' | 'itemTrailing' | 'itemTrailingIcon' | 'itemTrailingKbds' | 'itemTrailingKbdsSize'>
3839
[key: string]: any
3940
}
4041
@@ -75,6 +76,11 @@ export interface ContextMenuProps<T extends ArrayOrNested<ContextMenuItem> = Arr
7576
* @defaultValue 'label'
7677
*/
7778
labelKey?: GetItemKeys<T>
79+
/**
80+
* The key used to get the description from the item.
81+
* @defaultValue 'description'
82+
*/
83+
descriptionKey?: GetItemKeys<T>
7884
disabled?: boolean
7985
class?: any
8086
ui?: ContextMenu['slots']
@@ -92,11 +98,12 @@ export type ContextMenuSlots<
9298
'item': SlotProps<T>
9399
'item-leading': SlotProps<T>
94100
'item-label': (props: { item: T, active?: boolean, index: number }) => any
101+
'item-description': (props: { item: T, active?: boolean, index: number }) => any
95102
'item-trailing': SlotProps<T>
96103
'content-top': (props?: {}) => any
97104
'content-bottom': (props?: {}) => any
98105
}
99-
& DynamicSlots<MergeTypes<T>, 'label', { active?: boolean, index: number }>
106+
& DynamicSlots<MergeTypes<T>, 'label' | 'description', { active?: boolean, index: number }>
100107
& DynamicSlots<MergeTypes<T>, 'leading' | 'trailing', { active?: boolean, index: number, ui: ContextMenu['ui'] }>
101108
102109
</script>
@@ -114,7 +121,8 @@ const props = withDefaults(defineProps<ContextMenuProps<T>>(), {
114121
portal: true,
115122
modal: true,
116123
externalIcon: true,
117-
labelKey: 'label'
124+
labelKey: 'label',
125+
descriptionKey: 'description'
118126
})
119127
const emits = defineEmits<ContextMenuEmits>()
120128
const slots = defineSlots<ContextMenuSlots<T>>()
@@ -144,6 +152,7 @@ const ui = computed(() => tv({ extend: tv(theme), ...(appConfig.ui?.contextMenu
144152
:items="items"
145153
:portal="portal"
146154
:label-key="(labelKey as keyof NestedItem<T>)"
155+
:description-key="(descriptionKey as keyof NestedItem<T>)"
147156
:checked-icon="checkedIcon"
148157
:loading-icon="loadingIcon"
149158
:external-icon="externalIcon"

src/runtime/components/ContextMenuContent.vue

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ interface ContextMenuContentProps<T extends ArrayOrNested<ContextMenuItem>> exte
1313
portal?: boolean | string | HTMLElement
1414
sub?: boolean
1515
labelKey: GetItemKeys<T>
16+
descriptionKey: GetItemKeys<T>
1617
/**
1718
* @IconifyIcon
1819
*/
@@ -58,7 +59,7 @@ const { dir } = useLocale()
5859
const appConfig = useAppConfig()
5960
6061
const portalProps = usePortal(toRef(() => props.portal))
61-
const contentProps = useForwardPropsEmits(reactiveOmit(props, 'sub', 'items', 'portal', 'labelKey', 'checkedIcon', 'loadingIcon', 'externalIcon', 'class', 'ui', 'uiOverride'), emits)
62+
const contentProps = useForwardPropsEmits(reactiveOmit(props, 'sub', 'items', 'portal', 'labelKey', 'descriptionKey', 'checkedIcon', 'loadingIcon', 'externalIcon', 'class', 'ui', 'uiOverride'), emits)
6263
const getProxySlots = () => omit(slots, ['default'])
6364
6465
const [DefineItemTemplate, ReuseItemTemplate] = createReusableTemplate<{ item: ContextMenuItem, active?: boolean, index: number }>()
@@ -82,12 +83,20 @@ const groups = computed<ContextMenuItem[][]>(() =>
8283
<UAvatar v-else-if="item.avatar" :size="((item.ui?.itemLeadingAvatarSize || uiOverride?.itemLeadingAvatarSize || ui.itemLeadingAvatarSize()) as AvatarProps['size'])" v-bind="item.avatar" :class="ui.itemLeadingAvatar({ class: [uiOverride?.itemLeadingAvatar, item.ui?.itemLeadingAvatar], active })" />
8384
</slot>
8485

85-
<span v-if="get(item, props.labelKey as string) || !!slots[(item.slot ? `${item.slot}-label`: 'item-label') as keyof ContextMenuSlots<T>]" :class="ui.itemLabel({ class: [uiOverride?.itemLabel, item.ui?.itemLabel], active })">
86-
<slot :name="((item.slot ? `${item.slot}-label`: 'item-label') as keyof ContextMenuSlots<T>)" :item="item" :active="active" :index="index">
87-
{{ get(item, props.labelKey as string) }}
88-
</slot>
86+
<span v-if="(get(item, props.labelKey as string) || !!slots[(item.slot ? `${item.slot}-label`: 'item-label') as keyof ContextMenuSlots<T>]) || (get(item, props.descriptionKey as string) || !!slots[(item.slot ? `${item.slot}-description`: 'item-description') as keyof ContextMenuSlots<T>])" :class="ui.itemWrapper({ class: [uiOverride?.itemWrapper, item.ui?.itemWrapper] })">
87+
<span :class="ui.itemLabel({ class: [uiOverride?.itemLabel, item.ui?.itemLabel], active })">
88+
<slot :name="((item.slot ? `${item.slot}-label`: 'item-label') as keyof ContextMenuSlots<T>)" :item="item" :active="active" :index="index">
89+
{{ get(item, props.labelKey as string) }}
90+
</slot>
91+
92+
<UIcon v-if="item.target === '_blank' && externalIcon !== false" :name="typeof externalIcon === 'string' ? externalIcon : appConfig.ui.icons.external" :class="ui.itemLabelExternalIcon({ class: [uiOverride?.itemLabelExternalIcon, item.ui?.itemLabelExternalIcon], color: item?.color, active })" />
93+
</span>
8994

90-
<UIcon v-if="item.target === '_blank' && externalIcon !== false" :name="typeof externalIcon === 'string' ? externalIcon : appConfig.ui.icons.external" :class="ui.itemLabelExternalIcon({ class: [uiOverride?.itemLabelExternalIcon, item.ui?.itemLabelExternalIcon], color: item?.color, active })" />
95+
<span v-if="get(item, props.descriptionKey as string)" :class="ui.itemDescription({ class: [uiOverride?.itemDescription, item.ui?.itemDescription] })">
96+
<slot :name="((item.slot ? `${item.slot}-description`: 'item-description') as keyof ContextMenuSlots<T>)" :item="item" :active="active" :index="index">
97+
{{ get(item, props.descriptionKey as string) }}
98+
</slot>
99+
</span>
91100
</span>
92101

93102
<span :class="ui.itemTrailing({ class: [uiOverride?.itemTrailing, item.ui?.itemTrailing] })">
@@ -136,6 +145,7 @@ const groups = computed<ContextMenuItem[][]>(() =>
136145
:items="(item.children as T)"
137146
:align-offset="-4"
138147
:label-key="labelKey"
148+
:description-key="descriptionKey"
139149
:checked-icon="checkedIcon"
140150
:loading-icon="loadingIcon"
141151
:external-icon="externalIcon"

src/runtime/components/DropdownMenu.vue

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ type DropdownMenu = ComponentConfig<typeof theme, AppConfig, 'dropdownMenu'>
1111
1212
export interface DropdownMenuItem extends Omit<LinkProps, 'type' | 'raw' | 'custom'> {
1313
label?: string
14+
description?: string
1415
/**
1516
* @IconifyIcon
1617
*/
@@ -34,7 +35,7 @@ export interface DropdownMenuItem extends Omit<LinkProps, 'type' | 'raw' | 'cust
3435
onSelect?: (e: Event) => void
3536
onUpdateChecked?: (checked: boolean) => void
3637
class?: any
37-
ui?: Pick<DropdownMenu['slots'], 'item' | 'label' | 'separator' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemLabel' | 'itemLabelExternalIcon' | 'itemTrailing' | 'itemTrailingIcon' | 'itemTrailingKbds' | 'itemTrailingKbdsSize'>
38+
ui?: Pick<DropdownMenu['slots'], 'item' | 'label' | 'separator' | 'itemLeadingIcon' | 'itemLeadingAvatarSize' | 'itemLeadingAvatar' | 'itemWrapper' | 'itemLabel' | 'itemDescription' | 'itemLabelExternalIcon' | 'itemTrailing' | 'itemTrailingIcon' | 'itemTrailingKbds' | 'itemTrailingKbdsSize'>
3839
[key: string]: any
3940
}
4041
@@ -83,6 +84,11 @@ export interface DropdownMenuProps<T extends ArrayOrNested<DropdownMenuItem> = A
8384
* @defaultValue 'label'
8485
*/
8586
labelKey?: GetItemKeys<T>
87+
/**
88+
* The key used to get the description from the item.
89+
* @defaultValue 'description'
90+
*/
91+
descriptionKey?: GetItemKeys<T>
8692
disabled?: boolean
8793
class?: any
8894
ui?: DropdownMenu['slots']
@@ -100,11 +106,12 @@ export type DropdownMenuSlots<
100106
'item': SlotProps<T>
101107
'item-leading': SlotProps<T>
102108
'item-label': (props: { item: T, active?: boolean, index: number }) => any
109+
'item-description': (props: { item: T, active?: boolean, index: number }) => any
103110
'item-trailing': SlotProps<T>
104111
'content-top': (props?: {}) => any
105112
'content-bottom': (props?: {}) => any
106113
}
107-
& DynamicSlots<MergeTypes<T>, 'label', { active?: boolean, index: number }>
114+
& DynamicSlots<MergeTypes<T>, 'label' | 'description', { active?: boolean, index: number }>
108115
& DynamicSlots<MergeTypes<T>, 'leading' | 'trailing', { active?: boolean, index: number, ui: DropdownMenu['ui'] }>
109116
110117
</script>
@@ -123,7 +130,8 @@ const props = withDefaults(defineProps<DropdownMenuProps<T>>(), {
123130
portal: true,
124131
modal: true,
125132
externalIcon: true,
126-
labelKey: 'label'
133+
labelKey: 'label',
134+
descriptionKey: 'description'
127135
})
128136
const emits = defineEmits<DropdownMenuEmits>()
129137
const slots = defineSlots<DropdownMenuSlots<T>>()
@@ -154,6 +162,7 @@ const ui = computed(() => tv({ extend: tv(theme), ...(appConfig.ui?.dropdownMenu
154162
:items="items"
155163
:portal="portal"
156164
:label-key="(labelKey as keyof NestedItem<T>)"
165+
:description-key="(descriptionKey as keyof NestedItem<T>)"
157166
:checked-icon="checkedIcon"
158167
:loading-icon="loadingIcon"
159168
:external-icon="externalIcon"

0 commit comments

Comments
 (0)