使用Vue递归组件实现动态菜单

  • 现在很多项目的菜单都是动态生成的,之前自己做项目也是遇到这种需求,翻看了官网案例,和网上大神的案例.只有两个感觉,官网的案例太简洁,没有什么注释,看起来不太好理解,大神们的作品又比较复杂,对于初学者来说理解起来还是有难度,自己捣鼓了几天,勉强理解了递归组件菜单的实现,这里结合官网的案例,把代码和注释附上.

  • 如果你的项目是element-ui,其实它里面也有提供树形菜单,但是由于是别人封装的,所以使用起来没那么方便,大多数还是会自己配置,好了,不说那么多,还是回到递归组件上来吧

  • 先来看一下菜单的最终效果,有+号的都是可以点击展开的
  •             
  • 首先看一下项目的目录,在后台菜单数据没拿到之前,这里先演示一个模拟数据的,先在SRC文档下建一个data存放菜单数据.按照菜单层级关系写 数据里设置menuLevel是为了配置路由的,值是组件的名字

  • 接着创建两个组件,一个是菜单父组件,一个是递归的子组件,父组件代码:

  • <template>
    <div>
    <ul id="demo">
    <submenu
    class="item"
    :model="treeData">
    </submenu>
    </ul>
    </div>
    </template>
    <script>
    // 引入菜单数据
    import data from '../../data/treeData'
    // 引入子组件
    import submenu from './submenu/submenu.vue'
    export default {
    components: {
    submenu
    },
    name: 'treeMenu',
    data () {
    return {
    treeData: data
    }
    }
    }
    </script>
    <style scoped>
    @import './treeMenu.scss';
    </style>
  • 子组件代码,html部分:
  • <template>
    <div>
    <li>
    <div
    :class="{bold: isFolder}"
    @click="toggle"
    @dblclick="changeType">
    <!-- 配置路由跳转 -->
    <router-link :to="{ name: model.menuLevel }">{{ model.name }}</router-link> <span v-if="isFolder">[{{ open ? '-' : '+' }}]</span>
    </div>
    <ul v-show="open" v-if="isFolder">
    <submenu
    class="item"
    v-for="(model, index) in model.children"
    :key="index"
    :model="model"> </submenu>
    <!-- <li class="add" @click="addChild">+</li> -->
    </ul>
    </li>
    </div>
    </template>

    子组件代码,js部分:

  • // 引入子组件
    import submenu from './submenu'
    export default {
    components: {
    submenu
    },
    name: 'submenu',
    props: {
    model: Object
    },
    data: function () {
    return {
    open: false
    }
    },
    computed: {
    // 是否展示+图标
    isFolder: function () {
    return this.model.children &&
    this.model.children.length
    }
    },
    methods: {
    // 单击展示子菜单
    toggle: function () {
    if (this.isFolder) {
    this.open = !this.open
    }
    },
    // 双击给当前单一不可展开的菜单添加children,变成可展开样式
    changeType: function () {
    if (!this.isFolder) {
    // Vue.set(this.model, 'children', [])
    this.$set(this.model, 'children', [])
    this.addChild()
    this.open = true
    }
    },
    // 给子菜单添加内容
    addChild: function () {
    this.model.children.push({
    name: 'new stuff'
    })
    }
    }
    }

    路由配置,这里的name和data数据里的menuLevel一样:

  • import Vue from 'vue'
    import Router from 'vue-router'
    // import OnePage from '@/components/OnePage/OnePage'
    // 引入菜单组件
    import treeMenu from '@/components/menu/treeMenu'
    // 引入一级菜单
    import one from '@/components/one/one'
    // 引入二级菜单
    import two from '@/components/two/two'
    // 引入三级菜单
    import three from '@/components/three/three' Vue.use(Router) export default new Router({
    routes: [
    // {
    // path: '/',
    // name: 'OnePage',
    // component: OnePage
    // }
    {
    path: '/',
    name: 'treeMenu',
    component: treeMenu
    },
    {
    path: '/one',
    name: 'one',
    component: one
    },
    {
    path: '/two',
    name: 'two',
    component: two
    },
    {
    path: '/three',
    name: 'three',
    component: three
    }
    ]
    })

    这样一个树形菜单就大致完成了,配置了路由的也可以跳转到相应页面,如果菜单数据是后台给你的,数据只要和你一开始设置data数据格式一样就可以直接用了

Vue.js递归组件实现动态树形菜单的更多相关文章

  1. 【Vue.js实战案例】- Vue.js递归组件实现组织架构树和选人功能

    大家好!先上图看看本次案例的整体效果. 浪奔,浪流,万里涛涛江水永不休.如果在jq时代来实这个功能简直有些噩梦了,但是自从前端思想发展到现在的以MVVM为主流的大背景下,来实现一个这样繁杂的功能简直不 ...

  2. Vue.js 递归组件实现树形菜单

    最近看了 Vue.js 的递归组件,实现了一个最基本的树形菜单. 项目结构: main.js 作为入口,很简单: import Vue from 'vue' Vue.config.debug = tr ...

  3. 用Vue.js递归组件构建一个可折叠的树形菜单

    在Vue.js中一个递归组件调用的是其本身,如: Vue.component('recursive-component', {   template: `<!--Invoking myself! ...

  4. Vue.js的组件(slot/动态组件等)、单文件组件、递归组件使用

    一.组件 1> 组件命名方式有两种(注意:在DOM模板中只有kebab-case命名方法才生效): html中引用组件: <!-- 在DOM模板中,只有 kebab-case命名才生效 - ...

  5. 【Vue课堂】Vue.js 父子组件之间通信的十种方式

    这篇文章介绍了Vue.js 父子组件之间通信的十种方式,不管是初学者还是已经在用 Vue 的开发者都会有所收获.无可否认,现在无论大厂还是小厂都已经用上了 Vue.js 框架,简单易上手不说,教程详尽 ...

  6. 谈谈Vue的递归组件

    2月最后一天,而且还四年一遇,然而本月居然一篇博客没写,有点说不过去.所以,今天就来谈谈Vue的递归组件.我们先来看一个例子: See the Pen 递归组件 by imgss (@imgss) o ...

  7. Vue.js多重组件嵌套

    Vue.js多重组件嵌套 Vue.js中提供了非常棒的组件化思想,组件提高了代码的复用性.今天我们来实现一个形如 <app> <app-header></app-head ...

  8. Vue.js之组件传值

    Vue.js之组件传值 属性传值可以从父组件到子组件,也可以从子组件到父组件. 这里讲一下从父组件到子组件的传值 还以上次的demo为例,demo里有APP.vue是父组件,Header.vue,Us ...

  9. Vue.js之组件嵌套小demo

    Vue.js之组件嵌套的小demo项目 第一步:初始化一个wabpack项目,这里不在复述.第二步:在components文件夹下新建Header.vue Footer.vue和Users.vue三个 ...

随机推荐

  1. ROS Learning-031 (提高篇-009 A Mobile Base-07) 控制移动平台 --- (操作)人机交互

    ROS 提高篇 之 A Mobile Base-07 - 控制移动平台 - (操作)人机交互 我使用的虚拟机软件:VMware Workstation 11 使用的Ubuntu系统:Ubuntu 14 ...

  2. TinkerPop中的遍历:图的遍历策略

    遍历策略 一个TraversalStrategy分析一个遍历,如果遍历符合它的标准,可以相应地改变它.遍历策略在编译时被执行,并构成Gremlin遍历机的编译器的基础.有五类策略分列如下: decor ...

  3. git命令(二)

    2.查看.添加.提交.删除.找回,重置修改文件 3.查看文件diff git diff <file> # 比较当前文件和暂存区文件差异 git diff git diff <$id1 ...

  4. DotNet经典面试题(转载)

    .Net基础常见 什么叫应用程序域?什么是受管制的代码?什么是强类型系统?什么是装箱和拆箱?什么是重载?CTS.CLS.CLR分别作何解释? 答: 1应用程序域可以理解为一种轻量级进程.起到安全的作用 ...

  5. 判断本地是否存在Jquery文件,如果不存在则使用CDN加速的Jquery文件

    <script>//判断是否成功将Jquery库引入,如果没有成功引入则引入本地Jquery库if (typeof jQuery == 'undefined') {document.wri ...

  6. window 启用 windows 自动登录

    启用 windows 自动登录 方案一: 1.运行命令:control userpasswords2 2.取掉复选框的钩: 方案二:(方案一无效的时候使用) 微软官网地址:https://suppor ...

  7. JetBrains WebStorm 如何从GitHub上克隆的代码

    工作中经常会遇到要从GitHub上拉代码,详细操作记录如下: 绑定账号 1.File->Settings->Version Control->Github 成功后会出现下面的这个账户 ...

  8. Glib学习笔记(三)

    你将学到什么 如何实现Object的方法 Object的方法 Object的public方法 在头文件声明一个函数,然后在源文件中实现函数即可 /* declaration in the header ...

  9. PHP里public和private的区别

    public  公共的,谁都可以用 private 私有的,当前class可以随便用,外部不能调用

  10. P2245 星际导航 瓶颈路

    \(\color{#0066ff}{ 题目描述 }\) sideman 做好了回到 \(\text{Gliese}\) 星球的硬件准备,但是 \(\text{sideman}\) 的导航系统还没有完全 ...