Menu 導覽選單
頁面導覽元件。支援水平 / 垂直版面配置、巢狀子選單、摺疊態、手風琴,鍵盤對齊 APG menu pattern。
垂直版面配置(內嵌子選單)
垂直內嵌模式支援鍵盤遍歷:展開子選單後 ↑/↓ 可跨「葉項 ↔ 子選單標題 ↔ 面板內項」邊界移動(Home/End 跳首末),停用項與收起面板內的項自動跳過。
垂直版面配置
- 首頁
- 設定▾
- 基本設定
- 安全設定
- 停用項
vue
<script setup>
import { ref } from 'vue'
const active = ref('home')
const active2 = ref('settings2-basic')
</script>
<template>
<!-- 垂直版面配置 -->
<LhMenu v-model="active">
<LhMenuItem index="home">首页</LhMenuItem>
<LhSubMenu index="settings" title="设置">
<LhMenuItem index="settings-basic">基本设置</LhMenuItem>
<LhMenuItem index="settings-security">安全设置</LhMenuItem>
</LhSubMenu>
<LhMenuItem index="docs" disabled>禁用项</LhMenuItem>
</LhMenu>
</template>vue
<script>
export default {
data() {
return {
active: 'home',
active2: 'settings2-basic',
}
},
}
</script>
<template>
<!-- 垂直版面配置 -->
<LhMenu v-model="active">
<LhMenuItem index="home">首页</LhMenuItem>
<LhSubMenu index="settings" title="设置">
<LhMenuItem index="settings-basic">基本设置</LhMenuItem>
<LhMenuItem index="settings-security">安全设置</LhMenuItem>
</LhSubMenu>
<LhMenuItem index="docs" disabled>禁用项</LhMenuItem>
</LhMenu>
</template>展開控制
default-openeds 初始展開的子選單;openeds(配合 v-model:openeds)受控展開集合;unique-opened 同時只展開一個子選單。LhSubMenu 也支援 disabled 整體停用。
展開控制
- 設定(預設展開)▾
- 基本設定
- 安全設定
- 管理(停用)▾
- 使用者管理
- 關於
vue
<script setup>
import { ref } from 'vue'
const active2 = ref('settings2-basic')
</script>
<template>
<!-- 展開控制 -->
<LhMenu
v-model="active2"
:default-openeds="['settings2']"
unique-opened
style="max-width: 240px"
>
<LhSubMenu index="settings2" title="设置(默认展开)">
<LhMenuItem index="settings2-basic">基本设置</LhMenuItem>
<LhMenuItem index="settings2-security">安全设置</LhMenuItem>
</LhSubMenu>
<LhSubMenu index="manage" title="管理(禁用)" disabled>
<LhMenuItem index="manage-users">用户管理</LhMenuItem>
</LhSubMenu>
<LhMenuItem index="about2">关于</LhMenuItem>
</LhMenu>
</template>vue
<script>
export default {
data() {
return { active2: 'settings2-basic' }
},
}
</script>
<template>
<!-- 展開控制 -->
<LhMenu
v-model="active2"
:default-openeds="['settings2']"
unique-opened
style="max-width: 240px"
>
<LhSubMenu index="settings2" title="设置(默认展开)">
<LhMenuItem index="settings2-basic">基本设置</LhMenuItem>
<LhMenuItem index="settings2-security">安全设置</LhMenuItem>
</LhSubMenu>
<LhSubMenu index="manage" title="管理(禁用)" disabled>
<LhMenuItem index="manage-users">用户管理</LhMenuItem>
</LhSubMenu>
<LhMenuItem index="about2">关于</LhMenuItem>
</LhMenu>
</template>受控展開集合
- 設定▾
- 基本設定
vue
<script setup lang="ts">
import { ref } from 'vue'
const active2 = ref('settings2-basic')
</script>
<template>
<!-- 受控展開集合 -->
<LhMenu v-model="active2" :openeds="['settings2']">
<LhSubMenu index="settings2" title="设置">
<LhMenuItem index="settings2-basic">基本设置</LhMenuItem>
</LhSubMenu>
</LhMenu>
</template>vue
<script>
export default {
data() {
return { active2: 'settings2-basic' }
},
}
</script>
<template>
<!-- 受控展開集合 -->
<LhMenu v-model="active2" :openeds="['settings2']">
<LhSubMenu index="settings2" title="设置">
<LhMenuItem index="settings2-basic">基本设置</LhMenuItem>
</LhSubMenu>
</LhMenu>
</template>水平版面配置(飛出子選單)
水平版面配置
- 首頁
- 設定▾
vue
<script setup lang="ts">
import { ref } from 'vue'
const active = ref('home')
</script>
<template>
<!-- 水平版面配置 -->
<LhMenu v-model="active" mode="horizontal">
<LhMenuItem index="home">首页</LhMenuItem>
<LhSubMenu index="settings" title="设置">
<LhMenuItem index="settings-basic">基本设置</LhMenuItem>
</LhSubMenu>
</LhMenu>
</template>vue
<script>
export default {
data() {
return { active: 'home' }
},
}
</script>
<template>
<!-- 水平版面配置 -->
<LhMenu v-model="active" mode="horizontal">
<LhMenuItem index="home">首页</LhMenuItem>
<LhSubMenu index="settings" title="设置">
<LhMenuItem index="settings-basic">基本设置</LhMenuItem>
</LhSubMenu>
</LhMenu>
</template>摺疊態與分組
摺疊 + 分組
- 內容
- 首頁
vue
<script setup lang="ts">
import { ref } from 'vue'
const active = ref('home')
</script>
<template>
<!-- 摺疊 + 分組 -->
<LhMenu v-model="active" collapse>
<LhMenuItemGroup title="内容">
<LhMenuItem index="home">首页</LhMenuItem>
</LhMenuItemGroup>
</LhMenu>
</template>vue
<script>
export default {
data() {
return { active: 'home' }
},
}
</script>
<template>
<!-- 摺疊 + 分組 -->
<LhMenu v-model="active" collapse>
<LhMenuItemGroup title="内容">
<LhMenuItem index="home">首页</LhMenuItem>
</LhMenuItemGroup>
</LhMenu>
</template>API
LhMenu Props
| 屬性名 | 說明 | 類型 | 預設值 |
|---|---|---|---|
| modelValue | 目前啟動項(受控 v-model;未傳時內部維護) | string | — |
| mode | 版面配置模式 | "horizontal" | "vertical" | 'vertical' |
| collapse | 垂直模式摺疊為圖示列(子選單改為飛出面板) | boolean | false |
| defaultOpeneds | 預設展開的子選單鍵(非受控) | string[] | () => [] |
| openeds | 受控展開的子選單鍵 | string[] | — |
| uniqueOpened | 手風琴:同時只展開一個子選單 | boolean | false |
| sx | sx 快速版面配置屬性 | LhSxProps | — |
Events
| 事件名 | 說明 | 回呼參數 |
|---|---|---|
| update:modelValue | 啟動項變化時觸發(v-model) | (value: string) |
| update:openeds | 展開的子選單集合變化時觸發(v-model:openeds) | (value: string[]) |
| select | 選單項被選中時觸發 | (index: string, indexPath: string[]) |
| open | 子選單展開時觸發 | (index: string, indexPath: string[]) |
| close | 子選單收起時觸發 | (index: string, indexPath: string[]) |
LhMenuItem Props
| 屬性名 | 說明 | 類型 | 預設值 |
|---|---|---|---|
| index | 唯一標識(必填) | string | — |
| disabled | 停用 | boolean | false |
| sx | sx 快速版面配置屬性 | LhSxProps | — |
事件:click(index);插槽:default。
LhSubMenu Props
| 屬性名 | 說明 | 類型 | 預設值 |
|---|---|---|---|
| index | 唯一標識(必填) | string | — |
| title | 標題(也可用 title 插槽) | string | — |
| disabled | 停用 | boolean | false |
| sx | sx 快速版面配置屬性 | LhSxProps | — |
事件:select(index, indexPath)(冒泡);插槽:title、default(可再巢狀 LhSubMenu)。
LhMenuItemGroup Props
| 屬性名 | 說明 | 類型 | 預設值 |
|---|---|---|---|
| title | 分組標題(也可用 title 插槽) | string | — |
| sx | sx 快速版面配置屬性 | LhSxProps | — |
插槽:title、default。
無障礙
- 水平為
role="menubar"、垂直為role="menu";項為role="menuitem"、分組為role="group"(容器role="presentation") - 子選單標題
aria-haspopup+aria-expanded+aria-controls關聯面板 - 鍵盤:Enter/Space/→ 展開並聚焦首項、← 收起、Esc 關閉;垂直內嵌模式 ↑/↓/Home/End 在可見項(葉項、子選單標題與已展開面板內項)間跨邊界遍歷並循環,停用項與收起面板內的項自動跳過
- 內嵌展開高度用 CSS
grid-template-rows: 0fr/1fr(零 JS 測高);飛出面板由 popper 引擎定位(flip/shift/視區外收起)
類型定義
本元件對外匯出的 TypeScript 類型結構如下(自動提取自 packages/components/menu/src/types.ts 與 @lh-ui/share/core/* 原始碼,點選各條目展開檢視完整定義;屬性說明見上方 Props 表):
LhMenuProps
ts
/** 選單 props */
export interface LhMenuProps {
/** 目前啟動項(受控 v-model;未傳時元件內部維護) */
modelValue?: string
/** 版面配置模式 */
mode?: LhMenuMode
/** 垂直模式摺疊為圖示列(子選單改為飛出面板) */
collapse?: boolean
/** 預設展開的子選單鍵(非受控) */
defaultOpeneds?: string[]
/** 受控展開的子選單鍵 */
openeds?: string[]
/** 手風琴:同時只展開一個子選單 */
uniqueOpened?: boolean
/** sx 快速版面配置屬性 */
sx?: LhSxProps
}LhMenuItemProps
ts
/** 葉項 props */
export interface LhMenuItemProps {
/** 唯一標識(必填) */
index: string
disabled?: boolean
/** sx 快速版面配置屬性 */
sx?: LhSxProps
}LhSubMenuProps
ts
/** 子選單 props(可遞迴巢狀) */
export interface LhSubMenuProps {
/** 唯一標識(必填) */
index: string
/** 標題(也可用 title 插槽) */
title?: string
disabled?: boolean
/** sx 快速版面配置屬性 */
sx?: LhSxProps
}LhMenuItemGroupProps
ts
/** 分組 props */
export interface LhMenuItemGroupProps {
/** 分組標題(也可用 title 插槽) */
title?: string
/** sx 快速版面配置屬性 */
sx?: LhSxProps
}LhMenuMode (來自 @lh-ui/share/core/menu)
ts
/** 選單版面配置模式 */
export type LhMenuMode = 'horizontal' | 'vertical'