[路飞]-手写一个mini-vueRouter

284 阅读2分钟

这是我参与11月更文挑战的第5天,活动详情查看:2021最后一次更文挑战

写前说明

vueRouter是 Vue.js (opens new window)官方的路由管理器。它和 Vue.js 的核心深度集成,让构建单页面应用变得易如反掌。包含的功能有:

  • 手写代码里使用的是路由的hash模式,未实现路由的嵌套功能,想进一步了解VueRouter的原理可以参考官方源码。
  • 只实现了router—link的to属性,其他属性未实现
  • 实现了router-view的展示效果。嵌套功能未实现

回顾vue-router用法

我们通过使用的过程当中来一步一步实现自己手写的mini-VueRouter的核心功能。

1、实现Vue.use(VueRouter),安装VueRouter插件
   // 需要在Router类中,实现一个静态的install方法,
  static install(_Vue) {
  
  //将Vue提供的参数保存一下以便在其他地方都能用到
   Vue = _Vue;

   Vue.mixin({
     // 在根组件创建前,将router挂载到Vue的原型上,
     // 原因:只有这个生命周期才能取到this
     beforeCreate() {
       if (this.options.router) {
         Vue.prototype.$router = this.options.router;
       }
     },
   });
 }
2、实现new VueRouter({routes})
class Router {
    // 保存配置项
  constructor(options) {
    this.options = options;
  }
}
3.实现router-view让视图展示出来,router-link实现跳转
 使用Vue.component 创建自定义组件
 Vue.component("router-view", {
      render(h) {
        // 获取component
        let component = null;
        
        // 通过Vue的原型取到router里的配置项 ,根据当前页面hash路径匹配对应的组件进行渲染
        let route = this.$router.options.routes.find((route) => {
          if (this.$router.current == route.path) {
            return true;
          }
        });
        component = route.component;
        return h(component);
      },
    });

    Vue.component("router-link", {
      props: {
        to: {
          type: String,
          required: true,
        },
      },
      render(h) {
        // 这里直接当a标签处理了
        return h("a", { attrs: { href: `#${this.to}` } }, this.$slots.default);
      },
    });
  }

4 、router-view组件

tips: 处理页面url变化时,重新渲染,这里用到了Vue.util提供的defineReactive方法来讲当前页面的url变成响应式数据,触发页面重新渲染

 // 这段代码位置在VueRouter的constructor 中
 // 实现url的响应式
    Vue.util.defineReactive(
      this,
      "current",
      window.location.hash.slice(1) || "/"
    );
    //监听路由变化
    window.addEventListener("hashchange", () => {
      let path = window.location.hash.slice(1);
      this.current = path;
    });

 最后,这里只是使用了简单的api实现了路由的跳转功能。我们可以在这个简单的代码实现上进一步完善自己的功能!

结束语

如果您喜欢我的文章,可以[关注⭐]+[点赞👍]+[评论📃],您的三连是我前进的动力,期待与您共同成长~