vue3+ts+vite 路由详解

 安装

1.首先创建项目

npm init vite@latest

 输入文件名,选择Vue、TypeScript


2.vscode打开项目,安装router,less,less-loader,@types/node

npm i vue-router -S
npm i less less-loader -S
npm i @types/node -D
npm install pinia
npm install animate.css --save

*注意 Vue3中router要安装4版本,3版本的router语法和4不一样。

3.在components中创建login.vue和register.vue文件






4.在src下创建router文件夹,创建index.ts文件

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    component: () => import("../components/login.vue"),
  },
  {
    path: "/register",
    component: () => import("../components/register.vue"),
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;

5.在main.ts中引入并注册router

import { createApp } from "vue";
import App from "./App.vue";
// 引入router
import router from "./router";
// .ues(router) 注册router
createApp(App).use(router).mount("#app");

6.在app.vue中写路由出口才能显示路由页面






 vue3+ts+vite 路由详解_第1张图片

 路由模式

vue3+ts+vite 路由详解_第2张图片

 vue3+ts+vite 路由详解_第3张图片

 命名路由

1.将router下index.ts文件里的路由命名

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    // 命名
    name: "Login",
    component: () => import("../components/login.vue"),
  },
  {
    path: "/register",
    // 命名
    name: "Register",
    component: () => import("../components/register.vue"),
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;

2.app.vue中使用






编程式导航






路由传参

*注意下载 JSON to TS 插件,选中json文件(ctrl+shift+alt+s)可以转为ts文件

1.path,query传参











2.name,params传参

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    name: "Father",
    component: () => import("../components/father.vue"),
  },
  {
    // 因为params传参是保存在内存中,所以接收参数的页面刷新会丢失数据
    // params传参需要配合动态路由参数一起使用就不会有上面的问题
    path: "/child/:id",
    name: "Child",
    component: () => import("../components/child.vue"),
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;










嵌套路由

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    // 父路由
    path: "/user",
    component: () => import("../components/father.vue"),
    // 子路由
    children: [
      {
        path: "",
        component: () => import("../components/child1.vue"),
      },
      {
        path: "child2",
        component: () => import("../components/child2.vue"),
      },
    ],
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;





命名视图

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    components: {
      default: () => import("../components/layout/menu.vue"),
      header: () => import("../components/layout/header.vue"),
      content: () => import("../components/layout/content.vue"),
    },
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;





重定向/别名

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    component: () => import("../components/login.vue"),
    // 字符串形式重定向
    // redirect: "/menu",

    // 对象形式重定向
    // redirect: { path: "/menu" },

    // 函数形式重定向
    redirect(to) {
      return {
        path: "/content",
        query: to.query,
      };
    },
    alias: ["/root", "/lala"], // 设置别名(为重定向服务)
    children: [
      {
        path: "/menu",
        components: {
          default: () => import("../components/layout/menu.vue"),
        },
      },
      {
        path: "/content",
        components: {
          aaa: () => import("../components/layout/header.vue"),
          bbb: () => import("../components/layout/content.vue"),
        },
      },
    ],
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;

 配置别名

import { defineConfig } from "vite";
import { fileURLToPath, URL } from "url";
import vue from "@vitejs/plugin-vue";

// https://vitejs.dev/config/
export default defineConfig({
  plugins: [vue()],
  // 配置别名
  resolve: {
    alias: {
      "@": fileURLToPath(new URL("./src", import.meta.url)),
    },
  },
});

注意:如果在vite.config.ts配置别名时,出现 找不到模块“xxx”或其相应的类型声明 这种报错时,需要安装 “@types/node” 模块,处理配置别名不生效的问题

npm i @types/node -D

导航守卫  

loadingBar.vue





 main.ts

import { createApp, createVNode, render } from "vue";
import App from "./App.vue";
import router from "./router";
import ElementUI from "element-plus";
import "element-plus/dist/index.css";
import loadingBar from "./components/loadingBar.vue";
const app = createApp(App);

app.use(router);
app.use(ElementUI);
app.mount("#app");

// 设置白名单(允许直接跳转的路由)
const whileList = ["/"];
// 设置前置守卫
router.beforeEach((to, from, next) => {
  if (whileList.includes(to.path) || localStorage.getItem("token")) {
    next();
    Vnode.component?.exposed?.startLoading();
  } else {
    next("/");
  }
});

const Vnode = createVNode(loadingBar);
render(Vnode, document.body);
console.log(Vnode);

// 设置后置守卫(一般用做导航完成的loading页面)
router.afterEach((to, from) => {
  Vnode.component?.exposed?.endLoading();
});
to: Route, 即将要进入的目标 路由对象;
from: Route,当前导航正要离开的路由;
next(): 进行管道中的下一个钩子。如果全部钩子执行完了,则导航的状态就是 confirmed (确认的)。
next(false): 中断当前的导航。如果浏览器的 URL 改变了 (可能是用户手动或者浏览器后退按钮),那么 URL 地址会重置到 from 路由对应的地址。
next('/') 或者 next({ path: '/' }): 跳转到一个不同的地址。当前的导航被中断,然后进行一个新的导航。

路由元信息

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 定义路由元信息meta的title的类型
declare module "vue-router" {
  interface RouteMeta {
    title: string;
  }
}

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    component: () => import("@/views/login.vue"),
    // 设置路由元信息
    meta: {
      title: "登录页面",
    },
  },
  {
    path: "/register",
    component: () => import("@/views/register.vue"),
    // 设置路由元信息
    meta: {
      title: "注册页面",
    },
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;
import { createApp } from "vue";
import App from "./App.vue";
import router from "./router";
import ElementUI from "element-plus";
import "element-plus/dist/index.css";
const app = createApp(App);

app.use(router);
app.use(ElementUI);
app.mount("#app");

// 设置白名单(允许直接跳转的路由)
const whileList = ["/"];
// 设置前置守卫
router.beforeEach((to, from, next) => {
  // 设置路由元信息
  document.title = to.meta.title;
  if (whileList.includes(to.path) || localStorage.getItem("token")) {
    next();
  } else {
    next("/");
  }
});

路由过度动效

import { createRouter, createWebHistory, RouteRecordRaw } from "vue-router";

// 定义title的类型
declare module "vue-router" {
  interface RouteMeta {
    title: string;
    transition: string;
  }
}

// 路由类型:RouteRecordRaw
const routes: Array = [
  {
    path: "/",
    component: () => import("@/views/login.vue"),
    // 设置路由元信息
    meta: {
      title: "登录页面",
      // 设置路由动效类名(基于animate动画库)
      transition: "animate__bounceIn",
    },
  },
  {
    path: "/register",
    component: () => import("@/views/register.vue"),
    // 设置路由元信息
    meta: {
      title: "注册页面",
      // 设置路由动效类名(基于animate动画库)
      transition: "animate__fadeInUpBig",
    },
  },
];

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,
});

export default router;

app.vue





滚动行为

const router = createRouter({
  // 路由模式
  history: createWebHistory(),
  routes,

  // 滚动行为
  scrollBehavior: (to, from, savePosition) => {
    if (savePosition) {
      return savePosition;
    } else {
      return {
        top: 500,
      };
    }
  },
});

动态路由


const initRouter = async () => {
    const result = await axios.get('http://localhost:9999/login', { params: formInline });
    result.data.route.forEach((v: any) => {
        router.addRoute({
            path: v.path,
            name: v.name,
                                    //这儿不能使用@
            component: () => import(`../views/${v.component}`)
        })
        router.push('/index')
    })
    console.log(router.getRoutes());
 
}

你可能感兴趣的:(vue3,vue.js,前端,typescript,前端框架)