背景:用element實現(xiàn)一個動態(tài)菜單闸英,支持多層級菜單
頁面布局:layout文件夾??
?layout.vue(菜單入口)?
side-bar.vue
compomne.vue 右側(cè)視圖組件, 支持 路由 iframe切換
1.layout.vue代碼
<template>
<template>
??<div?class="layout">
????<el-header>海外主題管理臺?<span><i?v-if="isCollapse"
???????????class="el-icon-s-unfold"
???????????@click="isCollapse?=?false"></i><i?class="el-icon-s-fold"
???????????v-else
???????????@click="isCollapse?=?true"></i></span></el-header>
????<el-container>
??????<div?:class="isCollapse???'left-content-colse'?:?'left-content'">
????????<el-aside?style="width:225px">
??????????<el-scrollbar?style="height:100%">
????????????<el-menu?class="el-menu-vertical-demo"
?????????????????????:default-active="componentId"
?????????????????????@open="handleOpen"
?????????????????????@close="handleClose"
?????????????????????:collapse-transition="false"
?????????????????????:unique-opened="true"
?????????????????????:collapse="isCollapse">
??????????????<side-bar?:list="menuList"
????????????????????????@onActive="onActive"
????????????????????????:isCollapse="isCollapse"></side-bar>
????????????</el-menu>
??????????</el-scrollbar>
????????</el-aside>
??????</div>
??????<el-main>
????????<Components?:componentId="componentId"></Components>
??????</el-main>
????</el-container>
??</div>
</template>
<script>
import?{?sideBarData?}?from?'./menuConfig'
import?SideBar?from?'./side-bar.vue'
import?Components?from?'./components.vue'
import?{?mapGetters?}?from?"vuex";
export?default?{
??components:?{?SideBar,?Components?},
??data()?{
????return?{
??????componentId:?'1-1',
??????isCollapse:?false,
??????menuList:?sideBarData
????};
??},
??methods:?{
????onActive(item)?{
??????this.componentId?=?item.id
??????this.$store.commit("saveActiveMenuId",?this.componentId);
????},
????handleOpen(key,?keyPath)?{
??????console.log(key,?keyPath,?'1111');
????},
????handleClose(key,?keyPath)?{
??????console.log(key,?keyPath);
????},
??},
??watch:?{},
??computed:?{
????...mapGetters(["activeMenuId"]),
??},
??created()?{
????if?(this.activeMenuId)?this.componentId?=?this.activeMenuId;
??},
??mounted()?{?},
};
</script>
<style?lang="less"?scoped>
.layout?{
??position:?absolute;
??top:?0;
??left:?0;
??width:?100vw;
??height:?100%;
??overflow:?hidden;
}
.left-content?{
??height:?100vh;
??overflow:?hidden;
}
.left-content-colse?{
??width:?64px;
??height:?100vh;
??background:?red;
??overflow:?hidden;
}
.el-submenu__title?{
??span?{
????display:?inline-block;
????overflow:?hidden;
????text-overflow:?ellipsis;
????white-space:?nowrap;
??}
}
</style>
<style>
.el-header?{
??background-color:?#008dff;
??color:?#fff;
??font-size:?18px;
??height:?auto;
??line-height:?60px;
}
.el-menu?{
??background-color:?#13254a;
??border-right:?none;
??color:?#fff;
}
.el-submenu__title?{
??color:?#fff;
??z-index:?9?!important;
}
.el-menu-item?{
??color:?#fff;
??border-color:?none;
}
.el-aside?{
??background-color:?#13254a;
??height:?100%;
??color:?#fff;
??transition:?width?0.5s;
}
.el-submenu__title:hover?{
??color:?#fff;
??background-color:?rgb(0,?141,?255,?0.2)?!important;
}
.el-menu-item:hover?{
??color:?#fff;
??background-color:?rgb(0,?141,?255,?0.2)?!important;
}
.el-menu-item.is-active?{
??color:?#fff;
??background-color:?#008dff?!important;
}
.el-main?{
??background-color:?#e9eef3;
??color:?#333;
}
.el-icon-menu:before?{
??content:?"\e798";
??color:?#fff;
}
/*?
.el-menu-vertical-demo:not(.el-menu--collapse)?{
??width:?200px;
??min-height:?400px;
}?*/
</style>
2.side-bar.vue 代碼
<template>
??<fragment>
????<template?v-for="(item,index)?in?list">
??????<!--?標題?-->
??????<template?v-if="item.children?&&?item.children.length">
????????<el-submenu?:key="index"
????????????????????:index="item.id"
????????????????????@click="onClick(item)">
??????????<template?:index="item.id"
????????????????????slot="title">
????????????<i?:class="item.icon"
???????????????style="color:#fff"></i>
????????????<span?slot="title">{{item.name}}</span>
??????????</template>
??????????<el-menu-item-group>
????????????<sideBar?:list="item.children"
?????????????????????v-bind="$attrs"
?????????????????????v-on="$listeners"></sideBar>
??????????</el-menu-item-group>
????????</el-submenu>
??????</template>
??????<!--?選項?-->
??????<template?v-else>
????????<el-menu-item?:key="index"
??????????????????????@click="onClick(item)"
??????????????????????:index="item.id">
??????????<i?:class="item.icon"></i>
??????????<!--?<router-link?:to="item.path">{{item.name}}</router-link>?-->
??????????<span?slot="title">{{item.name}}</span>
????????</el-menu-item>
??????</template>
????</template>
??</fragment>
</template>
<script>
export?default?{
??name:?"sideBar",
??props:?{
????list:?Array,
????isCollapse:?Boolean
??},
??created()?{
??},
??methods:?{
????onClick(val)?{
??????this.$emit('onActive',?val)
????}
??}
};
</script>
<style></style>
3.components.vue代碼
<template>
??<div?class="box"
???????v-loading="loading">
????<template>
??????<iframe?id="myIframe"
??????????????:src="path"
??????????????frameborder="0"></iframe>
????</template>
????<template>
??????<router-view></router-view>
????</template>
??</div>
</template>
<script>
import?{?sideBarData?}?from?'./menuConfig'
export?default?{
??name:?"components",
??props:?{
????componentId:?String,
????list:?Array,
??},
??watch:?{
????componentId:?{
??????handler(val)?{
????????if?(val)?{
??????????this.loading?=?true;
??????????this.getNode(this.menuList,?val);
????????}
??????},
??????immediate:?true
????}
??},
??data()?{
????return?{
??????loading:?true,
??????currentView:?'wallpaper-approve',
??????menuList:?sideBarData,
??????activeNode:?{},
??????path:?'',
????};
??},
??methods:?{
????//??遞歸獲取節(jié)點
????getNode(dataList,?val)?{
??????if?(dataList.length?>?0)?{
????????dataList.forEach(item?=>?{
??????????if?(item.children)?{
????????????this.getNode(item.children,?val)
??????????}?else?{
????????????if?(item.id?===?val)?{
??????????????this.activeNode?=?item;
????????????}
??????????}
????????})
??????}
??????this.path?=?this.activeNode.url;
??????console.log('this.activeNode',?this.activeNode)
????},
????changeviewFun(val)?{
??????this.currentView?=?val;
????}
??},
??mounted()?{
????let?self?=?this
????var?iframe?=?document.getElementById('myIframe');
????if?(!/*@cc_on!@*/0)?{?//if?not?IE
??????iframe.onload?=?function?()?{
????????self.loading?=?false
??????};
????}?else?{
??????iframe.onreadystatechange?=?function?()?{
????????if?(iframe.readyState?==?"complete")?{
??????????self.loading?=?false
????????}
??????};
????}
??}
};
</script>
<style>
.box?{
??width:?100%;
??height:?calc(100%?-?60px);
}
.el-main?{
??background-color:?#f0f2f5?!important;
??color:?#f0f2f5;
}
iframe?{
??width:?100%;
??height:?100%;
??/*?background:?red?!important;?*/
}
</style>
4.配置文件
????{
????????id:'1',
????????name:'一級目錄',
????????icon:?"el-icon-menu",
????????type:'',?????????//?1路由?或??2?iframe
????????children:?[
????????????{
????????????????id:?'1-1',
????????????????name:'二級目錄',
????????????????type:'2',????
????????????????path:'xxx',
????????????????url:??`${BASE_URL}/xxx`
????????????},
????????]
????},
5. 動態(tài)加載菜單收縮字體不顯示問題main.js
collapse-transition
// main.js
import Fragment from ‘vue-fragment’
Vue.use(Fragment.Plugin)
參考:Vue-Components-Library/SidebarItem.vue at master · NLRX-WJC/Vue-Components-Library · GitHub