vue-router

这里的路由就是SPA(单页应用)的路径管理器

路由用于设定访问路径,并将路径和组件映射起来

单页面应用(SPA)的核心之一是: 更新视图而不重新请求页面

1、Hash模式:

vue-router 默认 hash 模式 —— 使用 URL 的 hash 来模拟一个完整的 URL,于是当 URL 改变时,页面不会重新加载。

可以通过location.hast取得#后面的路由

window.onhashchange=functioin(){} //当hash路由改变时候触发

2、History模式:

这种模式充分利用 history.pushState API 来完成 URL 跳转而无须重新加载页面。

location.pathname 取得路由地址

onpopstate来监听history的路由变化

3、使用路由模块来实现页面跳转的方式

方式1:直接修改地址栏

方式2:this.$router.push(‘路由地址’)

方式3:<router-link to="路由地址"></router-link>

4、实现方式

Vue.use(VueRouter)

  1. 执行VueRouter方法
  2. 如果这个方法有一个属性 install 并且这个属性是一个方法 就会执行install这个方法 例如 (VueRouter.install=function(){})
  3. install这个方法的第一个参数 是vue

5、手写router

//router的index文件

import  VueRouter from '../myrouter/index'
import  Vue from 'vue'

const register =() =>import('../src/register')
const home =()=>import('../src/home')

Vue.use(VueRouter)

const routes=[
    {
        path: '/register',
        name: '注册',
        component: register,
        title: '注册',
      }, {
        path: '/',
        name: '首页',
        component: home,
        title: '注册',
      },
   
   
]

const router = new VueRouter({
    routes
  })

export default router
//实现VueRouter实例 hash模式实现

let Vue

//注册一个类
class VueRouter{
    constructor(options)
    {
        console.log(options);

        let initPath='/' //默认值
        Vue.util.defineReactive(this,'current',initPath) //this指向VueRouter  响应式
        this.current='/' //当前路由
        this.routes=options.routes//用户路由规则
        this.mode=options.mode||'hash' //默认hash
        this.init() //监听路由改变
        
    }
    init()
    {
     
        if(this.mode=='hash'){
            console.log(location.hash); //拿到hash模式下的hash地址

            //监听第一次加载项目要加/#/
            window.addEventListener('load',()=>{
                this.current=location.hash.slice(1)
    
            })
            //监听路由改变
            window.addEventListener('hashchange',()=>{
                this.current=location.hash.slice(1)
            })
        }
    }
}

VueRouter.install=function(_Vue){
        Vue=_Vue

        //给调用组件添加一个属性  router
        Vue.mixin({  
            //全局添加数据和方法  vue3改为compostions api
            //每一个实例都是一个 $options api 例如app.vue 和main.js 里面的都是一个实例
            beforeCreate() {
                console.log(this.$options.name);
                if(this.$options.router)//根组件上才有的属性
                {
                    Vue.prototype.$router=this.$options.router //在Vue实例原生链上添加属性 实现全局添加this.$router属性
                }
            },
        })

        //创建全局组件
        //router-link 
        Vue.component('router-link',{
            //传参过来
            props:{
              to:{
                  type:String,
                  require:true
              }
            },
            render(h) {
                return h('a',{attrs:{
                    href:"#"+this.to
                }},this.$slots.default)//创建html的内容 就是插槽里面的内容
            },
        }),


        Vue.component('router-view',{
            //必须是响应式数据才能触发
            render(h) {

                //当前路由
                let current =this.$router.current
                console.log(current);
                //获取到了配置的路由数组  然后通过上面的取出对应的路由模块并且渲染出来
                let routers=this.$router.routes
                console.log(routers);

                //找出匹配的数组项
                let com=routers.find(item=>{
                    return current==item.path
                })
                console.log(com);
                return h(com.component)//创建html
            },
        })
}


export default  VueRouter
//App.vue 文件

<template>
  <div id="app">


<div class="tolink">
    <router-link to='/register'>注册</router-link>
    <router-link to='/'>home</router-link>
   
</div>
   <div>
      <router-view></router-view>
    </div>
  </div>
</template>

<script>

export default {
  name: 'App',
  beforeCreate() {
    console.log(this.$router);
  },
  data() {
    return {
  
    }
  },
 


}
</script>

<style>
.tolink{
  width: 40%;
  margin: auto;
  display: flex;
  justify-content:space-between;
}
</style>

实现效果