vue3使用vue-router嵌套路由(多级路由)

文章目录

    • 1、Vue3 嵌套路由
    • 2、项目结构
    • 3、编写相关页面代码
      • 3.1、编写route文件下 index.ts文件
      • 3.2、main.ts文件代码:
      • 3.3、App.vue文件代码:
      • 3.4、views文件夹下的Home文件夹下的index.vue文件代码:
      • 3.5、views文件夹下的Home文件夹下的Tigerhhzzb.vue文件代码:
      • 3.6、views文件夹下的Home文件夹下的T.vue文件代码:
      • 3.7、views文件夹下的Home文件夹下的ChildA.vue文件代码:
    • 4、测试效果

1、Vue3 嵌套路由

Vue3 嵌套路由的使用和 Vue2 相差不大,主要的区别是 Vue3 的路由实例化使用了 createApp() 方法,所以实例化路由时需要传入根组件。另外,Vue3 的路由对象除了包含 Vue2 中的导航守卫、导航钩子和解析守卫等功能外,还新增了 meta prop 和 route prop。

在使用嵌套路由时,建议将路由按照功能模块进行分层,每一层代表一个主要的功能块,每个层级下的路由数量不要过多,一般建议不要超过 10 个,层级也不要超过 5 层。同时,根据实际业务需求,可以适当调整路由层级和数量,以达到更好的管理和使用效果。

2、项目结构

在这里插入图片描述

3、编写相关页面代码

3.1、编写route文件下 index.ts文件

route文件下 index.ts文件代码:

import { createRouter, createWebHistory, type RouteRecordRaw } from 'vue-router'
import HomeView from '../views/HomeView.vue'

const routes: RouteRecordRaw[] = [
  {
    path: '/',
    redirect: '/home',
  },
  {
    path: '/home',
    name: 'Homeindex',
    component: () => import('../views/Home/index.vue'),
    meta: {
      title: 'Home Page',
      roles: ['admin', 'admin1']
    },
    children: [
      {
        path: 'tigerhhzz',
        name: 'Tigerhhzz',
        component: () => import('@/views/Home/Tigerhhzz.vue'),
        // 也可以使用props传参方式接收传来的参数
        props: (propsRouter) => {
          // console.log('props >router', propsRouter)
          // 可以return query 也可以return params支持两种传参方式
          return propsRouter.query
        },
        // 多级嵌套 建议用query传参
        children: [
          {
            path: 'childA',
            name: 'ChildA',
            component: () => import('@/views/Home/ChildA.vue'),
          },
        ]
      },
      {
        path: 'tigerhhzzb/:id/:title', // 提前定义params参数(可以定义多个)
        name: 'Tigerhhzzb',
        component: () => import('@/views/Home/Tigerhhzzb.vue'),
      },
    ]
  },
]


export const router = createRouter({
  // 路由的history模式,共有三种模式,
  // createWebHistory、createWebHashHistory、createMemoryHistory
  // history: createWebHashHistory(),
  history: createWebHistory(),
  // 路由配置
  routes,
  // 是否严格匹配路由
  strict: true,
  // 路由跳转完成后,页面滚动行为
  scrollBehavior: () => ({ left: 0, top: 0 }),
})

3.2、main.ts文件代码:

import './assets/main.css'

import { createApp } from 'vue'
import { createPinia } from 'pinia'

import App from './App.vue'
import {router} from './router/index'

const app = createApp(App)

app.use(createPinia())
app.use(router)

app.mount('#app')

3.3、App.vue文件代码:

<script>

import { defineComponent } from 'vue'
 // vue3.0版本语法
export default defineComponent({
  name: 'App',
})

</script>

<template>

  <RouterView />

</template>

<style>

</style>

3.4、views文件夹下的Home文件夹下的index.vue文件代码:

<template>
  <div class="home">
    <h2>首页{{ title }}</h2>
    <!-- 模拟有权限时显示 -->
    <div v-if="roles.includes(role)">
      <h2>嵌套路由</h2>
      <router-link to="/home/tigerhhzz">push跳转到/home/tigerhhzz页面</router-link>
      <br>
      <!-- 加了/就要写全 /home/lxb -->
      <router-link replace to="/home/tigerhhzzb/id:2/title:102">push跳转到/home/tigerhhzzb页面</router-link>

      <router-view></router-view>
    </div>
  </div>
</template>

<script lang="ts">
import { defineComponent, reactive, onMounted, toRefs, } from 'vue'
import { useRoute, useRouter } from 'vue-router'

export default defineComponent({
  name: 'Homeindex',
  setup() {
    const router = useRouter()
    const route: any = useRoute()

    const state = reactive({
      title: '',
      role: '', // 我的当前角色
      roles: [''],
      routerGo: (path) => {
        if (path === 'lx') {
          // query传参可以用path 也可以用name: Lx
          router.push({
            path: path,
            query: {
              title: '101',
              id: 1
            }
          })
          // router.replace
        } else {
          // params传参只能用name
          router.replace({
            // path: path + '/id:2/title:102',
            name: 'Lxb',
            params: {
              title: '102',
              id: 2
            }
          })
        }
      },
    })
    onMounted(() => {
      console.log('/home', route)
      state.title = route.meta.title
      state.roles = route.meta.roles
      // 模拟一个接口
      setTimeout(() => {
        const res = {
          code: 200,
          data: {
            token: '123456',
            userName: '吴彦祖',
            role: 'admin'
          }
        }
        state.role = res.data.role
      }, 0)
    })
    return {
      ...toRefs(state)
    }
  }
})
</script>

<style>
.home {
  color: pink;
  font-size: 14px;
}
</style>

3.5、views文件夹下的Home文件夹下的Tigerhhzzb.vue文件代码:

<template>
  <div style="font-size: 14px;">
    <h2>我是练习b{{ route?.params?.title }}页面</h2>
    <div>id:{{ route?.params?.id }}</div>
    <button @click="routerGoBack">返回首页</button>
  </div>
</template>

<script lang="ts">
import { defineComponent, onMounted, reactive, toRefs } from 'vue'
import { useRoute, useRouter } from 'vue-router'

// vue3.0语法
export default defineComponent({
  name: 'Tigerhhzzb',
  setup() {
    const route = useRoute()
    const router = useRouter()
    const state: any = reactive({
      routerGoBack: () => {
        router.replace('/home')
        // 由replace跳转进来的不可以使用router.go(-1) 路由栈是空的》回不到上一个路由
      },
    })

    onMounted(() => {
      console.log(route)
    })

    return {
      route,
      ...toRefs(state)
    }
  },
})
</script>

3.6、views文件夹下的Home文件夹下的T.vue文件代码:

<template>
  <div style="font-size: 14px;">
    <h2>我是练习{{ title }}页面</h2>
    <div>id:{{ id }}</div>
    <div>props: {{ props }}</div>
    <button @click="routerGoBack">返回上一页</button>
    <br>
    <button @click="routerGo('/home/lx/childA')">去子路由childA</button>
    <!-- <router-view></router-view> -->
    <router-view />
  </div>
</template>

<script lang="ts">
import { defineComponent, onMounted, reactive, toRefs } from 'vue'
import { useRoute, useRouter } from 'vue-router'

// vue3.0语法
export default defineComponent({
  name: 'Tigerhhzz',
  props: {
    id: {
      type: String,
      default: ''
    },
    title: {
      type: String,
      default: ''
    },
  },
  setup(props) {
    const route = useRoute()
    const router = useRouter()
    const state: any = reactive({
      id: '',
      title: '',
      routerGoBack: () => {
        router.go(-1) // go(-1)回到上一个路由
        // 也可以用router.replace('/home')跳回指定页
      },
      routerGo: (path) => {
        router.push(path)
      }
    })

    onMounted(() => {
      console.log('lx route', route)
      console.log('lx props', props)
      if (route.query) {
        state.id = route.query.id
        state.title = route.query.title
      }
    })

    return {
      props,
      ...toRefs(state)
    }
  },
})
</script>

3.7、views文件夹下的Home文件夹下的ChildA.vue文件代码:

<template>
    <div style="font-size: 14px;background: skyblue;">
      <h3>我是ChildA组件</h3>
      <h3>route.query:{{ route.query }}</h3>
    </div>
  </template>
  
  <script lang="ts">
  import { defineComponent, onMounted, } from 'vue'
  import { useRoute, useRouter } from 'vue-router'
  // vue3.0语法
  export default defineComponent({
    name: 'ChildA',
    setup() {
      const router = useRouter()
      const route = useRoute()
      function goBack() {
        router.go(-1)
      }
      onMounted(() => {
        console.log(route)
      })
      // 可以在页面销毁前清除事件
      // onUnmounted(() => {
      //   proxy.$mittBus.off('mittUserA')
      // })
      return {
        route, goBack
      }
    },
  })
  </script>

4、测试效果

  • 初始页面效果:
    在这里插入图片描述
  • 先点击push跳转到/home/tigerhhzzb页面>(嵌套一层的路由)页面效果:
    嵌套一层的路由从原本/home跳入了/home/tigerhhzzb 子路由页面,点击回到首页。
    在这里插入图片描述
  • 再点击push跳转到/home/tigerhhzz页面>(嵌套多层的路由)页面效果:
    在这里插入图片描述
  • 子路由效果:

先去到了第一层/home/tigerhhzz子路由页面,

再点击去子路由childA按钮>页面效果:

进到了嵌套的第二层/home/tigerhhzz/childA子路由页面
在这里插入图片描述
点击可返回上一页/home/lx 再点击可回到/home首页。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/254634.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

生命在于学习——TV电视盒子渗透测试抓包设置

一、前言 封面图是示例图&#xff0c;因为涉及到保密&#xff0c;所以本次测试的电视盒子不放出外观和设置界面。 这一次要测试电视盒子&#xff0c;大家也都知道&#xff0c;市面上的电视盒子大部分都是Android&#xff0c;当然&#xff0c;要使用笔记本去抓电视盒子的数据包…

圣诞节来了,为大家送上专属圣诞树

Hello大家好&#xff0c;我是Dream。 今天给大家分享一下我很早之前做过的圣诞树&#xff0c;分享给大家&#xff0c;希望可以帮助到大家度过一个浪漫的圣诞节~ Python打造专属于你的圣诞树落叶雪花背景音乐浪漫弹窗 五合一版圣诞树 一、背景故事圣诞节风波❤️❤️❤️ 二、五…

针对海量数据的存储与访问瓶颈的解决方案

背景 在当今这个时代&#xff0c;人们对互联网的依赖程度非常高&#xff0c;也因此产生了大量的数据&#xff0c;企业视这些数据为瑰宝。而这些被视为瑰宝的数据为我们的系统带来了很大的烦恼。这些海量数据的存储与访问成为了系统设计与使用的瓶颈&#xff0c;而这些数据往往存…

内网BUG管理系统本地部署并结合内网穿透实现异地远程访问

文章目录 前言1. 本地安装配置BUG管理系统2. 内网穿透2.1 安装cpolar内网穿透2.2 创建隧道映射本地服务3. 测试公网远程访问4. 配置固定二级子域名4.1 保留一个二级子域名5.1 配置二级子域名6. 使用固定二级子域名远程 前言 BUG管理软件,作为软件测试工程师的必备工具之一。在…

Windows如何安装使用TortoiseSVN客户端并实现公网访问本地SVN Server

文章目录 前言1. TortoiseSVN 客户端下载安装2. 创建检出文件夹3. 创建与提交文件4. 公网访问测试 前言 TortoiseSVN是一个开源的版本控制系统&#xff0c;它与Apache Subversion&#xff08;SVN&#xff09;集成在一起&#xff0c;提供了一个用户友好的界面&#xff0c;方便用…

泛型深入理解

泛型的概述 泛型&#xff1a;是JDK5中引入的特性&#xff0c;可以在编译阶段约束操作的数据类型&#xff0c;并进行检查。 泛型的格式&#xff1a;<数据类型>; 注意&#xff1a;泛型只能支持引用数据类型。 集合体系的全部接口和实现类都是支持泛型的使用的。 泛型的…

周周清(3)

周一&#xff1a; 写了一道算法题&#xff0c;然后由于身体原因&#xff0c;在宿舍休息了很久&#xff1b;然后还是完成了一道算法题&#xff1a;写了一道LRC缓存题&#xff0c;之前就开始写了&#xff0c;写了很久&#xff0c;每次都开始动笔&#xff0c;刚开始用的是队列加m…

太阳能电池效能IV测试PV检测太阳光模拟器

目录 概述 一、系统组成 产品特点&#xff1a; 技术参数 数字源表 本系统支持Keithley24xx系列源表 标准太阳能电池 低阻测试夹具 自动化测试软件 概述 太阳能光伏器件的所有性能表征手段中&#xff0c;IV特性测试无疑是最直观、最有效、最被广泛应用的一种…

智能配电房运维

智能配电房运维是指利用先进的信息化技术&#xff0c;依托电力智慧运维工具-电易云&#xff0c;对配电房的电气运行设备进行实时在线监测、集中监控和故障诊断处理&#xff0c;以提高设备维护效率、降低停电损失、提高用电效益&#xff0c;并消除用户终端配电系统的安全隐患。 …

进来看!企业有效监管员工工作微信的总要性

随着社交媒体的普及和信息传播的便捷化&#xff0c;员工在工作间隙利用微信进行交流已经成为一种常见的现象。然而&#xff0c;这种行为也引发了企业对员工微信监管的需求。 首先&#xff0c;企业监管员工微信可以帮助确保企业对内部信息的保密和安全。通过监管员工微信&#…

演讲回顾:半导体设计中的数字资产管理最佳实践

近日&#xff0c;在广州举行的中国集成电路设计业2023年会&#xff08;ICCAD 2023&#xff09;上&#xff0c;龙智资深顾问、技术支持部门负责人李培将带来主题演讲“半导体设计中的数字资产管理”&#xff0c;聚焦数字资产管理的两个层面——文件级别的管理和更高抽象层次的管…

Kotlin 笔记 -- Kotlin 语言特性的理解(二)

都是编译成字节码&#xff0c;为什么 Kotlin 能支持 Java 中没有的特性&#xff1f; kotlin 有哪些 Java 中没有的特性&#xff1a; 类型推断、可变性、可空性自动拆装箱、泛型数组高阶函数、DSL顶层函数、扩展函数、内联函数伴生对象、数据类、密封类、单例类接口代理、inter…

每日一练2023.12.18——天梯赛的善良【PTA】

题目链接&#xff1a;L1-079 天梯赛的善良 题目要求&#xff1a; 天梯赛是个善良的比赛。善良的命题组希望将题目难度控制在一个范围内&#xff0c;使得每个参赛的学生都有能做出来的题目&#xff0c;并且最厉害的学生也要非常努力才有可能得到高分。 于是命题组首先将编程能…

「Vue3面试系列」Vue3.0的设计目标是什么?做了哪些优化?

文章目录 一、设计目标更小更快更友好 三、优化方案源码源码管理TypeScript 性能语法 API逻辑组织逻辑复用 参考文献 一、设计目标 不以解决实际业务痛点的更新都是耍流氓&#xff0c;下面我们来列举一下Vue3之前我们或许会面临的问题 随着功能的增长&#xff0c;复杂组件的代…

【Cocos Creator】vscode 保存代码自动编译

使用Cocos Creator的时候&#xff0c;之前每次修改代码&#xff0c;都要到编辑器界面点击刷新按钮&#xff0c;感觉有些麻烦&#xff0c;搜索引擎上找到的解决方案都比较麻烦&#xff0c; 最后在vscode&#xff0c;刚好找到一款插件–Cocos Creator Devtools。 cocos-creator-…

盲盒扭蛋机小程序,科技与传统的完美结合

盲盒扭蛋具有着较大的粉丝群体&#xff0c;成为一大商业模式。扭蛋机与盲盒具有一样的特征&#xff0c;不确定性、未知性&#xff0c;深深吸引着消费者。 传统的扭蛋机一般活跃于各大商场中&#xff0c;深受不同年龄层人的喜欢。但随着互联网技术的完善&#xff0c;相对于线下…

Kafka消息延迟和时序性详解(文末送书)

目录 一、概括1.1 介绍 Kafka 消息延迟和时序性1.1.1 什么是 Kafka 消息延迟&#xff1f;1.1.2 为什么消息延迟很重要&#xff1f;1.1.3 什么是 Kafka 消息时序性&#xff1f;1.1.4 消息延迟和时序性的关系 1.2 延迟的来源1.2.1 Kafka 内部延迟 二、衡量和监控消息延迟2.1 延迟…

解决 Hbuilder打包 Apk pad 无法横屏 以及 H5 直接打包 成Apk

解决 Hbuilder打包 Apk pad 无法横屏 前言云打包配置 前言 利用VUE 写了一套H5 想着 做一个APP壳 然后把 H5 直接嵌进去 客户要求 在pad 端 能够操作 然后页面风格 也需要pad 横屏展示 云打包 配置 下面是manifest.json 配置文件 {"platforms": ["iPad"…

docker consul容器的自动发现与注册

目录 什么叫做微服务&#xff08;容器&#xff09;注册于发现 docker consul数据流程图 服务注册于发现的优点 什么是consul&#xff1f; consul的主要特点 Consul部署和服务发现 架构 docker1 docker2 实现管理配置自动化 作用 自动化更新配置文件 配置template并…

01|LangChain系统安装和快速入门

01&#xff5c;LangChain系统安装和快速入门 什么是大语言模型 大语言模型是一种人工智能模型&#xff0c;通常使用深度学习技术&#xff0c;比如神经网络&#xff0c;来理解和生成人类语言。这些模型的“大”在于它们的参数数量非常多&#xff0c;可以达到数十亿甚至更多&am…