• Vue3中动态渲染菜单栏(TS)


    需求:左侧的菜单栏渲染数据从路由文件中获取并组织成我们想要的数据格式。

    路由:router》index.ts

    1. const routes: Array<RouteRecordRaw> = [
    2. {
    3. path: '/',
    4. name: 'home',
    5. component: HomeView,
    6. redirect:"order",
    7. children: [
    8. {
    9. path: 'order',
    10. name: 'order',
    11. meta:{isShow:true,title:"订单列表"},
    12. component: () => import('../views/OrderList.vue'),
    13. },
    14. {
    15. path: 'user',
    16. name: 'user',
    17. meta:{isShow:true,title:"用户列表"},
    18. component: () => import('../views/UserList.vue'),
    19. },
    20. ]
    21. },
    22. {
    23. path: '/about',
    24. name: 'about',
    25. // route level code-splitting
    26. // this generates a separate chunk (about.[hash].js) for this route
    27. // which is lazy-loaded when the route is visited.
    28. component: () => import(/* webpackChunkName: "about" */ '../views/AboutView.vue')
    29. },
    30. {
    31. path: '/login',
    32. name: 'login',
    33. component: () => import( '../views/Login.vue')
    34. }
    35. ]

    渲染菜单:

    1、组织数据:

    2、使用element-plus的Menu组件进行展示:

    • el-menu组件要开启路由模式:router
    • 要添加 
    1. <el-container>
    2. <el-aside width="200px">
    3. <el-menu
    4. router
    5. active-text-color="#ffd04b"
    6. background-color="#545c64"
    7. class="el-menu-vertical-demo"
    8. :default-active="active"
    9. text-color="#fff"
    10. >
    11. <el-menu-item v-for="i in list" :key="i.path" :index="i.path">
    12. <el-icon><icon-menu />el-icon>
    13. <span>{{ i.meta.title }}span>
    14. el-menu-item>
    15. el-menu>
    16. el-aside>
    17. <el-main>
    18. <router-view />
    19. el-main>
    20. el-container>

    效果:

    此代码只适用一级菜单,多级菜单也是这个思路组织好数据然后再渲染。

    这个其实不完全算是动态的路由,动态的路由其实应该是后端根据当前用户信息返回的路由。

    可以在路由拦截里从后台获取路由数据并添加到路由里:

    1. // 路由拦截
    2. router.beforeEach(async to => {
    3. const token:string | null = localStorage.getItem('token')
    4. if (!token && to.path !== '/login') {
    5. // 若没有登录且去的不是登录页面,强制用户登录
    6. return '/login'
    7. } else if (token && to.path !== '/login/') {
    8. // 如果登陆过了且不去登录页面,并且之前没有加载过菜单,那么要加载菜单
    9. if (router.getRoutes().length === 3) {
    10. // 请求后台接口获取路由【同步】
    11. let routerData:any = await getRouter()
    12. routerData = routerData.data
    13. routerData.forEach((v:any) => {
    14. const routerObj:RouteRecordRaw = {
    15. path:v.path,
    16. name:v.name,
    17. meta: v.meta,
    18. component:()=>import(/* webpackChunkName: "[request]" */ `../views/${v.path}.vue`)
    19. }
    20. //将路由节点添加到home的children中
    21. router.addRoute("home",routerObj)
    22. })
    23. router.replace(to.path)
    24. }
    25. } else if (token && to.path === "/login") {
    26. return '/'
    27. }
    28. })

  • 相关阅读:
    加密技术1
    CMake教程-第 8 步:添加自定义命令和生成文件
    初探工厂抽象模式
    kafka基本概念
    Rabbitmq—— 从入门到放弃
    代码Bug太多?给新人Code Review头都大了?快来试试SpotBugs
    ASP.NET集成客户关系管理的企业网站的设计与开发
    Elasticsearch 深入理解search After 处理深度分页问题
    DC综合学习
    牛客网:NC74 数字在升序数组中出现的次数
  • 原文地址:https://blog.csdn.net/qq_39290323/article/details/126241526