Appearance
BizTabsNav 多标签页导航
中后台主框架的页签栏(Chrome 页签形态):激活项白底浮起、关闭 / 批量关闭(当前 / 其他 / 左侧 / 右侧 / 全部,affix 固定项保留)、右键菜单(重新加载 / 关闭系全量,menus 可裁剪)、before-close 异步关闭拦截(脏检查)、原生拖拽排序、超出横向滚动 + 滚轮平移。
本组件由 BizTabsNav(纯页签条 UI:Chrome 页签视觉 / 拖拽 / 溢出滚动)与 BizPageTabs(多页签管理语义:affix 固定 / beforeClose 拦截 / menus 裁剪)合并升级而来,是中后台多标签页导航的唯一组件。原
refresh事件更名为reload,原BizPageTabs的 exposeclose(key)更名为closeTab(key),其余能力全部保留。
组件只负责页签栏本身,不接管路由与页面缓存:tabs 列表由父级维护(v-model:tabs 双向同步),与 <router-view> + <keep-alive> 配合即可组成多页签主框架(见下方 结合 BizLayout)。
基础用法
工作台
工单中心
订单详情 #1001
当前页:工作台
关闭自动激活相邻页签
工作台
用户管理
工单 #01
工单 #02
工单 #03
当前激活:工单 #02
关闭「工单 #02」后自动激活右邻「工单 #03」;关闭最右侧的「工单 #03」则回退左邻; 全部关完只剩固定项时激活「工作台」。也可直接点页签上的关闭按钮验证。
固定页签(affix)
首页
待办事项
通知公告
审批中心
「首页」由 affix-keys 声明为固定页签(显示圆点标记、无关闭按钮): 关闭当前 / 其他 / 左侧 / 右侧 / 全部均不会关掉它,关闭全部后自动激活首页。 当前固定项:(无)
右键菜单全量与裁剪
在任意页签上点击鼠标右键:固定项「首页」的关闭类菜单为置灰禁用
首页
数据看板
工单中心
用户管理
系统设置
menus 裁剪版(仅「重新加载 / 关闭当前」):
首页
数据看板
工单中心
关闭拦截(脏检查)
首页
商品编辑(草稿)
公告编辑(草稿)
操作日志
拖拽排序
首页
用户管理
工单中心
数据看板
系统设置
按住页签左右拖动即可调整顺序(拖动半透明、落点显示蓝色指示线);排序结果回写
当前顺序:首页 → 用户管理 → 工单中心 → 数据看板 → 系统设置
v-model:tabs 并外抛 sort 事件。当前顺序:首页 → 用户管理 → 工单中心 → 数据看板 → 系统设置
事件日志
首页
数据看板
工单中心
- 切换 / 关闭 / 右键重新加载 / 拖拽排序,事件日志在此显示
页签图标
数据看板
工单中心
通知公告
操作手册
字体图标页签
无图标页签
全局不可关闭
经营总览(常驻)
临时分析页 1
临时分析页 2
临时分析页 3
全局
closable=false 关闭按钮全部隐藏;仅单项声明 closable: true 的临时分析页放行(悬停可见关闭按钮)。 溢出横向滚动
监控点-01
监控点-02
监控点-03
监控点-04
监控点-05
监控点-06
监控点-07
监控点-08
监控点-09
监控点-10
监控点-11
监控点-12
监控点-13
监控点-14
监控点-15
监控点-16
监控点-17
监控点-18
页签超出宽度后自动横向滚动:在页签栏上滚动鼠标滚轮平移; 激活变化时该页签自动滚入视口(点击「跳到最后一个」体验); 右键可「关闭右侧 / 关闭其他」批量清理。 当前 18 个页签,激活:point-1
keep-alive 与重新加载
工单录入
公告草稿箱
审核备注
「工单录入」的输入(切走再切回内容保留;右键「重新加载」后清空重建):
结合 BizLayout 的多页签框架
首页
首页
菜单开页签、页签切换联动菜单高亮;右键「重新加载」或点击右上按钮换 :key 重建本区域。 keep-alive 由业务路由层承载(<router-view> + <keep-alive :include>)。
与路由集成(模式参考)
ts
// 主框架内监听路由维护页签列表(组件不绑定路由,模式任选)
const tabs = ref<BizTabsNavItem[]>([{ key: '/home', title: '首页', affix: true, closable: false }])
const active = ref(route.fullPath)
watch(
() => route.fullPath,
(path) => {
active.value = path
if (!tabs.value.some((t) => t.key === path)) {
tabs.value = [...tabs.value, { key: path, title: (route.meta.title ?? path) as string }]
}
},
{ immediate: true }
)vue
<!-- keep-alive 缓存已打开页面;reload 戳用于右键「重新加载」强制重建 -->
<BizTabsNav v-model="active" v-model:tabs="tabs" @reload="(key) => (reloadStamp = Date.now())" />
<router-view v-slot="{ Component }">
<keep-alive>
<component :is="Component" :key="`${route.fullPath}-${reloadStamp}`" />
</keep-alive>
</router-view>Props
| 属性名 | 类型 | 默认值 | 说明 |
|---|---|---|---|
| model-value / v-model | string | number | — | 当前激活页签 key |
| tabs | BizTabsNavItem[] | [] | 页签列表(建议 v-model:tabs 双向绑定) |
| affix-keys | Array<string | number> | [] | 固定页签 key 集合(如首页),等价于在 item 上写 affix: true |
| closable | boolean | true | 全局默认可关闭(单项可被 item.closable 覆盖;affix 恒不可关) |
| context-menu | boolean | true | 右键菜单开关 |
| menus | BizTabsNavMenuAction[] | 全量六项 | 右键菜单启用项裁剪:reload / close / close-others / close-left / close-right / close-all |
| draggable | boolean | false | 页签拖拽排序(原生 DnD,零依赖) |
| before-close | (key, tab) => boolean | Promise<boolean> | — | 关闭前拦截(脏检查):返回 false 或 Promise<false> 取消关闭;单个与批量关闭均逐项询问 |
其余属性经
v-bind="$attrs"透传根节点。
BizTabsNavItem
| 字段 | 类型 | 说明 |
|---|---|---|
| key | string | number | 唯一标识(路由场景传 fullPath / name) |
| title | string | 页签标题(超出 220px 省略,悬浮 title 全显) |
| icon | Component | string | 图标组件或字体 class 字符串(iconfont) |
| affix | boolean | 固定页签:不显示关闭按钮(显示圆点标记),批量关闭时保留 |
| closable | boolean | 单项可关闭覆盖(优先于全局 closable) |
Events
| 事件名 | 参数 | 说明 |
|---|---|---|
| update:model-value | (key) | 激活页签变化(列表清空时为 undefined) |
| update:tabs | (tabs) | 列表变化(关闭 / 批量关闭 / 排序后回写,v-model:tabs 自动接收) |
| change | (key, tab) | 页签被激活(含关闭后自动切换相邻页签) |
| tab-click | (key, tab) | 页签被点击(点击已激活项也触发) |
| close | (key, tab) | 单个页签被关闭(批量关闭只回写列表,不逐项触发) |
| close-all | (tabs) | 「关闭全部」完成,参数为剩余列表(固定项) |
| reload | (key, tab) | 右键「重新加载」意图(原 refresh 更名),父级换 :key 重建页面 |
| sort | (tabs) | 拖拽排序完成 |
Slots
| 插槽名 | 作用域 | 说明 |
|---|---|---|
| default | { tab, index, active } | 页签内容接管(图标 / 圆点 / 标题为默认渲染;关闭按钮始终由组件渲染) |
Expose
| 属性/方法 | 类型 | 说明 |
|---|---|---|
| activate | (key) => void | 激活指定页签(key 不存在则不动作)并滚动到可视区 |
| closeTab | (key) => Promise<void> | 关闭指定页签(走 before-close 拦截;关闭激活项时自动激活相邻项;原 close(key) 更名) |
| closeOthers | (key?) => Promise<void> | 关闭除锚点外的全部可关页签(key 缺省为当前激活页签) |
| closeAll | () => Promise<void> | 关闭全部可关页签(固定项保留),完成后外抛 close-all |
| reloadTab | (key?) => void | 外抛指定页签的 reload 事件(key 缺省为当前激活页签,等价右键「重新加载」) |
| scrollToTab | (key?) => void | 滚动定位到指定页签(key 缺省为当前激活页签) |
| scrollToActive | () => void | 激活页签滚入视口(激活变化时已自动调用) |
TIP
迁移提示:原 BizPageTabs 的 menus 值 refresh 更名为 reload 并新增 close-left / close-right;refresh 事件更名为 reload;expose close / scrollToTab 由 closeTab / scrollToTab 承接;BizPageTabItem 字段并入 BizTabsNavItem(title / affix / icon / closable 语义不变)。