• vue基础路由篇


    const path = require('path');
    const BASE_URL = process.env.NODE_ENV === 'production' ? './' : '/';
    const resolve = dir => path.join(__dirname,dir);
    module.exports = {
    lintOnSave: false,
    publicPath : BASE_URL,
    chainWebpack : config => {
    config.resolve.alias
    .set('@',resolve('src')) // 配置:用 @ 符号来代替 src 的根目录
    .set('_s',resolve('src/assets/style'))
    },
    //打包时不生成 .map 文件 减小打包体积 缩短打包时间
    productionSourceMap : false,
    devServer : {
    proxy : 'http://localhost:4000'
    }
    }

    上述为配置:后面所有例子都以该配置为主

    一般项目中会把路由文件分为两个部分: 1.配置路由列表文件 2. 创建路由实例文件(需引入vue-router插件)

    // 配置路由列表
    import Home from '@/views/Home.vue'
    export default [
      {
        path: '/', //path 指代路径
        component: Home
      },
      {
        path: '/about',// route level code-splitting
        // this generates a separate chunk (about.[hash].js) for this route
        // which is lazy-loaded when the route is visited.
        component: () => import(/* webpackChunkName: "about" */ '@/views/About.vue')
      },
      {
        path : '/argu/:name',
        component : () => import('@/views/argu.vue')
      }
    ]
    //上面例子概述了两种组件的引入方式 : 第一种 Home 的引入方式 将组件以变量的形式引入 第二种直接在 component 中引入
    // 创建路由实例
    import Vue from 'vue'
    import Router from 'vue-router' // 插件
    import routes from './router'  //引入路由列表文件
    Vue.use(Router)
    export default new Router({
        routes
    })

    实例化一个vue:

    import Vue from 'vue'
    import App from './App.vue'   //引入App组件 赋值给App
    import router from './router' //引入创建路由实例文件 赋值给变量 router
    import store from './store'
    
    Vue.config.productionTip = false
    
    new Vue({
      router,
      render: h => h(App)
    }).$mount('#app') //app为vue渲染的元素
    //App.vue组件
    <template>
      <div id="app">
        <div id="nav">
          <router-link to="/">Home</router-link> |  //router-link封装了一个 a 标签 to指定的值是路径 也就是路由列表中的 path
          <router-link :to="{name : 'about'}">About</router-link>
        </div>
        <router-view/> //视图渲染组件通过 router-link 加载的组件都会在这边渲染
      </div>
    </template>

    动态路由匹配:

    //在配置路由列表中
    {
        path : '/argu/:name',
        component : () => import('@/views/argu.vue') //引入 argue 组件
    },
    //argue组件
    <template>
        <!--$route表示当前加载页面的路由对象 params是参数 name是值-->
        <div>{{$route.params.name}}</div>
    </template>
    <script>
        export default {
            //
        }
    </script>

     嵌套路由:

    //在配置路由列表中
    {
        path : '/parent',
        component : () => import('@/views/parent.vue'),
        children : [  //嵌套子组件
          {
            path : 'child',//子组件路径不需要加 '/'
            component : () => import('@/views/child.vue')
          }
        ]
    }
    <!-父组件-->
    <template>
        <div>
            I am parent
            <router-view/>
        </div>
    </template>
    <script>
        export default {
            // name: "parent"
        }
    </script>
    <!--子组件-->
    <template>
        <div>I am child</div>
    </template>
    <script>
        export default {
            // name: "child"
        }
    </script>

    命名路由 :

          <!--命名路由 name值与路由列表中的name值对应-->
          <router-link :to="{name : 'about'}">About</router-link> 
    //在配置路由列表中配置(router.js)
    {
        path: '/about',
        name: 'about',
        // route level code-splitting
        // this generates a separate chunk (about.[hash].js) for this route
        // which is lazy-loaded when the route is visited.
        component: () => import(/* webpackChunkName: "about" */ '@/views/About.vue')
      }

    命名视图:(同一个页面上显示多个视图)

        <router-view/>
        <!--命名视图-->
        <router-view name="email"/>
        <router-view name="tel"/>
      {
        path: '/name_view',
        components:{
          default: () => import('@/views/child.vue'),
          email: () => import('@/views/email.vue'),
          tel: () => import('@/views/tel.vue'),
        }
      }

    注意:路由列表中组件的优先级是由上而下的,上面的优先级较高

    前置守卫:

    // 创建路由实例
    import Vue from 'vue'
    import Router from 'vue-router' // 插件
    import routes from './router'  //引入路由列表文件
    
    Vue.use(Router)
    
    const router = new Router({
        mode : 'history',//默认hash模式
        routes
    })
    //实例化一个登录页面
    const HAS_LOGINED = true  // 做一个简单的判断 是否登录
    //注册一个全局前置守卫
    //to 即将跳转页面的路由对象 from当前操作的路由对象 next时一个函数
    router.beforeEach((to,from,next) => {
        if(to.name !== 'login'){//如果即将跳转的页面不是登录页面
            //判断是否登录 如果已经登录直接执行 next() 跳转
            if(HAS_LOGINED) next()
            //如果没有登录直接执行 next() 跳转到 login 页面
            else next({name : 'login'})
        }else{
            if(HAS_LOGINED) next({name : 'home'})
            else next()
        }
    })
    export default router
    //在配置路由列表中配置(router.js)
      {
        path : '/login',
        name : 'login',
        component: () => import(/* webpackChunkName: "about" */ '@/views/login.vue')
      },
    //login.vue文件
    <template>
        <div>login-page</div>
    </template>
    <script>
        export default {
            name: "login"
        }
    </script>

    组件独享守卫:

     {
        path: '/',
        name: 'home',
        component: Home,
        //to 即将跳转页面的路由对象 from当前操作的路由对象 next时一个函数
        beforeEnter : (to,from,next) => {
          if(from.name === 'about') alert('这是由about页面跳转来的')
          else alert('这不是由about页面跳转来的')
          next()
        }
      }

    在组件内使用守卫:

    <template>
      <div class="home">
        <img alt="Vue logo" src="@/assets/image/logo.png">
        <HelloWorld msg="Welcome to Your Vue.js App"/>
        <button @click="hendleClick">返回上一页</button>
      </div>
    </template>
    
    <script>
    // @ is an alias to /src
    import HelloWorld from '@/components/HelloWorld.vue'
    
    export default {
      name: 'home',
      components: {
        HelloWorld
      },
      beforeRouteEnter(to,from,next){
        alert(to.name + from.name)
        next()
      },
      //多用在文本编辑 
      beforeRouteLeave(to,from,next){
        const leave = confirm('您确定要离开吗')
        if(leave) next()
        else next(false)
      },
      methods: {
        hendleClick: function () {
          this.$router.back()
        }
      }
    }
    </script>

    完整的导航解析流程:

      1. 导航被触发

      2. 在失活的组件(即将离开的组件)里调用离开守卫 beforeRouteLeave

      3.调用全局的前置守卫 beforeEach

      4.在重用的组件里调用 beforeRouteUpdate

      5.调用路由独享的守卫 beforeEnter

      6.解析异步路由组件

      7.在被激活的组件(即将进入的组件)里调用 beforeRouteEnter

      8.调用全局的解析守卫 

      9. 导航被确认

      10. 调用全局的后置守卫

      11.触发DOM更新

  • 相关阅读:
    OC
    提取AppDelegate.m中的"RDVTabBarController"第三方框架的方法
    spring_aop
    spring_xml配置&依赖注入
    关于idea运行web项目时出现的浏览器问题
    Java中main方法参数类型个人粗略理解
    函数式编程_lambda
    反射_注解
    pl/sql使用小技巧
    触发器&索引&视图
  • 原文地址:https://www.cnblogs.com/rickyctbur/p/11623696.html
Copyright © 2020-2023  润新知