Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

vue-router原理 #3

Open
spring-fe opened this issue Jan 2, 2019 · 0 comments
Open

vue-router原理 #3

spring-fe opened this issue Jan 2, 2019 · 0 comments

Comments

@spring-fe
Copy link
Owner

spring-fe commented Jan 2, 2019

SPA前端路由

路由模块的本质 就是建立起url和页面之间的映射关系。

路由2种实现方式

  1. window.history
  2. location.hash

window.history

history interface是浏览器历史记录栈提供的接口,通过back(),forward(),go()等方法,可以读取浏览器历史记录栈的信息,进行跳转。
1.在HTML5,history对象增加了pushState()方法和replaceState()方法,这两个方法可以向历史栈中添加记录,就好像url变了一样(之前只有url变化历史栈才会变化),这样可以模拟浏览历史。
2.popstate事件
每当

location.hash

特征:
1.hash('#')本身的作用是在URL中指定网页中的位置
2.监听hash改变的监听事件
window.addEventListener("hashchange", funcRef, false)
3.每一次改变hash(window.location.hash),都会在浏览器的访问记录中增加一个记录
基于以上特征,可以实现前端路由。

实现

<a class="api a">a.html</a>
<a class="api b">b.html</a>

history模式

模拟单页面路由
1.首先绑定click事件。用户点击一个链接时,通过preventDefault函数防止默认行为(页面跳转)。同时读取链接地址,通过pushSate放入浏览器记录中,并且更新网页内容。
2.为了处理前进、后退,监听popstate事件。当用户点击前进或后退按钮时,浏览器自动被替换成相应的地址,同时触发popstate事件。在事件处理函数中,更新网页内容。

    // 注册路由
    document.querySelectorAll('.api').forEach(item => {
      item.addEventListener('click', e => {
        e.preventDefault();
        let link = item.textContent;
        if (!!(window.history && history.pushState)) {
          // 支持History API
          window.history.pushState({name: 'api'}, link, link);
          ... // 更新页面
        } else {
          // 不支持,可使用一些Polyfill库来实现
        }
      }, false)
    });

    // 监听路由
    window.addEventListener('popstate', e => {
      ... // 更新页面
      console.log({
        location: location.href,
        state: e.state
      })
    }, false)

hash模式

    // 注册路由
    document.querySelectorAll('.api').forEach(item => {
      item.addEventListener('click', e => {
        e.preventDefault();
        let link = item.textContent;
        location.hash = link;
      }, false)
    });

    // 监听路由
    window.addEventListener('hashchange', e => {
     ... // 更新页面
      console.log({
        location: location.href,
        hash: location.hash
      })
    }, false)

总结

实现单页面条件
1.url内容和显示页面内容关联
2.url内容改变页面不刷新
3.记录url历史,用于前进回退

[1] https://juejin.im/post/5b0281b851882542845257e7
[2] https://juejin.im/post/5abf2f44f265da238925da22
[3] https://zhuanlan.zhihu.com/p/27588422
[4] muwoo/blogs#22

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant