理解 vue-router 实现原理

  • 实现插件
  • url变化监听
  • 路由配置解析: {‘/’: Home}
  • 实现全局组件:router-link router-view
import Vue from "vue";
// 实现插件 
// url变化监听 
// 路由配置解析: {‘/’: Home} 
// 实现全局组件:router-link router-view
class VueRouter {
    constructor(options) {
        this.$options = options
        // 解析后的路由
        this.routeMap = {}

        // 实现路由响应式
        this.app = new Vue({
            data: {
                current: '/'
            }
        })
    }

    init() {
        this.bindEvents()// 监听url
        this.createRouteMap(this.$options)// 解析路由配置
        this.initComponent()// 实现两个组件
    }

    bindEvents() {
        window.addEventListener('load', this.onHashChange.bind(this))
        window.addEventListener('hashchange', this.onHashChange.bind(this))
    }

    onHashChange() {
        this.app.current = window.location.hash.slice(1) || '/'
    }

    createRouteMap(options) {
        options.routes.forEach(item => {
            this.routeMap[item.path] = item.component
        })
    }

    initComponent() {
        // <router-link to='/about'>About</router-link>
        Vue.component('router-link', {
            props: { to: String, required: { type: Boolean, default: true } },
            render(h) {
                return h('a', { attrs: { href: '#' + this.to } }, [
                    this.$slots.default
                ])
            }
        })
        // <router-view></router-view>
        Vue.component('router-view', {
            render: (h) => {
                const comp = this.routeMap[this.app.current]
                return h(comp)
            }
        })
    }
}
VueRouter.install = function (Vue) {
    // 混入
    Vue.mixin({
        beforeCreate() {
            // this是vue实例
            if (this.$options.router) {
                // 仅在根组件执行一次
                Vue.prototype.$router = this.$options.router
                this.$options.router.init()
            }
        }
    })
}
Vue.use(VueRouter);

export default new VueRouter({
    routes: [{ path: "/", component: Home }, { path: "/about", component: About }]
});
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • vue路由的使用 vue-router是Vue.js官方的路由插件,它和vue.js是深度集成的,适合用于构建单页...
    赵客缦胡缨v吴钩霜雪明阅读 940评论 0 17
  • 回忆: 我们知道,h5的history或者hash帮助我们解决了,变化url跳转页面不发送请求,并且我们能监听到u...
    LoveBugs_King阅读 3,677评论 0 5
  • 那这次呢?我决定直接就先放一个小小demo上来 其实我们在引入vue-router插件那一刻,我们的网页就已经附带...
    看物看雾阅读 847评论 0 1
  • 介绍 vue-router是一个vue插件。其实质是在location.hash、location.replace...
    AmazRan阅读 1,597评论 0 6
  • 前言 vue-router是什么:是vue.js官方的路由管理器和vue.js的核心深度的集成,让开发者更加简单的...
    GUAN_one阅读 3,753评论 0 2