vue+elementui实现选项卡功能

vue+elementui实现选项卡功能

本文实例为大家分享了vue+elementui实现选项卡功的具体代码,供大家参考,具体内容如下

用法:

首先自己先在项目中定义三个组件(顶部TopNav,左侧LeftAside,中间Main),这方法三两句话描述不清

我就上我用过的一个项目代码实例(但是这个有点缺陷,没有做像一键清空选项卡,关闭左右侧选项卡的方法)

TopNav

<template>     <el-menu class="el-menu-demo" mode="horizontal" background-color="#334157" text-color="#fff" active-text-color="#fff">         <el-button class="buttonimg">             <img class="showimg" :src="collapsed?imgshow:imgsq" @click="doToggle()">             <!-- :src="collapsed?imgshow:imgsq" @click="doToggle()" -->         </el-button>         <el-submenu index="2" class="submenu">             <template slot="title">当前用户【{{username}}】身份认证:{{usertype}}</template>             <el-menu-item index="2-1">设置</el-menu-item>             <el-menu-item index="2-2" @click="mya()">个人中心</el-menu-item>             <el-menu-item @click="exit()" index="2-3">退出</el-menu-item>         </el-submenu>     </el-menu> </template> <script>     export default {         name: 'LeftAside',         data: function() {             return {                 collapsed: false, //是否折叠                 imgshow: require('../assets/img/show.webp'),                 imgsq: require('../assets/img/sq.webp'),                 username:sessionStorage.getItem("username"),                 usertype:sessionStorage.getItem("deptment")             };         },         methods: {             doToggle() {                 this.collapsed = !this.collapsed;                 console.log("TopNav的collapsed=%s", this.collapsed);                 this.$emit('top-click', this.collapsed);             },             exit() {                 this.$confirm('亲,请不要走,留下好不好?', '提示', {                     confirmButtonText: '残忍离开',                     cancelButtonText: '留下~',                     type: 'warning'                 }).then(() => {                     this.$router.push('/');                 }).catch(() => {});             },       mya(){         /* this.$router.push('/userCenter'); */          /* this.$router.push('/system/UserCenter'); */       }         }     } </script> <style scoped>     .el-menu-vertical-demo:not(.el-menu--collapse) {         border: none;     }     .submenu {         float: right;     }     .buttonimg {         height: 60px;         background-color: transparent;         border: none;     }     .showimg {         width: 26px;         height: 26px;         position: absolute;         top: 17px;         left: 17px;     }     .showimg:active {         border: none;     } </style>

LeftAside

<template>   <el-menu router :default-active="$route.path" class="el-menu-vertical-demo" background-color="#334157" text-color="#fff"     active-text-color="#ffd04b" :collapse="leftCollapsed">     <!-- <el-menu default-active="2" :collapse="collapsed" collapse-transition router :default-active="$route.path" unique-opened class="el-menu-vertical-demo" background-color="#334157" text-color="#fff" active-text-color="#ffd04b"> -->     <div class="logobox">       <img class="logoimg" src="../assets/img/logo.webp" alt="">     </div>     <!--          第一级菜单          el-submenu属性:          index:用于菜单折叠,不能重复          key:菜单项的唯一标识,不可重复          -->     <el-menu-item index="/Home" key="Home">       <i class="el-icon-house"></i>       <span slot="title">首页</span>     </el-menu-item>     <!-- <el-menu-item index="/Page1" key="Page1">             <i class="el-icon-menu"></i>             <span slot="title">Page1</span>         </el-menu-item>         <el-menu-item index="/Page2" key="Page2">             <i class="el-icon-menu"></i>             <span slot="title">Page2</span>         </el-menu-item> -->     <el-submenu v-for="root in treenode" :index="'index-'+root.dictId" :key="'key-'+root.dictId">       <template slot="title">         <i :class="root.dictIcon"></i>         <span slot="title">{{root.dictText}}</span>       </template>       <!-- 第二级菜单 -->       <!--             el-menu-item属性:             index:用于跳转页面,不能重复             key:菜单项的唯一标识,不可重复              -->       <el-menu-item @click="addTab(node.dictUrl,node.dictText)" v-for="node in root.children" :index="node.dictUrl"         :key="'key-'+node.dictId">         <i class="el-icon-menu"></i>         <span slot="title">{{node.dictText}}</span>       </el-menu-item>     </el-submenu>   </el-menu> </template> <script>   export default {     name: 'LeftAside',     props: ['leftCollapsed'],     data: function() {       return {         treenode: ''       };     },     methods: {       addTab: function(url, text) {         console.log(url, text);         //调用vuex中的addTab方法,将点击的菜单对应的组件信息添加到已打开的openTabs中         this.$store.commit('addTab', {           title: text, //Tab页签标题           name: url //组件的路由         });         //设置当前Tab面板为选中状态         this.$store.commit('setTabActive', url);       }     },     created() {       //获取请求路径       /* let url = this.axios.urls.SYSTEM_TREENODE; */       let url = this.axios.urls.SYSTEM_QUERY;       /*  ,{username:sessionStorage.getItem("username")} */       console.log(url);       //发送axios请求       this.axios.post(url, {         username: sessionStorage.getItem("username")       }).then(resp => {         console.log(resp.data);         this.treenode = resp.data.data;       }).catch(resp => {});       //设置首页默认显示       // this.$router.push('/Home');     }   } </script>

Main

<template style="background-color:floralwhite">     <el-container class="main-container">         <el-aside :class="openCollapse">             <LeftAside :open-collapsed="collapsed"></LeftAside>         </el-aside>         //选项卡控件         <el-container>             <el-header class="main-header">                 <TopNav @click-collapse="topClick"></TopNav>             </el-header>             <el-main class="main-center">                 <el-tabs class="tabs-panel-fit" v-model="activeTab" type="border-card" closable @tab-remove="removeTab">                     <el-tab-pane v-for="item in openTabs" :key="item.name" :label="item.title" :name="item.name">                         <component :is="item.content"></component>                     </el-tab-pane>                 </el-tabs>             </el-main>        //时钟效果       <div id="app" style="margin-left: 200px;margin-top: -400px;font-size: 30px;">           {{date}}       </div>         </el-container>     </el-container> </template> <script>     import TopNav from '@/components/TopNav'     import LeftAside from '@/components/LeftAside'     export default {         name: 'Main',         data: function() {             return {                 collapsed: false,         date: new Date()             };         },         methods: {             topClick: function(collapsed) {                 this.collapsed = collapsed;             },             removeTab: function(targetName) {                 //获取所有已打开的Tabs选项卡                 let tabs = this.$store.getters.openTabs;                 //获取当前激活的Tab选项卡                 let activeName = this.$store.getters.activeTab;                 //判断当前激活的Tab选项卡和当前被关闭的Tab选项卡是否相同                 if (activeName === targetName) {                     //遍历已打开的选项卡                     tabs.forEach((tab, index) => {                         //判断是否相同,并获取就近需要被激活选项卡                         if (tab.name === targetName) {                             let nextTab = tabs[index + 1] || tabs[index - 1];                             if (nextTab) {                                 activeName = nextTab.name;                             }                         }                     });                 }                 //激活选项卡                 this.$store.commit('setTabActive', activeName);                 //删除Tab                 this.$store.commit('delTab', tabs.filter(tab => tab.name !== targetName));             }         },         components: {             TopNav,             LeftAside         },         computed: {//计算属性             openCollapse: function() {                 return !this.collapsed ? 'main-aside' : 'main-aside-collapsed'             },             openTabs: function() {                 let openTabs = this.$store.getters.openTabs;                 let tabs = [];                 if (null == openTabs)                     return tabs;                 else {                     for (let tab of openTabs) {                         let component = resolve => require.ensure([], () => resolve(require('@/views' + tab.name + '.vue')));                         tabs.push({                             title: tab.title,                             name: tab.name,                             content: component                         });                     }                     return tabs;                 }             },             activeTab: {                 get() {                     return this.$store.getters.activeTab;                 },                 set(val) {                     this.$store.commit('setTabActive', val);                 }             }         },         //展示时钟的方法         mounted() {//挂载完成             console.log(this.$route.path);             if (this.$route.path == '/Home') {                 this.$store.commit('addTab', {                     title: '首页',                     name: '/Home'                 });                 this.$store.commit('setTabActive', '/Home');             }        let _this = this; // 声明一个变量指向Vue实例this,保证作用域一致           this.timer = setInterval(() => {             _this.date = new Date(); // 修改数据date           }, 1000)         },         beforeDestroy() {           if (this.timer) {             clearInterval(this.timer); // 在Vue实例销毁前,清除我们的定时器           }         }     } </script> <style>     .main-container {         height: 100%;         width: 100%;         box-sizing: border-box;     }     .main-aside-collapsed {         /* 在CSS中,通过对某一样式声明! important ,可以更改默认的CSS样式优先级规则,使该条样式属性声明具有最高优先级 */         width: 64px !important;         height: 100%;         background-color: #334157;         margin: 0px;     }     .main-aside {         width: 240px !important;         height: 100%;         background-color: #334157;         margin: 0px;     }     .main-header,     .main-center {         padding: 0px;         border-left: 2px solid #333;         height: 100%;         object-fit: fill;     }     .div-pagination {         margin: 10px 0px;         width: 100%;     }     /* 设置tabs内容面板100%填充父容器 */     .tabs-panel-fit {         margin: 0;         padding: 0;         /* background-color:#1F2D3D; */         width: 100%;         height: 100%;         object-fit: fill;     }     /* 设置tabs内容面板的内边距为0 */     .el-tabs--border-card>.el-tabs__content {         padding: 0;     }     /* 设置tab的表框效果(重要) */     .el-tabs.el-tabs--border-card {         box-shadow: none;         border-bottom: none;         border: 0;     }     /*设置选项卡中第一个首页选项卡不能关闭*/     .el-tabs>.el-tabs__header .el-tabs__item:first-child>span {         display: none;     }     /* elementUI dialog弹出框样式优化 */     .el-dialog {         position: absolute;         top: 50%;         left: 50%;         margin: 0 !important;         transform: translate(-50%, -50%);         max-height: calc(100% - 30px);         max-width: calc(100% - 30px);         display: flex;         flex-direction: column;         /* 圆角效果 */         border-radius: 0.4em;     }     .el-dialog>.el-dialog__body {         overflow: auto;     }     .el-dialog__header {         background-color: #F5F7FA;         border-bottom: 1px solid #ccc;         font-size: 14px;         font-weight: bold;         padding: 15px 20px 15px;         /* 圆角效果 */         border-radius: 0.4em 0.4em 0em 0em;     }     .el-dialog__body {         padding: 20px 15px;     }     .el-dialog__footer {         background-color: #F5F7FA;         border-top: 1px solid #ccc;         padding: 15px;         /* 圆角效果 */         border-radius: 0em 0em 0.4em 0.4em;     }     .el-form>.el-form-item:last-child {         margin-bottom: 0px;     }     /* 更改table表格的高亮背景色*/     /* .el-table tr.current-row>td {         background: #FFF68F;     } */     .el-table .el-table__body tr:hover>td{         background: #FFF68F;         font-weight:bold;         color:#000000;     }     /* 分页组件 */     /* .div-pagination {         margin: 10px 0px;         width: 100%;     } */ </style>

推荐阅读