前端路由hash和history

什么是前端路由

简单地说,就是在保证只有一个html页面,且在和用户交互时,不刷新和跳转页面的同时,为单页面(SPA)中的每个视图展示**匹配一个特殊的url,**在刷新,前进后退时都通过这个特殊的url来实现

hash模式

hash模式中的hash就是指#号及其后面的字符,比如’www.baidu.com/#hash’,其中#hash就是hash值, hash通过监听浏览器的onhashchange()事件来实现路由的变化,如果我们在window.hashChange事件中获取当前的hash值,并根据hash值来修改页面的内容,就达到了前端路由的目的,并且hash 值的变化不会导致浏览器向服务器发送请求

<body>
  <!-- html:菜单中href设置为hash形式,id为app中放置页面内容 -->
  <ul id="menu">
    <li>
      <a href="#index">首页</a>
    </li>
    <li>
      <a href="#shop">商城</a>
    </li>
    <li>
      <a href="#my">我的</a>
    </li>

  </ul>

  <div id="app"></div>
  <script>
    //在window.onhashchange中获取hash值,根据不同的值,修改app中不同的内容,起到了路由的效果
    function hashChange(e) {
      console.log('hash值',location.hash)
      console.log('herf值',location.href)
      console.log('新路径',e.newURL)
      console.log('旧路径',e.oldURL)
      let app = document.getElementById('app')
      switch (location.hash) {
        case '#index':
          app.innerHTML = '<h1>这是首页内容</h1>'
          break
        case '#shop':
          app.innerHTML = '<h1>这是商城内容</h1>'
          break
        case '#my':
          app.innerHTML = '<h1>这是我的内容</h1>'
          break
        default:
          app.innerHTML = '<h1>404</h1>'
      }
    }
    window.onhashchange = hashChange
    hashChange()

  </script>
</body>

history模式

history就是我们平时看到的正常的连接形式。history模式基于window.history对象的方法。相较于hash模式样式上少个#
在html4中,已经支持window.history对象来控制页面历史记录跳转,常用的方法包括:
history.forward():在历史记录中前进一步
history.back():在历史记录中后退一步
history.go(n):在历史记录中跳转n步骤,n=0为刷新本页,n=-1为后退一页
在HTML5中,window.history对象得到了扩展,新增的API包括:
history.pushState(data[,title][,url]):向历史记录中追加一条记录
history.replaceState(data[,title][,url]):替换当前页在历史记录中的信息。
history.state:是一个属性,可以得到当前页的state信息。
window.onpopstate:是一个事件,在点击浏览器后退按钮或js调用forward()、back()、go()时触发。监听函数中可传入一个event对象,event.state即为通过pushState()或replaceState()方法传入的data参数

如果用户使用浏览器的前进后退按钮,则会触发window.onpopstate事件,监听页面根据路由地址修改页面内容。

<body>
  <!-- html:菜单中href设置为history形式,id为app中放置页面内容 -->
  <ul id="menu">
    <li>
      <a href="/index">首页</a>
    </li>
    <li>
      <a href="/shop">商城</a>
    </li>
    <li>
      <a href="/my">我的</a>
    </li>

  </ul>

  <div id="app"></div>
  
  <script>
    //js:
    //改造超链接,阻止默认跳转,默认的跳转是会刷新页面的
    document.querySelector('#menu').addEventListener('click', function (e) {
      console.log('e',e);
      if (e.target.nodeName === 'A') {
        e.preventDefault()
        let path = e.target.getAttribute('href')  //获取超链接的href,改为pushState跳转,不刷新页面
        window.history.pushState({}, '', path)  //修改浏览器中显示的url地址
        render(path)  //根据path,更改页面内容
      }
    })

    function render(path) {
      let app = document.getElementById('app')
      switch (path) {
        case '/index':
          app.innerHTML = '<h1>这是首页内容</h1>'
          break
        case '/shop':
          app.innerHTML = '<h1>这是商城内容</h1>'
          break
        case '/my':
          app.innerHTML = '<h1>这是我的内容</h1>'
          break
        default:
          app.innerHTML = '<h1>404</h1>'
      }
    }
    //监听浏览器前进后退事件,并根据当前路径渲染页面
    window.onpopstate = function (e) {
      render(location.pathname)
    }
    //第一次进入页面显示首页
    render('/index')


  </script>
</body>

两种模式的区别

模式hash模式history模式
样式带有#号不带#号
加载源只能修改#后面的部分,只能加载与当前同文档的url通过pushState设置的新的url与当前url同源的任意url
浏览器历史栈必须设置新的hash值与原来不一样才会添加到记录到历史栈中pushState设置的新的url,即使与当前url一模一样也会添加记录到历史栈中
添加到记录中的数据类型只能添加短字符串pushState通过history.state对象可以添加任意类型的数据到记录中
兼容ie8以上ie10以上
是否需要后端配合前端自己控制hash值来改变路由需要后端配合将所有访问都指向index.html,负责用户刷新页面会导致404
  • 20
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值