前端开发

popstate玩转浏览器历史记录

2019-03-17  本文已影响3人  李轻舟

一、popstate用来做什么的?

简而言之就是HTML5新增的用来控制浏览器历史记录的api。

二、过去如何操纵浏览器历史记录?

window.history 对象,该对象上包含有 lengthstate 的两个值,在它的 __proto__ 上继承有 backforwardgo 等几个功能函数
popstate 之前,我们可以利用 backforwardgohistory 进行后退和前进操作。
例如:

history.back(); 
// 后退一步,使用history.go(-1)也可实现后退效果

弊端:只能操作前进后退,但是无法控制前进后要去哪, history.length 都只会维持原来的状态

三、popstate的怎么用?

HTML5 的新 API 扩展了 window.history ,使历史记录点更加开放了。可以存储当前历史记录点 pushState 、替换当前历史记录点 replaceState 、监听历史记录点 popstate

pushStatereplaceState 两者用法差不多。
使用方法:

history.pushState(data,title,url);
/* 其中第一个参数data是给state的值;
*  第二个参数title为页面的标题,但当前所有浏览器都忽略这个参数,传个空字符串就好;
*  第三个参数url是你想要去的链接;
*/

replaceState用法类似,例如:

history.replaceState("首页", "", location.href + "#news");

两者区别pushState 会改变 history.length,而 replaceState 不改变 history.length

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="UTF-8">
    <title>popstate玩转浏览器历史记录</title>
</head>
<body>


  <span class="js-news">新闻</span>
  <span class="js-music">音乐</span>
  <script>

    var locationHref = location.href;
    document.addEventListener("click", function (event) {
        var target = event.target;
        if (target.className == "js-news") {
            history.pushState("首页", "", locationHref + "#news");
        } else if (target.className == "js-music") {
            history.pushState("音乐", "", locationHref + "#music");
        }
    });

    /*    document.addEventListener("click",function(event){
     var target = event.target;
     if(target.className == "js-news"){
     history.replaceState("首页","",locationHref + "#news");
     }else if(target.className == "js-music"){
     history.replaceState("音乐","",locationHref + "#music");
     }
     });*/
    
    window.addEventListener("popstate", function () {
        console.log(history.state);
    })
  </script>
</body>
</html>

通过下图我们可以对比看出 pushStatereplaceState 的差别(注意看 history.length 的变化):

pushState
replaceState

四、监听浏览器状态(popstate)变化事件

当活动历史记录条目更改时,将触发 popstate 事件。如果被激活的历史记录条目是通过对 history.pushState 的调用创建的,或者受到对 history.replaceState 的调用的影响,popstate 事件的 state 属性包含历史条目的状态对象的副本。
可以理解为监听浏览器后退、前进的操作,只要后退或者前进就会触发。在上面的 demo 中,我们预先做了如下操作: 打开页面 → 点击“新闻” → 点击“音乐” → 再点击“新闻”,产生了4个 history 记录。然后监听浏览器后退和前进的状态变化,如下图所示:

popstate
需要注意的是调用 history.pushStatehistory.replaceState 不会触发 popstate 事件。只有在做出浏览器动作时,才会触发该事件,如用户点击浏览器的回退按钮(或者在 Javascript 代码中调用 history.back
不同的浏览器在加载页面时处理popstate事件的形式存在差异。页面加载时Chrome和Safari通常会触发(emit) popstate 事件,但 Firefox 则不会。

属性

Property Type Description
target | 只读 EventTarget The browsing context (window).
type | 只读 DOMString The type of event.
bubbles | 只读 Boolean Whether the event normally bubbles or not.
cancelable | 只读 Boolean Whether the event is cancellable or not.
state | 只读 any The current history entry's state object (if any).

浏览器兼容性

Feature Chrome Firefox (Gecko) Internet Explorer Opera Safari
Basic support Yes 4.0 (2) 10.0 Yes limited
Feature Android Firefox Mobile (Gecko) IE Mobile Opera Mobile Safari Mobile
Basic support 3.0 (buggy in 2.2 and 2.3) 4.0 (2) 10.0 Yes limited
上一篇 下一篇

猜你喜欢

热点阅读