vue-router部分源码

分析路由模式Hash、History

单页应用(SinglePage Application,SPA)**

指只有一个主页面的应用,一开始只需加载一次 js,css 等相关资源。所有的内容都包含在主页面,对每一个功能模块组件化。单页应用跳转,就是切换相关组件,仅刷新局部资源。比如vue
在这里插入图片描述

多页应用(MultiPage Application,MPA)

指有多个独立的页面的应用,每个页面必须重复加载 js,css 等相关资源。多页应用跳转,需要整页资源刷新。
在这里插入图片描述
在这里插入图片描述

前端路由模式

前端路由的核心:改变视图的同时不会向后端发出请求。

hash 模式

例子:http://music.163.com/#/friend

hash 模式背后的原理是 onhashchange 事件。

window.addEventListener(hashchange ,function(e){
   console.log(e.oldURL);
   console.log(e.newURL)
},false);

通过 window.location.hash 属性获取和设置 hash 值。

由于 hash 发生变化的 url 都会被浏览器记录下来,所以浏览器的前进后退可以使用,尽管浏览器没有请求服务器,但是页面状态和 url 关联起来。后来人们称其为前端路由,成为单页应用标配。

hash 模式的特点在于 hash 出现在 url 中,但是不会被包括在 HTTP 请求中,对后端没有影响,不会重新加载页面

history模式

随着history api的到来,前端路由开始进化了,前面的hashchange,你只能改变#后面的url片段,而history api则给了前端完全的自由
用了HTML5 History Interface中新增的pushState()和replaceState()方法。(需要特定浏览器支持)

这两个方法应用于浏览器的历史记录栈,在当前已有的back、forward、go的基础上,它们提供了对历史记录进行修改的功能。只是当它们执行修改时,虽然改变了当前的URL,但浏览器不会即向后端发送请求。

通过history api,我们丢掉了丑陋的#,但是它也有个毛病:

不怕前进,不怕后退,就怕刷新,f5,(如果后端没有准备的话),因为刷新是实实在在地去请求服务器的,不玩虚的。

在hash模式下,前端路由修改的是#中的信息,而浏览器请求时是不带它玩的,所以没有问题.但是在history下,你可以自由的修改path,当刷新时,如果服务器中没有相应的响应或者资源,会分分钟刷出一个404来。

入口文件分析

  1. 说明VueRouter是一个插件,所以实现过程中需要使用install方法来实现一个插件。
  2. 说明VueRouter是一个类,所以实现过程中需要创建一个类,然后构造函数需要接收传过来的参数。
    在这里插入图片描述

二, 实现过程剖析。

实现插件:

我们使用Vue的mixin ,这样可以在组件的钩子函数beforeCreate生命周期在Vue的原型上挂载router,这也是为什么在vue中到处都可以使用this.$ router的原因。router是从this.$ options取的,vue的执行是组件的一个个渲染的过程。并不是每一个组件都可以从this.$ options 拿到router ,只有在跟组件中在可以拿到,所以加判断 拿到了router对象,才将其挂载在原型上。

在这里插入图片描述
接下来我们实现router-link组件.我们使用render函数来渲染。router-link 实际上是a标签,然后加上属性,跳转就可以实现了。所以我们使用props的to属性,来接收外部传过来的值,我们用render方法的h这个参数来渲染。this.slots.default可以拿到子组件的内容。

在这里插入图片描述

  1. router-view和 router-link差不多,都是在render函数里面去用h方法来渲染。router-view的实现,只需拿到当前路由的路由表的component在渲染出去就行了。所以我们先拿到当前的路由。

  2. 监听hashchange方法,当路由改变切换时获取hash值,然后用current这个值来接收。

  3. 我们在VueRouter的类的构造函数中,使用Vue.util.defineReactive这个方法,让数据变成响应式的,这样我们拿到的this.current就是最新的,所谓响应式属性,即当current值改变时,会自动调用Vue实例的render()方法,更新视图

在这里插入图片描述
经过以上三步的操作,我们在install方法中 就可以用this.$router获取current属性,也就是当前的路由。我们遍历路由表,然后找出当前的路由的对象,拿到component,然后渲染出去
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值