如何使用 JavaScript 操作浏览器历史记录 API

History 是 window 对象中的一个 JavaScript 对象,它包含了关于浏览器会话历史的详细信息。你所访问过的 URL 列表将被像堆栈一样存储起来。浏览器上的返回和前进按钮使用的就是 history 的信息。

History 对象包含长度属性,它包含了会话历史记录栈中的 URL 数量。例如,如果用户在浏览器中打开一个标签页,历史记录的长度将是 1(新的标签页也是一个网页)。然后用户输入一个网址 foo.com 并点击回车,现在历史记录对象的长度将是 2, 用户转到其他页面 bar.com,历史记录对象的长度将就是 3 了。

Back 和 Forward 方法

你可以使用 history 对象的 back 和 forward 方法来浏览网页。例如,如果你想转到上一个页面,那么可以使用:

history.back()

同样的,如果你想转到下一页,你可以使用:

history.forward()

Go 方法

如果您想向前或向后移动 n 个页面,那么您可以使用 go 方法:

history.go(-2) // 倒退 2 页
history.go(2) // 前进 2 页

所以 history.go(1) 和 history.forward() 效果是相同的,history.go(-1) 和 history.go(-1) 效果是相同的。history.go 方法的默认值为 0,如果不传任何数字,则当前页面会被刷新。

window.history.go(0)
window.history.go()

PushState

你也可以使用 pushState 和 replaceState 方法改变页面的 URL。pushState 会改变页面的 URL,并将改变后的 URL 添加到 history 对象的 URL 栈顶部。语法如下:

history.pushState(state, title, url)

参数 state 是状态数据,它将被存储在 history.state 变量中。参数 title 是标题文本,不过它对大多数浏览器都没有效果,所以一般传空字符串("")或传 null 就可以了。

让我们在控制台中尝试一下,在执行之前,比如打开 baidu.com,然后在控制台输入:

history.pushState('123', '', 'new-url')

执行上面的代码后,它会将页面地址栏中的 URL 改为 baidu.com/new-url,同时将 URL 添加到 history 对象中。此时检查 history.length 会增加 1。

除此之外,我们还可以为每个 URL 存储状态(当前页面的数据)。在上面的例子中,你会把 "123" 存储在 history.state 变量中,当你返回到这个页面时,你就可以 history.state 再次拿到到这些数据。例如:

history.pushState('temp data 1', 'title', 'new-url-1')
history.state //"temp data 1"
history.pushState('temp data 2', 'title', 'new-url-2')
history.state //"temp data 2"
history.back()
history.state // "temp data 1"

每当通过 pushState 返回到之前被添加到历史记录的页面时,浏览器就会触发一个名为 popstate 的事件,并将 state 数据作为参数。比如在浏览器打开一个新标签页,进入某个网页(比如 baidu.com),先监听 popstate 事件:

window.addEventListener('popstate', (e) => console.log(e))

然后调用 pushState:

history.pushState({ name: 'test1' }, 'title', 'test1')

然后按下返回按钮,popstate 事件就会被触发,你可以在监听事件中查看打印出来的数据。在打印的数据中,可以找到 history.state 的值。

注册 pushState 中的 url 可以是完整的 url,但必须和当前页面是相同的域名,否则会抛出跨域异常。

浏览器还有一个 replaceState API,和 pushState 的区别是,它只改变了 URL,不会将 URL 添加到历史记录,这里就不再累述了。

实例演示

现在我们做一个小的网页应用,这个应用将实现如下功能:

  1. 显示用户列表
  2. 可以通过下拉框筛选“先生”和“女士”
  3. 当下列列表发生变化时,URL 也会相应的变化

我们先不关心 history API,先实现功能。下面是 html 关键代码:

<select id="selectbox">
 <option value="both">全部</option>
 <option value="male">先生</option>
 <option value="femalt">女士</option>
</select>
<ul id="userslist">
 <li gender="male">张先生</li>
 <li gender="female">李女士</li>
 <li gender="female">王女士</li>
</ul>

下面是 javascript 关键代码:

let selectBox = document.getElementById('selectBox')
let usersList = document.getElementById('usersList')

selectBox.addEventListener('change', onSelectBoxChange)

function onSelectBoxChange(ev) {
 let val = this.value
 filterList(val)
}

function filterList(val) {
 let users = usersList.children
 for (let i = 0; i < users.length; i++) {
  let user = users[i]
  let gender = user.getAttribute('gender')
  if (gender === val || val === 'both') {
   user.style.display = ''
  } else {
   user.style.display = 'none'
  }
 }
}

实现后的效果如下:

当修改下拉列表时,为了使浏览器地址也发生变化,需要使用 pushSate 方法:

function onSelectBoxChange(ev) {
 let val = this.value
 filterList(val)
 history.pushState({ gender: val }, null, val)
}

此时会有个问题,当我们点击前进/后退时,浏览器地址变了,但对应的数据却不对。因此,当进行前进/后退时,我们需要监听 popstate 重新过滤数据:

window.addEventListener('popstate', onPopState)
function onPopState(ev) {
 let state = ev.state
 filterList(state.gender)
}

我们还需要处理页面刷新的问题。当刷新页面时,历史记录不会改变,history.state 的状态值也保持不变。所以我们可以从 history.state 中取出当前的状态数据,利用 state.gender 的值就可以在 load 事件中来过虑出当前 URL 对应的用户列表:

window.addEventListener('load', function () {
 let gender = history.state ? history.state.gender : 'both'
 filterList(gender)
})

这是个简单的示例,你也可以继续进一步优化。今天的分享就到这里,有问题请在下面留言哦~~

以上就是如何使用 JavaScript 操作浏览器历史记录 API的详细内容,更多关于JavaScript 操作历史记录api的资料请关注我们其它相关文章!

(0)

相关推荐

  • 手机浏览器唤起微信分享(JS)

    最近在做一个手机站,要求点击分享可以直接打开微信分享出去.而不是jiathis,share分享这种的点击出来二维码.在网上看了很多,都说APP能唤起微信,手机网页实现不了.也找了很多都不能直接唤起微信. 总结出来一个可以直接唤起微信的.适应手机qq浏览器和uc浏览器. 下面上代码,把这些直接放到要转发的页面里就可以了: html部分: <script src="mshare.js"></script>//引进mshare.js <button data-m

  • Node.js API详解之 dgram模块用法实例分析

    本文实例讲述了Node.js API详解之 dgram模块用法.分享给大家供大家参考,具体如下: Node.js API详解之 dgram dgram模块提供了 UDP 数据包 socket 的实现. 使用以下方式引用: const dgram = require('dgram'); dgram.createSocket(options[, callback]) 说明: 创建一个 dgram.Socket 对象. 一旦创建了套接字,调用 socket.bind() 会指示套接字开始监听数据报消息

  • 利用浏览器全屏api实现js全屏

    复制代码 代码如下: (function () { var fullScreenApi = {  supportsFullScreen : false,  isFullScreen : function () {   return false;  },  requestFullScreen : function () {},  cancelFullScreen : function () {},  fullScreenEventName : '',  prefix : '' }, browser

  • JS跨浏览器解析XML应用过程详解

    首先介绍简单的理论: 对于XML,我们可以理解它是一种树结构,它包含根,元素,属性,文本等内容.不同浏览器都有自己的解析器,把XML读入内存,并把它转换为可被 JavaScript 访问的 XML DOM 对象. 微软的 XML 解析器与其他浏览器中的解析器是有差异的.微软的解析器支持对 XML 文件和 XML 字符串(文本)的加载,而其他浏览器使用单独的解析器.不过,所有的解析器都含有遍历 XML 树.访问.插入及删除节点的函数. 如果你使用的是一个本地文件或者网络文件且该文件在是在本服务器,

  • 基于js判断浏览器是否支持webGL

    起因是我之前开发的网页,用到了three.js制作了一个3d的旋转球体效果. 在各种浏览器上运行都没问题,在IE上也做了兼容代码. 但是今天接电话,老板说你这网页在xp上不显示啊.IE上好使.google浏览器不好使. 于是开始解决问题,不禁陷入了沉思.what?网页显示难道还与操作系统有关?google竟然不好使? 于是搭建一个xp虚拟机. 于是下载一个chorme. 惊奇的发现并不能安装最新版本的chrome. 哦?一定是xp上安装的低版本chrome而那时候的chrome还不支持webGL

  • python 调用API接口 获取和解析 Json数据

    任务背景: 调用API接口数据,抽取我们所需类型的数据,并写入指定mysql数据库. 先从宏观上看这个任务,并对任务进行分解: step1:需要学习python下的通过url读取数据的方式: step2:数据解析,也是核心部分,数据格式从python角度去理解,是字典?列表?还是各种嵌套? step3:连接mysql数据库,将数据写入. 从功能上看,该数据获取程序可以分为3个方法,即step1对应方法request_data(),step2对应方法parse_data(),step3对应data

  • 如何基于js判断浏览器版本

    这篇文章主要介绍了如何基于js判断浏览器版本,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下 浏览器类型判断 不考虑对 IE9 以下浏览器的判断 function getBrowserType(){ var userAgent = navigator.userAgent; //取得浏览器的userAgent字符串 var browser='unknown'; if (userAgent.indexOf("IE")!=-1) { brow

  • JS检测浏览器开发者工具是否打开的方法详解

    在某些情况下我们需要检测当前用户是否打开了浏览器开发者工具,比如前端爬虫检测,如果检测到用户打开了控制台就认为是潜在的爬虫用户,再通过其它策略对其进行处理.本篇文章主要讲述几种前端JS检测开发者工具是否打开的方法.  一.重写toString() 对于一些浏览器,比如Chrome.FireFox,如果控制台输出的是对象,则保留对象的引用,每次打开开发者工具的时候都会重新调用一下对象的toString()方法将返回结果打印到控制台(console tab)上. 所以只需要创建一个对象,重写它的to

  • Vue.js获取手机系统型号、版本、浏览器类型的示例代码

    1.index.html引入 <script src="http://code.jquery.com/jquery-1.11.1.min.js"> </script> <script src="https://cdn.jsdelivr.net/npm/mobile-detect@1.4.4/mobile-detect.min.js"> </script> 2.直接用 <script> //判断数组中是否包含

  • Node.js API详解之 V8模块用法实例分析

    本文实例讲述了Node.js API详解之 V8模块用法.分享给大家供大家参考,具体如下: Node.js API详解之 V8 v8 模块暴露了特定于V8版本内置到 Node.js 二进制文件中的API. 通过以下方式使用: const v8 = require('v8'); 注意: APIs 和实现可能在任何时间变动. v8.cachedDataVersionTag() 说明: 返回一个表示从V8版本,命令行标志和已检测到的CPU功能派生的"version tag"的整数. 这对于判

  • javascript使用百度地图api和html5特性获取浏览器位置

    复制代码 代码如下: <!DOCTYPE html><html><body><p id="demo">点击这个按钮,获得您的位置:</p><button onclick="getLocation()">试一下</button><script src="http://api.map.baidu.com/api?v=1.4" type="text/ja

  • JS浏览器BOM常见操作实例详解

    本文实例讲述了JS浏览器BOM常见操作.分享给大家供大家参考,具体如下: window尺寸 有三种方法能够确定浏览器窗口的尺寸(浏览器的视口,不包括工具栏和滚动条). 对于Internet Explorer.Chrome.Firefox.Opera 以及 Safari: window.innerHeight - 浏览器窗口的内部高度 window.innerWidth - 浏览器窗口的内部宽度 对于 Internet Explorer 8.7.6.5: document.documentElem

随机推荐