1、项目需求:在项目开发中,多级菜单的情况下,勾选子菜单时,需要在父级菜单添加active样式。

2、遇到的问题:一级路由菜单的话,点击当前路由会自动在路由标签上添加router-link-exact-active和router-link-active样式。因此针对一级路由只需要改写活跃状态下的css样式即可。但是在下拉菜单中,无法通过点击子菜单的路由给父级菜单自动添加活跃状态下的css属于,因为就需要另外想办法去处理。

3、解决方案分析:(记录当时的心路历程)

  (a)、考虑click事件添加css。给路由点击时,添加时间,获取当前点击的菜单,匹配到其父级菜单,给父级菜单添加css属性。

    (b)、通过监听路由变化事件进行判断。

当时第一种方案是一开始就想到的,但是经过分析旧的这种方法不可取,click事件需要把子菜单和父菜单做了对应的绑定,以后父级菜单命名修改也不方便,于是就想到监听路由变化来判断当前的页面。一开始是打算在路由守卫处做监听,判断to的path是否是需要渲染父级菜单的子菜单,通过vuex定义全局变量,在顶部的组件页面做监听全量变量的变化做判断。由于这种做法需要路由守卫的配合,耦合性比较高,不利于以后修改。经常搜索,才发现可以在组件页面内部直接监听路由的变化。

4、解决方案:

  (a)、在菜单组件内部watch监听路由变化。

  (b)、在路由表文件router.js中给需要渲染父级菜单的子菜单中添加meta属性,并在meta中添加routerParent属性,用于标识需要监听的父级对象。

  (c)、在菜单组件内部,定义一个clickMenuNum数据,具体值为数字,用数字用于表示当前需要渲染的父级菜单。

  (d)、在父级路由中,添加:class,用于判断是否需要添加路由活跃样式。

  (e)、在created初始化方法中,获取当前路由,判断。主要是用于F5刷新重新渲染。

  

  (a)在菜单组件内部watch监听路由变化:

    watch: {
'$route'(toRouter, fromRouter) {
this.doMemuActive(toRouter);
}
},
       doMemuActive(toRouter) {
if (toRouter && toRouter.meta && toRouter.meta.routerParent) {
if (toRouter.meta.routerParent == 'community') {
this.clickMenuNum = ;
} else if (toRouter.meta.routerParent == 'intel') {
this.clickMenuNum = ;
} else if (toRouter.meta.routerParent == 'disp') {
this.clickMenuNum = ;
} else {
this.clickMenuNum = -;
}
} else {
this.clickMenuNum = -;
}
},

  

  (b)、路由表定义 (routerParent字段表示父级代码的字符串标志,这样子不需要通过一个个路径去判断,只需要判断meta里面的一个属性即可找到其父级菜单)

 export const constantRouterMap = [
{path: '/home', component: _import('arcgisMap/home'), hidden: true,redirect: '/home/arcgisMap',
children: [
   {path: 'multipleQuery', component: _import('arcgisMap/multipleQuery'), hidden: true }, {path: 'communitySecurity', component: _import('arcgisMap/communitySecurity'), meta: { routerParent: 'community' }, hidden: true}, {path: 'IntelDigCtrl', component: _import('arcgisMap/IntelDigCtrl'), meta: { routerParent: 'intel' }, hidden: true },
{path: 'peerAnalysis', component: _import('arcgisMap/peerAnalysis'), meta: { routerParent: 'intel' }, hidden: true },
{path: 'dayInNightOut', component: _import('arcgisMap/dayInNightOut'), meta: { routerParent: 'intel' }, hidden: true },
{path: 'nightBehavior', component: _import('arcgisMap/nightBehavior'), meta: { routerParent: 'intel' }, hidden: true },
{path: 'frequentBehavior', component: _import('arcgisMap/frequentBehavior'), meta: { routerParent: 'intel' }, hidden: true },
{path: 'personWifiMergeAls', component: _import('arcgisMap/personWifiMergeAls'), meta: { routerParent: 'intel' }, hidden: true }, {path: 'dispGroup', component: _import('arcgisMap/dispositionModel/dispGroup/dispGroup'), meta: { routerParent: 'disp' }, hidden: true}, /*布控库管理*/
{path: 'dispTargetGroup', component: _import('arcgisMap/dispositionModel/dispTargetGroup/dispTargetGroup'), meta: { routerParent: 'disp' }, hidden: true}, /*布控库目标分组*/
{path: 'dispTarget', component: _import('arcgisMap/dispositionModel/dispTarget/dispTarget'), meta: { routerParent: 'disp' }, hidden: true}, /*布控目标管理*/
]
}]

  

  (c)、在菜单组件内部,定义一个clickMenuNum数据

  data(){
return{
clickMenuNum:-,
}
},

  

  (d)、在父级路由中,添加:class,用于判断是否需要添加路由活跃样式

 <el-col :span="" class="headerCenter flexClsNormal">
<div style="width: 100%;width: 100%;overflow-y: auto;text-align: center;height: 60px;">
<div><router-link to="/home/arcgisMap">首页</router-link></div>
<div><router-link to="/home/actualCensus">实有人口清查</router-link></div>
<div style="margin: auto 0px;" >
<el-dropdown class="headerBarCls" @command="dropdownClick" :class="{ 'clickMenuNumTrue':clickMenuNum==5}">
<span class="el-dropdown-link">社区管控<i class="el-icon-arrow-down el-icon--right"></i></span>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item command="">
<router-link to="/home/communitySecurity" >社区治安一览表</router-link>
</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</div>
<div style="margin: auto 0px;" >
<el-dropdown class="headerBarCls" @command="dropdownClick" :class="{ 'clickMenuNumTrue':clickMenuNum==6}">
<span class="el-dropdown-link">智能挖掘<i class="el-icon-arrow-down el-icon--right"></i></span>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item command="">
<router-link to="/home/IntelDigCtrl" >人员档案</router-link>
</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</div>
<div style="margin: auto 0px;" >
<el-dropdown class="headerBarCls" @command="dropdownClick" :class="{ 'clickMenuNumTrue':clickMenuNum == 7}">
<span class="el-dropdown-link">布控预警<i class="el-icon-arrow-down el-icon--right"></i></span>
<el-dropdown-menu slot="dropdown">
<el-dropdown-item>
<router-link to="/home/dispGroup" >布控库管理</router-link>
</el-dropdown-item>
</el-dropdown-menu>
</el-dropdown>
</div>
</div>
</el-col>

附加:

 由于路由菜单组件pageRoutersBar是只渲染一次,因此需要用监听的方法进行处理。

 <template>
<div id="home">
<div style="width: 100%;position: relative;" id="headerID" ref="headerID">
<!--顶部菜单-->
<el-row>
<pageRoutersBar></pageRoutersBar>
</el-row>
<el-row class="addressSearch" v-if="false">
<addressSearch></addressSearch>
</el-row>
</div>
<router-view></router-view>
</div>
</template>

vue 如何通过监听路由变化给父级路由菜单添加active样式的更多相关文章

  1. 009——VUE中watch监听属性变化实现类百度搜索栏功能

    <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title> ...

  2. vue项目如何监听窗口变化,达到页面自适应?

    [自适应]向来是前端工程师需要解决的一大问题--即便作为当今非常火热的vue框架,也无法摆脱--虽然elementui.iview等开源UI组件库层出不穷,但官方库毕竟不可能满足全部需求,因此我们可以 ...

  3. vue.js之过滤器,自定义指令,自定义键盘信息以及监听数据变化

    一.监听数据变化 1.监听数据变化有两种,深度和浅度,形式如下: vm.$watch(name,fnCb); //浅度 vm.$watch(name,fnCb,{deep:true}); //深度监视 ...

  4. vue mounted中监听div的变化

    vue mounted中监听div的变化 <div style="width:200px;height:30px;background: #0e90d2" id=" ...

  5. vue教程2-08 自定义键盘信息、监听数据变化vm.$watch

    vue教程2-08 自定义键盘信息 @keydown.up @keydown.enter @keydown.a/b/c.... 自定义键盘信息: Vue.directive('on').keyCode ...

  6. React和Vue中,是如何监听变量变化的

    React 中事件监听 本地调试React代码的方法 先将React代码下载到本地,进入项目文件夹后yarn build 利用create-react-app创建一个自己的项目 把react源码和自己 ...

  7. Vue的watch监听事件

    Vue的watch监听事件 相关Html: <!DOCTYPE html> <html lang="en"> <head> <meta c ...

  8. Vue.js:监听属性

    ylbtech-Vue.js:监听属性 1.返回顶部 1. Vue.js 监听属性 本章节,我们将为大家介绍 Vue.js 监听属性 watch,我们可以通过 watch 来响应数据的变化: 实例 & ...

  9. vue watch 深度监听

    watch 是vue 里非常有用的回调函数,监听数据变化,非常方便好用,但是,当监听的数据是个复杂型的数据里,里面的数据变化时普通的监听方式是监听不到的,必须使用深度监听: data() { retu ...

随机推荐

  1. Angular5 import interface 报错:XXX is not a module

    在项目里定义了一个interface,device.ts.然后在component.ts中要使用这个interface,import之后,VSCode报错:‘xxx/xxx/xxx/device.ts ...

  2. Python基础-1 python由来 Python安装入门 注释 pyc文件 python变量 获取用户输入 流程控制if while

    1.Python由来 Python前世今生 python的创始人为吉多·范罗苏姆(Guido van Rossum).1989年的圣诞节期间,吉多·范罗苏姆为了在阿姆斯特丹打发时间,决心开发一个新的脚 ...

  3. Sentinel整合Dubbo限流实战(分布式限流)

    之前我们了解了 Sentinel 集成 SpringBoot实现限流,也探讨了Sentinel的限流基本原理,那么接下去我们来学习一下Sentinel整合Dubbo及 Nacos 实现动态数据源的限流 ...

  4. 浅谈格雷码(Grey Code)在信息学竞赛中的应用

    1.格雷码的概念 1.性质 格雷码(Grey Code),又叫循环二进制码或反射二进制码,是一种编码方式,它的基本特点是任意两个相邻的格雷码只有一位二进制数不同. 常用的二进制数与格雷码间的转换关系如 ...

  5. ./configure 配置文件时出错checking for g++... no

    checking for g++... no checking for c++... no checking for gpp... no checking for aCC... no 缺少C++编译器 ...

  6. 3486 ( Interviewe )RMQ

    Problem Description YaoYao has a company and he wants to employ m people recently. Since his company ...

  7. 加秘钥的SSH

    import paramiko private_key = paramiko.RSAKey.from_private_key_file('id_rsa31.txt') # 创建SSH对象 ssh = ...

  8. AppDomain (转)

    AppDomain是CLR的运行单元,它可以加载Assembly.创建对象以及执行程序.AppDomain是CLR实现代码隔离的基本机制. 每一个AppDomain可以单独运行.停止:每个AppDom ...

  9. 08-js流程控制、循环、元素操作

    # js流程控制 > 流程控制用于基于不同的条件来执行不同的动作. ### if语句 >if... else ... >if ... else if ... else... > ...

  10. 如何利用Chrome进行跨域调试

    为什么要跨域调试: 拿嵌入式web开发说,代码都是跑在板子上,我一个优雅的前端开发要每次改完代码都打包到板子上,用板子的地址打开,这是人做的事??? 怎么跨域调试: 1.升级Chrome为最新版本 2 ...