一个左侧导航栏的选中状态把我迷得颠三倒四
事情是这样的 👇
前段时间我用arco.design这个组件库默认的模板项目开放,刚开始需求是这样的:总共八个页面,其中四个显示在导航栏,四个不在导航栏显示,可以导航的页面里又有俩个需要登录才能访问,俩个不登录就能访问。听着是有些绕不过开发起来不是SO EASY吗😎
我用的是vue版本的,说白了就一个知识点——路由和菜单。凭借我的聪明才智,肯定一看就会。
路由
首先,需要先了解一下路由表的配置。基本的路由配置请参阅 Vue-Router 官方文档
// 在本例子中,页面最终路径为 /dashboard/workplace
export default {
path: 'dashboard',
name: 'dashboard', // 路由名称
component: () => import('@/views/dashboard/index.vue'),
meta: {
locale: 'menu.dashboard',
requiresAuth: true,
icon: 'icon-dashboard',
},
children: [
{
path: 'workplace',
name: 'workplace',
component: () => import('@/views/dashboard/workplace/index.vue'),
meta: {
locale: 'menu.dashboard.workplace',
requiresAuth: true,
roles: ['admin'],
hideInMenu: false,
},
},
],
};
路由 Meta
元信息
参数名 | 说明 | 类型 | 默认值 |
---|---|---|---|
roles | 配置能访问该页面的角色,如果不匹配,则会被禁止访问该路由页面 | string[] | - |
requiresAuth | 是否需要登录鉴权 | boolean | false |
icon | 菜单配置icon | string | - |
locale | 一级菜单名(语言包键名) | string | - |
hideInMenu | 是否在左侧菜单中隐藏该项 | boolean | - |
hideChildrenInMenu | 强制在左侧菜单中显示单项 | boolean | - |
activeMenu | 高亮设置的菜单项 | string | - |
order | 排序路由菜单项。如果设置该值,值越高,越靠前 | number | - |
noAffix | 如果设置为true,标签将不会添加到tab-bar中 | boolean | - |
ignoreCache | 如果设置为true页面将不会被缓存 | boolean | - |
hideInMenu 控制菜单显示, requiresAuth 控制是否需要登录,没错,以上知识点完全够我用了🤏🤏🤏🤏
三下五除二就开发完成了,正当我沉浸在成功的喜悦时,测试给我提了个bug。
说导航栏目切换,选中状态有俩个正常,俩个不正常,切换页面导航没选中,再点一次才会选中。我擦👏👏👏👏👏,我傻眼了😧😧😧
到底哪里出了问题,我哪里写错了呢,人家官方肯定没问题,于是我开始寻找。是路由名称重复了,还是那个组件写的有问题,还好有俩个正常的,我仔细比对一下不就好了吗,我可真是个小机灵鬼。
就这样,我又一次为我的自大付出了汗水,对比了一天,我感觉好像真不是我写的有问题,不过还是有收获的,我发现requiresAuth 设置为true的导航正常,requiresAuth设置为false的不正常。抱着怀疑的态度我开始找原来模板项目中处理requiresAuth的代码。最后在components》menu》index.vue文件下发现一个方法:
listenerRouteChange((newRoute) => {
const { requiresAuth, activeMenu, hideInMenu } = newRoute.meta;
if (requiresAuth && (!hideInMenu || activeMenu)) {
const menuOpenKeys = findMenuOpenKeys(
(activeMenu || newRoute.name) as string
);
const keySet = new Set([...menuOpenKeys, ...openKeys.value]);
openKeys.value = [...keySet];
selectedKey.value = [
activeMenu || menuOpenKeys[menuOpenKeys.length - 1],
];
}
}, true);
这... ... 我人麻了,这不是只有requiresAuth 为true的时候才会有效吗?他为啥这么写呢?还是我复制项目的时候复制错了?然后我改成了
listenerRouteChange((newRoute) => {
const { requiresAuth, activeMenu, hideInMenu } = newRoute.meta;
if ((requiresAuth === true || requiresAuth === false) && (!hideInMenu || activeMenu)) {
const menuOpenKeys = findMenuOpenKeys(
(activeMenu || newRoute.name) as string
);
const keySet = new Set([...menuOpenKeys, ...openKeys.value]);
openKeys.value = [...keySet];
selectedKey.value = [
activeMenu || menuOpenKeys[menuOpenKeys.length - 1],
];
}
}, true);
🙈🙈🙈🙈🙈看出来我改哪里了吗,考考你们的眼力,我改的方法是不是很nice。
反正好使了,下班!!!!
来源:juejin.cn/post/7317277887567151145