102 lines
3.0 KiB
TypeScript
102 lines
3.0 KiB
TypeScript
import { computed } from 'vue'
|
||
import { useAppMode } from './useAppMode'
|
||
import { useTheme } from './useTheme'
|
||
|
||
export interface TabItem {
|
||
name: string
|
||
title: string
|
||
icon: string
|
||
path: string
|
||
}
|
||
|
||
const USER_TABS: TabItem[] = [
|
||
{ name: 'home', title: '首页', icon: 'home', path: '/pages/home/index' },
|
||
// wot-ui 无 app,正确图标名为 apps
|
||
{ name: 'explore', title: '功能入口', icon: 'apps', path: '/pages/explore/index' },
|
||
{ name: 'mine', title: '我的', icon: 'user', path: '/pages/mine/index' },
|
||
]
|
||
|
||
const ADMIN_TABS: TabItem[] = [
|
||
{ name: 'dashboard', title: '工作台', icon: 'dashboard', path: '/subPackages/admin/pages/dashboard/index' },
|
||
{ name: 'explore', title: '功能入口', icon: 'apps', path: '/subPackages/admin/pages/explore/index' },
|
||
{ name: 'mine', title: '我的', icon: 'user', path: '/pages/mine/index' },
|
||
]
|
||
|
||
export function useAppTabbar() {
|
||
const { appMode } = useAppMode()
|
||
const { apply } = useTheme()
|
||
|
||
const tabItems = computed(() => (appMode.value === 'admin' ? ADMIN_TABS : USER_TABS))
|
||
|
||
const resolveActive = (routePath?: string): string => {
|
||
const path = routePath || getCurrentRoutePath()
|
||
const items = tabItems.value
|
||
const hit = items.find(t => path.includes(t.path.replace(/^\//, '')) || path.endsWith(t.name))
|
||
if (hit) return hit.name
|
||
if (path.includes('/mine')) return 'mine'
|
||
if (path.includes('/explore')) return 'explore'
|
||
if (path.includes('/dashboard') || path.includes('/home')) return items[0].name
|
||
return items[0].name
|
||
}
|
||
|
||
/**
|
||
* Tab 切换:先同步底色再 redirectTo,避免 reLaunch 清栈 + 浅色 page 闪屏。
|
||
* 已在当前页则 no-op。
|
||
*/
|
||
const navigateTab = (name: string) => {
|
||
const item = tabItems.value.find(t => t.name === name)
|
||
if (!item) return
|
||
const cur = getCurrentRoutePath()
|
||
const target = item.path
|
||
if (cur === target || cur.endsWith(target.replace(/^\//, ''))) return
|
||
apply()
|
||
uni.redirectTo({ url: target })
|
||
}
|
||
|
||
const shouldShowTabbar = (routePath?: string): boolean => {
|
||
const path = routePath || getCurrentRoutePath()
|
||
const hidePatterns = [
|
||
'/blog/detail',
|
||
'/blog/ppt',
|
||
'/columns/detail',
|
||
'/works/detail',
|
||
'/videos/detail',
|
||
'/videos/album',
|
||
'/resource/form',
|
||
'/resource/list',
|
||
'/analytics',
|
||
'/columns/form',
|
||
'/posts/',
|
||
'/works/list',
|
||
'/works/form',
|
||
'/videos/list',
|
||
'/videos/form',
|
||
'/video-albums/',
|
||
'/snippets/form',
|
||
'/attachments/',
|
||
'/inquiries/',
|
||
'/about/index',
|
||
'/settings/',
|
||
'/oss-configs/',
|
||
'/users/',
|
||
'/logs/',
|
||
]
|
||
return !hidePatterns.some(p => path.includes(p))
|
||
}
|
||
|
||
return {
|
||
tabItems,
|
||
resolveActive,
|
||
navigateTab,
|
||
shouldShowTabbar,
|
||
USER_TABS,
|
||
ADMIN_TABS,
|
||
}
|
||
}
|
||
|
||
function getCurrentRoutePath(): string {
|
||
const pages = getCurrentPages()
|
||
const cur = pages[pages.length - 1] as { route?: string } | undefined
|
||
return cur?.route ? `/${cur.route}` : ''
|
||
}
|