分享JavaScript获取网页关闭与取消关闭的事件


Posted in Javascript onDecember 13, 2013

在做Web开发时,我们经常用到页面关闭事件onbeforeunload,可以给用户一个选择放弃关闭的机会,就比如这个博客编辑器。如果用户选择了离开,那么onunload事件自然会触发;但若用户选择了取消,又该如何检测呢?

我们假定一个页面离开取消事件,叫做onunloadcancel。显然,这个事件应触发在用户按下对话框的取消按钮之后。但关闭提示对话框的触发流程并不是那么简单。我们先来回顾下这个过程:

window.onbeforeunload = function()
{
    return "真的离开?";
}

当用户准备离开页面(比如按下关闭按钮,或者刷新页面等等),onbeforeunload事件触发。我们的脚本无法在这个事件里决定是否阻止页面的关闭,唯一能做到的只有返回一个字符串,这个字符串仅作为说明文字出现在关闭选择对话框里,用户可以选择关闭,或者不关闭。但究竟选择哪个,我们无从得知。

然而仔细分析下这个问题,其实不然。 如果用户真选择了关闭页面,那么之后所有的运行代码都byebye了;而继续留在页面的话,就当什么都没发生过,除了onbeforeunload事件。所以,我们在onbeforeunload事件里做点小花招,在此注册个几毫秒之后启动的定时器,如果页面真关闭了,那么这个定时器当然是作废了;那么页面还在,几毫秒的延时对于这个本来就是异步的界面交互事件也没有什么误差。

<script language="JavaScript">
window.onbeforeunload = function()
{
    setTimeout(onunloadcancel, 10);
    return "真的离开?";
}
window.onunloadcancel = function()
{
    alert("取消离开");
}
</script>

我们使用setTimeout,延时10ms执行onunloadcancel。如果页面真关闭了,定时器当然都销毁;反之继续。但在测试中,发现FireFox有个两个BUG:

有时按下关闭按钮,也会执行onunloadcancel,并且有个对话框一闪而过。如果换成while(1);浏览器会一直卡死,这说明onunloadcancel确实是执行了,只是销毁了界面,但并没有暂停脚本的运行。
如果是通过刷新页面的方式离开,仅执行一次onbeforeunload,但点击X按钮关闭页面,会执行两次onbeforeunload。因此我们还需在完善下,以便兼容FF。

<script language="JavaScript">
var _t;
window.onbeforeunload = function()
{
    setTimeout(function(){_t = setTimeout(onunloadcancel, 0)}, 0);
    return "真的离开?";
}
window.onunloadcancel = function()
{
    clearTimeout(_t);
    alert("取消离开");
}
</script>

这里使用了一种我也说不出原因的办法,应该算是hack,解决了FF下的bug。
Javascript 相关文章推荐
JavaScript NodeTree导航栏(菜单项JSON类型/自制)
Feb 01 Javascript
ajax读取数据后使用jqchart显示图表的方法
Jun 10 Javascript
jquery衣服颜色选取插件效果代码分享
Aug 28 Javascript
详细谈谈javascript的对象
Jul 31 Javascript
JavaScript实现复制文章自动添加版权
Aug 02 Javascript
select下拉框插件jquery.editable-select详解
Jan 22 Javascript
简单实现JS上传图片预览功能
Apr 14 Javascript
原生js轮播特效
May 18 Javascript
详解webpack+angular2开发环境搭建
Jun 28 Javascript
vue.js给动态绑定的radio列表做批量编辑的方法
Feb 28 Javascript
浅谈在react中如何实现扫码枪输入
Jul 04 Javascript
解决betterScroll在vue中存在图片时,出现拉不动的问题
Sep 27 Javascript
js获取触发事件元素在整个网页中的绝对坐标(示例代码)
Dec 13 #Javascript
浅析XMLHttpRequest的缓存问题
Dec 13 #Javascript
xmlhttp缓存清除的2种解决方法
Dec 13 #Javascript
js获取url参数代码实例分享(JS操作URL)
Dec 13 #Javascript
js获取html页面节点方法(递归方式)
Dec 13 #Javascript
jquery 合并内容相同的单元格(示例代码)
Dec 13 #Javascript
javascript读取xml实现javascript分页
Dec 13 #Javascript
You might like
dedecms采集中可以过滤多行代码的正则表达式
2007/03/17 PHP
PHP读取文件并可支持远程文件的代码分享
2012/10/03 PHP
TP5框架实现上传多张图片的方法分析
2020/03/29 PHP
Javascript typeof 用法
2008/12/28 Javascript
jquery ui dialog里调用datepicker的问题
2009/08/06 Javascript
TinyMCE 新增本地图片上传功能
2010/11/05 Javascript
jQuery阻止同类型事件小结
2013/04/19 Javascript
JQUERY实现左侧TIPS滑进滑出效果示例
2013/06/27 Javascript
兼容ie、firefox的图片自动缩放的css跟js代码分享
2013/08/12 Javascript
javascript实例--教你实现扑克牌洗牌功能
2014/05/15 Javascript
JS中实现简单Formatter函数示例代码
2014/08/19 Javascript
js实现滚动条滚动到某个位置便自动定位某个tr
2021/01/20 Javascript
jQuery动态生成表格及右键菜单功能示例
2017/01/13 Javascript
js放到head中失效的原因与解决方法
2017/03/07 Javascript
纯js实现动态时间显示
2020/09/07 Javascript
JS实现静态页面搜索并高亮显示功能完整示例
2017/09/19 Javascript
详解Koa中更方便简单发送响应的方式
2018/07/20 Javascript
vue中利用iscroll.js解决pc端滚动问题
2020/02/15 Javascript
Taro小程序自定义顶部导航栏功能的实现
2020/12/17 Javascript
[52:07]完美世界DOTA2联赛PWL S3 LBZS vs access 第二场 12.10
2020/12/13 DOTA
Python中输出ASCII大文字、艺术字、字符字小技巧
2015/04/28 Python
利用Python批量生成任意尺寸的图片
2016/08/29 Python
Python中出现IndentationError:unindent does not match any outer indentation level错误的解决方法
2020/04/18 Python
python爬虫之爬取百度音乐的实现方法
2019/08/24 Python
50道外企软件测试面试题
2014/08/18 面试题
机械专业毕业生推荐信范文
2013/11/25 职场文书
办公室前台岗位职责
2014/01/04 职场文书
校园达人秀策划书
2014/01/12 职场文书
工程资料员岗位职责
2014/03/10 职场文书
校园联欢晚会主持词
2014/03/17 职场文书
青春励志演讲稿
2014/04/29 职场文书
赔偿协议书范本
2014/09/12 职场文书
2014年党员自我评议总结
2014/09/23 职场文书
使用goaccess分析nginx日志的详细方法
2021/07/09 Servers
Python实现自动玩连连看的脚本分享
2022/04/04 Python
《传颂之物 虚伪的假面》BD发售宣传CM公开
2022/04/04 日漫