当我们使用组件库时,组件库提供给我们的组件不满足能我们的需求,故会对其组件二次封装或手敲组件。
以element-ui为例,对el-menu进行二次封装
创建nav组件
跳过element-ui安装和导入阶段,创建名为nav的组件,接收父组件的navList、openKey、clickKey数据,使用递归组件navItem
<template>
<div class="mynav">
<el-menu class="el-menu-vertical-demo" :unique-opened="true" :router="true" @open="$emit('getOpenKey', key)"
@close="handleClose" @select="$emit('getClickKey', key)">
<navItem :dataList="navList" :clickKey="clickKey"></navItem>
</el-menu>
</div>
</template>
<script>
import navItem from './navItem/navItem.vue'
export default {
name: 'Nav',
props: {
navList: { //导航列表
type: Array,
default: () => []
},
openKey: { //当前状态为展开的导航key
type: String,
default: ''
},
clickKey: { //当前激活导航的key
type: String,
default: ''
}
},
data() {
return {
}
},
components: {
navItem
},
methods: {
handleClose(key, keyPath) {
},
}
}
</script>
<style scoped>
.mynav {
text-align: left;
}
</style>
创建递归组件navItem
创建名为navItem的组件,递归自己不需要注册。
<template>
<div>
<template v-for="(item) in dataList">
<el-submenu :index="item.value" v-if="item.children.length" :key="item.name">
<template slot="title">
<i :class=" item.icon"></i>
<span>{{ item.name }}</span>
</template>
<navItem :dataList="item.children"></navItem>
</el-submenu>
<template v-else>
<el-menu-item :index="item.value" :key="item.name">
<i :class=" item.icon"></i>
<span slot="title">{{ item.name }}</span>
</el-menu-item>
</template>
</template>
</div>
</template>
<script>
export default {
name: 'NavItem',
props: {
dataList: { //导航列表
type: Array,
default: () => []
},
openKey: { //当前状态为展开的导航key
type: String,
default: ''
},
clickKey:{ //当前激活导航的key
type:String,
default:''
}
},
data() {
return {
}
},
}
</script>
<style scoped lang="less">
:deep(.el-menu-item.is-active){
box-sizing: border-box;
border-left: 3px solid #409EFF;
background-image: linear-gradient(to right,rgba(64,158,255,0.2),transparent 25%);
}
</style>
创建父组件调用封装好的nav组件
navList为导航列表,openKey为当前展开导航的key,clickKey为当前激活导航的key,getOpenKey方法获取当前打开菜单的key,getClickKey方法获取当前菜单的key
<template>
<div class="home">
<div class="menu">
<navVue :navList="navList" :openKey="openKey" :clickKey="clickKey" @getOpenKey="getOpenKey" @getClickKey="getClickKey"></navVue>
</div>
<div class="container">
<router-view />
</div>
</div>
</template>
<script>
import navVue from '@/components/nav/nav.vue';
export default {
name: 'Home',
data() {
return {
navList: [
{
name: '1',
value: '/page/1',
icon: '',
children: [
{
name: '1-1',
value: '/page/1-1',
icon: '',
children: [
{
name: '1-1-1',
value: '/page/1-1-1',
icon: '',
children: []
},
]
},
{
name: '1-2',
value: '/page/1-2',
icon: '',
children: []
},
]
},
{
name: '2',
value: '/page/2',
icon: '',
children: []
},
{
name: '3',
value: '/page/3',
icon: '',
children: []
},
],
openKey: '',
clickKey: ''
}
},
components: {
navVue
},
methods: {
//获取当前打开菜单的key
getOpenKey(res) {
this.openKey = res
},
// 获取当前菜单的key
getClickKey(res) {
this.clickKey=res
}
}
}
</script>
<style scoped lang="less">
.home {
width: 100%;
height: 100vh;
display: flex;
.menu {
width: 220px;
height: 100%;
flex: none;
}
.container {
flex: 1;
width: 100%;
height: 100%;
padding: 20px;
box-sizing: border-box;
text-align: left;
}
}
</style>