mirror of
https://github.com/nuxt/ui.git
synced 2026-09-14 19:51:10 +08:00
213 lines
4.8 KiB
Vue
213 lines
4.8 KiB
Vue
<script setup lang="ts">
|
|
import type { DropdownMenuItem, NavigationMenuItem } from '@nuxt/ui'
|
|
|
|
const open = ref(true)
|
|
|
|
const colorMode = useColorMode()
|
|
|
|
const teams = ref([{
|
|
label: 'Nuxt',
|
|
avatar: {
|
|
src: 'https://github.com/nuxt.png',
|
|
alt: 'Nuxt'
|
|
}
|
|
}, {
|
|
label: 'Vue',
|
|
avatar: {
|
|
src: 'https://github.com/vuejs.png',
|
|
alt: 'Vue'
|
|
}
|
|
}, {
|
|
label: 'UnJS',
|
|
avatar: {
|
|
src: 'https://github.com/unjs.png',
|
|
alt: 'UnJS'
|
|
}
|
|
}])
|
|
const selectedTeam = ref(teams.value[0])
|
|
|
|
const teamsItems = computed<DropdownMenuItem[][]>(() => {
|
|
return [teams.value.map((team, index) => ({
|
|
...team,
|
|
kbds: ['meta', String(index + 1)],
|
|
onSelect() {
|
|
selectedTeam.value = team
|
|
}
|
|
})), [{
|
|
label: 'Create team',
|
|
icon: 'i-lucide-circle-plus'
|
|
}]]
|
|
})
|
|
|
|
function getItems(state: 'collapsed' | 'expanded') {
|
|
return [{
|
|
label: 'Inbox',
|
|
icon: 'i-lucide-inbox',
|
|
badge: '4'
|
|
}, {
|
|
label: 'Issues',
|
|
icon: 'i-lucide-square-dot'
|
|
}, {
|
|
label: 'Activity',
|
|
icon: 'i-lucide-square-activity'
|
|
}, {
|
|
label: 'Settings',
|
|
icon: 'i-lucide-settings',
|
|
defaultOpen: true,
|
|
children: state === 'expanded'
|
|
? [{
|
|
label: 'General',
|
|
icon: 'i-lucide-house'
|
|
}, {
|
|
label: 'Team',
|
|
icon: 'i-lucide-users'
|
|
}, {
|
|
label: 'Billing',
|
|
icon: 'i-lucide-credit-card'
|
|
}]
|
|
: []
|
|
}] satisfies NavigationMenuItem[]
|
|
}
|
|
|
|
const user = ref({
|
|
name: 'Benjamin Canac',
|
|
avatar: {
|
|
src: 'https://github.com/benjamincanac.png',
|
|
alt: 'Benjamin Canac'
|
|
}
|
|
})
|
|
|
|
const userItems = computed<DropdownMenuItem[][]>(() => ([[{
|
|
label: 'Profile',
|
|
icon: 'i-lucide-user'
|
|
}, {
|
|
label: 'Billing',
|
|
icon: 'i-lucide-credit-card'
|
|
}, {
|
|
label: 'Settings',
|
|
icon: 'i-lucide-settings',
|
|
to: '/settings'
|
|
}], [{
|
|
label: 'Appearance',
|
|
icon: 'i-lucide-sun-moon',
|
|
children: [{
|
|
label: 'Light',
|
|
icon: 'i-lucide-sun',
|
|
type: 'checkbox',
|
|
checked: colorMode.value === 'light',
|
|
onUpdateChecked(checked: boolean) {
|
|
if (checked) {
|
|
colorMode.preference = 'light'
|
|
}
|
|
},
|
|
onSelect(e: Event) {
|
|
e.preventDefault()
|
|
}
|
|
}, {
|
|
label: 'Dark',
|
|
icon: 'i-lucide-moon',
|
|
type: 'checkbox',
|
|
checked: colorMode.value === 'dark',
|
|
onUpdateChecked(checked: boolean) {
|
|
if (checked) {
|
|
colorMode.preference = 'dark'
|
|
}
|
|
},
|
|
onSelect(e: Event) {
|
|
e.preventDefault()
|
|
}
|
|
}]
|
|
}], [{
|
|
label: 'GitHub',
|
|
icon: 'i-simple-icons-github',
|
|
to: 'https://github.com/nuxt/ui',
|
|
target: '_blank'
|
|
}, {
|
|
label: 'Log out',
|
|
icon: 'i-lucide-log-out'
|
|
}]]))
|
|
|
|
defineShortcuts(extractShortcuts(teamsItems.value))
|
|
</script>
|
|
|
|
<template>
|
|
<div class="flex flex-1">
|
|
<USidebar
|
|
v-model:open="open"
|
|
collapsible="icon"
|
|
rail
|
|
:ui="{
|
|
container: 'h-full',
|
|
inner: 'bg-elevated/25 divide-transparent',
|
|
body: 'py-0'
|
|
}"
|
|
>
|
|
<template #header>
|
|
<UDropdownMenu
|
|
:items="teamsItems"
|
|
:content="{ align: 'start', collisionPadding: 12 }"
|
|
:ui="{ content: 'w-(--reka-dropdown-menu-trigger-width) min-w-48' }"
|
|
>
|
|
<UButton
|
|
v-bind="selectedTeam"
|
|
trailing-icon="i-lucide-chevrons-up-down"
|
|
color="neutral"
|
|
variant="ghost"
|
|
square
|
|
class="w-full data-[state=open]:bg-elevated overflow-hidden"
|
|
:ui="{
|
|
trailingIcon: 'text-dimmed ms-auto'
|
|
}"
|
|
/>
|
|
</UDropdownMenu>
|
|
</template>
|
|
|
|
<template #default="{ state }">
|
|
<UNavigationMenu
|
|
:key="state"
|
|
:items="getItems(state)"
|
|
orientation="vertical"
|
|
:ui="{ link: 'p-1.5 overflow-hidden' }"
|
|
/>
|
|
</template>
|
|
|
|
<template #footer>
|
|
<UDropdownMenu
|
|
:items="userItems"
|
|
:content="{ align: 'center', collisionPadding: 12 }"
|
|
:ui="{ content: 'w-(--reka-dropdown-menu-trigger-width) min-w-48' }"
|
|
>
|
|
<UButton
|
|
v-bind="user"
|
|
:label="user?.name"
|
|
trailing-icon="i-lucide-chevrons-up-down"
|
|
color="neutral"
|
|
variant="ghost"
|
|
square
|
|
class="w-full data-[state=open]:bg-elevated overflow-hidden"
|
|
:ui="{
|
|
trailingIcon: 'text-dimmed ms-auto'
|
|
}"
|
|
/>
|
|
</UDropdownMenu>
|
|
</template>
|
|
</USidebar>
|
|
|
|
<div class="flex-1 flex flex-col">
|
|
<div class="h-(--ui-header-height) shrink-0 flex items-center px-4 border-b border-default">
|
|
<UButton
|
|
icon="i-lucide-panel-left"
|
|
color="neutral"
|
|
variant="ghost"
|
|
aria-label="Toggle sidebar"
|
|
@click="open = !open"
|
|
/>
|
|
</div>
|
|
|
|
<div class="flex-1 p-4">
|
|
<Placeholder class="size-full" />
|
|
</div>
|
|
</div>
|
|
</div>
|
|
</template>
|