用户通过“点击触发”,“操作历史”,“直接访问URL”的方式修改当前URL。这三种触发方式会使浏览器做出不同的行为

html5提供了两种方式在页面中操作历史

  • history.pushState(state, title, url)

    • 将当前URL和history.state加入到history中,并用新的state和URL替换当前, 不会造成页面刷新。
  • history.replaceState(state, title, url)
    • 用新的state和URL替换当前, 不会造成页面刷新。
  • history.state
    • 如果当前URL不是通过pushState或者replaceState产生的,那么history.state是null。

提供检测历史记录变化的事件popstate

  • 每当处于激活状态的历史记录条目发生变化时,popstate事件就会在对应window对象上触发.

    •  如果当前处于激活状态的历史记录条目是由history.pushState()方法创建,或者由history.replaceState()方法修改过的, 则popstate事件对象的state属性包含了这个历史记录条目的state对象的一个拷贝.

  • 调用history.pushState()或者history.replaceState()不会触发popstate事件.
  • popstate事件只会在浏览器操作如点击前进or后退按钮(JS调用也可), URL中"#"后面的字符串改变时触发.

利用这一特性, 就可以处理无刷新页面的前端后退,保存历史操作的页面状态啦。

demo一下

<a href="#1">text1</a>
<a href="#2">text2</a>
<a href="#3">text3</a>
<a href="#4">text4</a>
<a href="#5">text5</a> <script> window.addEventListener('popstate', function(event) {
readState(event.state);
}); for(i=0;i<5;i++){
var stateObject = {id: i};
var title = "Wow Title "+i;
var newUrl = "/my/awesome/url/"+i;
history.pushState(stateObject,title,newUrl);
} function readState(data){
alert(data.id);
}
</script>

  

hashchange

在URL的参数列表(及URL中"#"号后面的所有字符串)发生变化的时候触发, hash的变化不会触发浏览器请求资源,因此天然可以来处理页面内无刷新导航 。

兼容如下:

  • IE8+ | FF3.6+ | Safari5+ | Chrome | Opera 10.6+ 支持hashchange
  • event对象有两个属性:oldURL和newURL,  FF3.6+ Chrome Opera支持 oldURL 和 newURL

在IE6、7下可以采用定时循环检测或者采用添加隐藏iframe的方式来解决, 如:

if( ('onhashchange' in window) && ((typeof document.documentMode==='undefined') || document.documentMode==8)) {
// 浏览器支持onhashchange事件
window.onhashchange = hashChangeFire; // TODO,对应新的hash执行的操作函数
} else {
// 不支持则用定时器检测的办法
setInterval(function() {
// 检测hash值或其中某一段是否更改的函数, 在低版本的iE浏览器中通过window.location.hash取出的指和其它的浏览器不同,要注意
     var ischanged = isHashChanged();
if(ischanged) {
hashChangeFire(); // TODO,对应新的hash执行的操作函数
}
}, 150);
}

总结

在前端的实际应用场景中,如果页面局部刷新,不改变URl,在页面刷新、前进、后退,或者想分享一个具体的页面状态链接的时候, 就会体验特别差。

如果要改变url进行局部更新, 这时检测到URL的变化就非常重要。

我们可以利用改变hash触发hashchange或者兼容方案定时检测hashchange的方法,来达到更改页面Url并同时更新页面局部显示状态的效果。 不过有时会期望单页中的URL和服务端开发时的URL风格比较一致,会在document上监听链接的点击,利用html5 history提供的API来改变URl, 并调用相应的处理函数来达到不刷新页面同时更新页面局部状态的目的

以上已经能好的解决了页面内功能无刷新导航的功能, 但还有一个需要注意的是, 第一次访问链接或者刷新页面URL时, 需要后端配合将本页的所有URL做一下重定向。 另外首次从不同的URL进入时,也需要在前端根据URL进行一下手动的分发。

如何检测浏览器url变化的更多相关文章

  1. jQuery hashchange监听浏览器url变化

    $(window).bind('hashchange', function() { // });

  2. 对于单页应用中如何监听 URL 变化的思考

    周末开发了一个在 GitHub 中给 repo 增加自定义备注的 chrome 扩展. 开发这个扩展的原因是我在 GitHub 中所 star 的项目实在太多了(截止目前 671 个),有的项目过个几 ...

  3. 检查浏览器url改变,处理ajax前进和后退键

    在用ajax获取数据,不刷新页面情况下,保持前进后退按钮功能,网页端兼容性最好的方式如下: 首先url后面参数用#  如http://www.xxx.com/#txf; 使用改变location.ha ...

  4. 检测浏览器对HTML5新input类型的支持

    HTML5新增加了很多input元素类型,比如color,date,datetime,datetime-local,email,month,number,range,search,tel,time,u ...

  5. 如何检测浏览器是否安装了Adblock,uBlock Origin,Adguard,uBlock等广告屏蔽插件

    由于我们网站上的广告经常被一些广告插件给屏蔽掉,上级给我下达了一个检测浏览器是否安装了屏蔽广告的插件的任务. 经过研究,借鉴,参考,整合了如下三种解决方案.   方案一: 利用广告插件通过对含有goo ...

  6. 用 JavaScript 检测浏览器在线/离线状态(JavaScript API — navigator.onLine)

    如今HTML5 移动应用或 Web app 中越来越普遍的使用了离线浏览技术,所以用 JavaScript 检测浏览器在线/离线状态非常常见. 无论浏览器是否在线,navigator.onLine 属 ...

  7. jquery检测浏览器类型

    使用jquery如下代码检测浏览器版本时:出问题,在检测IE浏览器,如果版本是IE11时,会出现 $.browser.msie的返回值是false,$.browser.mozilla的返回值是true ...

  8. [转]JavaScript快速检测浏览器对CSS3特性的支持

    转自:https://yuguo.us/weblog/detect-css-support-in-browsers-with-javascript/ ------------------------- ...

  9. js检测浏览器是否支持某属性

    以检测浏览器是否支持 input 标签的 required 属性为例: var isSupport = 'required' in document.createElement('input');

随机推荐

  1. Java编程学习知识点分享 入门必看

    Java编程学习知识点分享 入门必看 阿尔法颜色组成(alpha color component):颜色组成用来描述颜色的透明度或不透明度.阿尔法组成越高,颜色越不透明. API:应用编程接口.针对软 ...

  2. Java 多线程笔记

    资料来源于网络,仅供参考学习.   1.A Java program ends when all its threads finish (more specifically, when all its ...

  3. Macaca环境搭建踩坑总结

    1.使用命令 npm i macaca-android -g 安装一直不成功,使用Macaca  doctor 一直没有显示出android C:\Users\ABC>npm i macaca- ...

  4. Python核心编程--浅拷贝与深拷贝

    一.问题引出浅拷贝 首先看下面代码的执行情况: a = [1, 2, 3] print('a = %s' % a) # a = [1, 2, 3] b = a print('b = %s' % b) ...

  5. MySQL数据库学习: 02 —— 数据库的安装与配置

                             MySQL安装图解 一.MYSQL的安装 1.打开下载的mysql安装文件mysql-5.0.27-win32.zip,双击解压缩,运行“setup. ...

  6. 在commons-lang3包中StringUtils类的ordinalIndexOf中有一个错误

    * StringUtils.ordinalIndexOf(null, *, *) = -1 * StringUtils.ordinalIndexOf(*, null, *) = -1 * String ...

  7. angular4.0如何引入外部插件1:import方案

    引入外部插件是项目中非常重要的环节.因为部分插件以js语法写的,而ng4用的是ts语法,所以在引入时需要配置. Step1:引入swiper插件的js文件[css在下面会讲到,先别急] 很重要的意见: ...

  8. 一种基于http协议的敏感数据传输方案

    最近公司需要通过公网与其它平台完成接口对接,但是基于开发时间和其它因素的考虑,本次对接无法采用https协议实现.既然不能用https协议,那就退而求其次采用http协议吧! 那么问题来了!在对接的过 ...

  9. react 开发知识准备

    react react使用教程 babel babel 可用于ES6转换为ES5,jsx转换为原生js. ES6 ES6 语法 webpack webpack打包工具,它把不同的.相互依赖的静态资源都 ...

  10. iOS 动画篇 (三) CADisplayLink与CoreGraphics实现动画

    本文主要介绍利用CoreGraphics和CADisplayLink来实现一个注水动画.来一个效果图先: 在介绍注水动画前,先介绍利用CoreGraphics实现进度条的绘制. 一.扇形进度绘制 效果 ...