JavaScript history 对象

在 JavaScript 中,我们可以使用 history 对象来操作当前窗口的浏览历史(如前进、后退)。

提示: history 对象本质上是 “window 对象” 的属性。因此在使用时,可以省略 “window.” 前缀。

JavaScript history 对象的属性

在 JavaScript 中,history 对象主要提供了 2 个属性:

  • length:获取访问历史记录中的数量。
  • state:获取当前历史状态。

示例 1:使用 history.length

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
</head>
<body>
    <script>
        console.log("当前会话历史记录的数量:", history.length);
    </script>
</body>
</html>

运行结果如下。

当前会话历史记录的数量:7

JavaScript history 对象的方法

在 JavaScript 中,history 对象主要提供了 5 种方法,如下表所示。

history 对象的方法
方法 说明
back() 加载前一个 URL
forward() 加载后一个 URL
go(n) 加载历史列表中指定位置的 URL
pushState() 在会话历史记录中,添加一个新的条目
replaceState() 在会话历史记录中,用新状态替换掉当前的条目

提示: 由于客观存在的技术原因,使用绿叶网的 HTML 在线编译器运行 history 对象方法会有问题。对于本节后面的例子,建议小伙伴们在本地自行测试。

示例 2:history.back() 和 history.forward()

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
</head>
<body>
    <button id="back">后退</button>
    <button id="forward">前进</button>
    <script>
        // 后退
        const oBack = document.getElementById("back");
        oBack.addEventListener("click", function() {
            history.back();
        });

        // 前进
        const oForward = document.getElementById("forward");
        oForward.addEventListener("click", function() {
            history.forward();
        });
    </script>
</body>
</html>

页面效果如下图所示。

JavaScript history.back()和history.forward() 示例

分析:

history.back() 方法用于加载历史列表中的前一个 URL,相当于用户点击了浏览器的 “后退” 按钮。而 history.forward() 方法用于加载历史列表中的下一个 URL,相当于用户点击了浏览器的 “前进” 按钮。

比如绿叶网的 404 页面,就使用了 history.back() 方法来实现 【返回上页】的功能,如下图所示。

history.back() 实现 “返回上页” 功能

示例 3:history.go()

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
</head>
<body>
    <button id="back">后退 2 步</button>
    <button id="forward">前进 2 步</button>
    <script>
        // 后退
        const oBack = document.getElementById("back");
        oBack.addEventListener("click", function() {
            history.go(-2);
        });

        // 前进
        const oForward = document.getElementById("forward");
        oForward.addEventListener("click", function() {
            history.forward(2);
        });
    </script>
</body>
</html>

页面效果如下图所示。

JavaScript history.go() 示例

分析:

history.go(n) 方法用于加载历史列表中的指定步数的 URL。n 的取值可以是以下几种情况:

  • 当取值为 “0” 时,表示重新加载当前页面,与 location.reload() 一样。关于 location.reload() 的使用,另请参阅:JavaScript location 对象
  • 当取值为 “正数(1、2、3等)” 时,表示向前(forward())跳转指定的步数。
  • 当取值为 “负数(-1、-2、-3等)” 时,表示向后(back())跳转指定的步数。

管理 SPA 状态:pushState() 和 replaceState()

我们都知道,Vue、React 等都是单页应用(SPA)。而在这些单页应用中,我们经常需要在不刷新页面的情况下更改 URL,以实现书签功能。

其中,history 对象的 pushState() 和 replaceState() 这两个方法,就是为此目的而设计的。

1. history.pushState()

在 JavaScript 中,我们可以使用 history.pushState() 方法来向会话历史记录中添加一个新的条目。history.pushState() 会更改浏览器的 URL,但不触发页面跳转。

语法:

history.pushState(state, title, url)

说明:

history.pushState() 方法接收以下 3 个参数。

  • state(必选):与新历史记录条目关联的状态对象,我们可以使用 history.state 来访问状态对象。
  • title(必选):页面的新标题(大多数浏览器目前忽略此参数)。
  • url(可选):新的历史记录条目 URL。

示例 4:history.pushState() 基本用法

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
</head>
<body>
    <script>
        const newState = { "user_id": 1001, "view": "profile" };
        const newUrl = "/users/1001/profile";

        history.pushState(newState, "用户资料页", newUrl);
    </script>
</body>
</html>

分析:

上面代码运行之后,浏览器地址栏会变为 “/users/1001/profile”。其中,history.pushState(newState, "用户资料页", newUrl) 可以在不刷新页面的情况下,将 URL 变为 “/users/1001/profile”,并保存状态(newState)。

提示: 当用户点击浏览器的 “前进/后退” 按钮时,会触发 popstate 事件,SPA 框架(如Vue、React 等)就是靠监听这个事件来切换页面的。

2. history.replaceState()

在 JavaScript 中,history.replaceState() 方法不创建新的历史记录条目,而是用新状态替换掉当前的条目。它经常用于避免在用户执行某些操作时创建不必要的历史记录。

语法:

history.replaceState(state, title, url)

说明:

history.replaceState() 与 history.pushState() 语法一样,也接收以下 3 个参数。

  • state(必选):与新历史记录条目关联的状态对象,我们可以使用 history.state 来访问状态对象。
  • title(必选):页面的新标题(大多数浏览器目前忽略此参数)。
  • url(可选):新的历史记录条目 URL。

示例 5:history.replaceState() 基本用法

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <title></title>
</head>
<body>
    <script>
        const updatedState = { "view": "settings" };
        const updatedUrl = "/user/settings";

        history.replaceState(updatedState, "用户设置页", updatedUrl);
    </script>
</body>
</html>

分析:

history.replaceState() 方法会替换当前历史记录条目,而不是添加新的。

给站长反馈

绿叶网正在不断完善中,小伙伴们如果发现任何问题,还望多多给站长反馈,谢谢!

邮箱:lvyenet@vip.qq.com

「绿叶网」服务号
绿叶网服务号放大
关注服务号,微信也能看教程。
绿叶网服务号