提问人:khelll 提问时间:10/28/2009 最后编辑:kenorbkhelll 更新时间:8/25/2022 访问量:493261
如何捕获浏览器窗口关闭事件?
How to capture the browser window close event?
问:
我想捕获浏览器窗口/选项卡关闭事件。 我用jQuery尝试了以下方法:
jQuery(window).bind(
"beforeunload",
function() {
return confirm("Do you really want to close?")
}
)
但它也适用于表单提交,这不是我想要的。我想要一个仅在用户关闭窗口时触发的事件。
答:
也许您可以处理 OnSubmit 并设置一个标志,稍后在 OnBeforeUnload 处理程序中签入该标志。
也许只是在表单的事件处理程序中取消绑定事件处理程序:beforeunload
submit
jQuery('form').submit(function() {
jQuery(window).unbind("beforeunload");
...
});
评论
onsubmit=...
每当用户出于任何原因离开您的页面时,都会触发该事件。beforeunload
例如,如果用户提交表单、单击链接、关闭窗口(或选项卡)或使用地址栏、搜索框或书签转到新页面,则会触发该按钮。
您可以使用以下代码排除表单提交和超链接(其他框架除外):
var inFormOrLink;
$('a').on('click', function() { inFormOrLink = true; });
$('form').on('submit', function() { inFormOrLink = true; });
$(window).on("beforeunload", function() {
return inFormOrLink ? "Do you really want to close?" : null;
})
对于早于 1.7 的 jQuery 版本,请尝试以下操作:
var inFormOrLink;
$('a').live('click', function() { inFormOrLink = true; });
$('form').bind('submit', function() { inFormOrLink = true; });
$(window).bind("beforeunload", function() {
return inFormOrLink ? "Do you really want to close?" : null;
})
该方法不适用于事件,因此,如果添加新窗体,则还需要将处理程序绑定到该窗体。live
submit
请注意,如果其他事件处理程序取消了提交或导航,则在稍后实际关闭窗口时,您将丢失确认提示。您可以通过在 和 事件中记录时间并检查是否在几秒钟后发生来解决这个问题。submit
click
beforeunload
评论
Ctrl + r
F5
Ctrl + Shift + r
.on()
如果您的表单提交将它们带到另一个页面(正如我假设的那样,因此触发了 ),您可以尝试将表单提交更改为 ajax 调用。这样,他们在提交表单时不会离开您的页面,您可以根据需要使用绑定代码。beforeunload
beforeunload
跟随对我有用;
$(window).unload(function(event) {
if(event.clientY < 0) {
//do whatever you want when closing the window..
}
});
评论
event.clientY
我的问题:只有当提交(点击次数)为奇数时,才会触发“onbeforeunload”事件。我在 SO 中结合了来自类似线程的解决方案,以使我的解决方案正常工作。好吧,我的代码会说话。
<!--The definition of event and initializing the trigger flag--->
$(document).ready(function() {
updatefgallowPrompt(true);
window.onbeforeunload = WarnUser;
}
function WarnUser() {
var allowPrompt = getfgallowPrompt();
if(allowPrompt) {
saveIndexedDataAlert();
return null;
} else {
updatefgallowPrompt(true);
event.stopPropagation
}
}
<!--The method responsible for deciding weather the unload event is triggered from submit or not--->
function saveIndexedDataAlert() {
var allowPrompt = getfgallowPrompt();
var lenIndexedDocs = parseInt($('#sortable3 > li').size()) + parseInt($('#sortable3 > ul').size());
if(allowPrompt && $.trim(lenIndexedDocs) > 0) {
event.returnValue = "Your message";
} else {
event.returnValue = " ";
updatefgallowPrompt(true);
}
}
<!---Function responsible to reset the trigger flag---->
$(document).click(function(event) {
$('a').live('click', function() { updatefgallowPrompt(false); });
});
<!--getter and setter for the flag---->
function updatefgallowPrompt (allowPrompt){ //exit msg dfds
$('body').data('allowPrompt', allowPrompt);
}
function getfgallowPrompt(){
return $('body').data('allowPrompt');
}
我使用了 Slaks 答案,但这并没有按原样工作,因为 onbeforeunload returnValue 被解析为字符串,然后显示在浏览器的确认框中。因此,显示值 true,如“true”。
只是使用返回工作。 这是我的代码
var preventUnloadPrompt;
var messageBeforeUnload = "my message here - Are you sure you want to leave this page?";
//var redirectAfterPrompt = "http://www.google.co.in";
$('a').live('click', function() { preventUnloadPrompt = true; });
$('form').live('submit', function() { preventUnloadPrompt = true; });
$(window).bind("beforeunload", function(e) {
var rval;
if(preventUnloadPrompt) {
return;
} else {
//location.replace(redirectAfterPrompt);
return messageBeforeUnload;
}
return rval;
})
对于跨浏览器解决方案(在 Chrome 21、IE9、FF15 中测试),请考虑使用以下代码,这是 Slaks 代码的略微调整版本:
var inFormOrLink;
$('a').live('click', function() { inFormOrLink = true; });
$('form').bind('submit', function() { inFormOrLink = true; });
$(window).bind('beforeunload', function(eventObject) {
var returnValue = undefined;
if (! inFormOrLink) {
returnValue = "Do you really want to close?";
}
eventObject.returnValue = returnValue;
return returnValue;
});
请注意,从 Firefox 4 开始,不再显示“Do you really want to close?”消息。FF 只显示一条通用消息。请参阅 https://developer.mozilla.org/en-US/docs/DOM/window.onbeforeunload 中的注释
评论
live
bind
on
对于适用于第三方控件(如 Telerik(例如:RadComboBox)和 DevExpress)的解决方案,这些控件出于各种原因使用定位标记,请考虑使用以下代码,该代码是 desm 代码的略微调整版本,具有更好的自定位定位定位标记选择器:
var inFormOrLink;
$('a[href]:not([target]), a[href][target=_self]').live('click', function() { inFormOrLink = true; });
$('form').bind('submit', function() { inFormOrLink = true; });
$(window).bind('beforeunload', function(eventObject) {
var returnValue = undefined;
if (! inFormOrLink) {
returnValue = "Do you really want to close?";
}
eventObject.returnValue = returnValue;
return returnValue;
});
评论
从 jQuery 1.7 开始,不推荐使用 .live() 方法。使用 .on() 附加事件处理程序。旧版本jQuery的用户应优先使用.delegate()而不是.live()
$(window).bind("beforeunload", function() {
return true || confirm("Do you really want to close?");
});
完成或链接
$(window).unbind();
只需验证...
function wopen_close(){
var w = window.open($url, '_blank', 'width=600, height=400, scrollbars=no, status=no, resizable=no, screenx=0, screeny=0');
w.onunload = function(){
if (window.closed) {
alert("window closed");
}else{
alert("just refreshed");
}
}
}
评论
window.onbeforeunload = function () {
return "Do you really want to close?";
};
jQuery(window).bind("beforeunload", function (e) {
var activeElementTagName = e.target.activeElement.tagName;
if (activeElementTagName != "A" && activeElementTagName != "INPUT") {
return "Do you really want to close?";
}
})
不幸的是,无论是重新加载、新页面重定向还是浏览器关闭,都会触发该事件。另一种方法是捕获触发事件的 id,如果是表单,则不要触发任何函数,如果它不是表单的 id,则在页面关闭时执行您想执行的操作。我不确定这是否也可以直接实现,而且很乏味。
您可以在客户关闭选项卡之前做一些小事情。 JavaScript 检测浏览器关闭选项卡/关闭浏览器,但是如果您的操作列表很大并且选项卡在完成之前关闭,那么您就无能为力了。你可以尝试一下,但以我的经验,不要依赖它。
window.addEventListener("beforeunload", function (e) {
var confirmationMessage = "\o/";
/* Do you small action code here */
(e || window.event).returnValue = confirmationMessage; //Gecko + IE
return confirmationMessage; //Webkit, Safari, Chrome
});
我的回答旨在提供简单的基准。
如何
请看@SLaks答案。
$(window).on("beforeunload", function() {
return inFormOrLink ? "Do you really want to close?" : null;
})
浏览器需要多长时间才能最终关闭您的页面?
每当用户关闭页面(按钮或+)时,浏览器都会执行给定的代码,但不是无限期的。唯一的例外是确认框 (),它将等待用户的响应。xCTRLWbeforeunload
return 'Do you really want to close?
Chrome:2 秒。
Firefox:∞(或双击,或强制关闭) Edge:∞(或双击)
Explorer 11:0 秒。
Safari:待办事项
我们用来测试这一点:
- 具有请求日志的 Node.js Express 服务器
- 以下简短的 HTML 文件
它的作用是在浏览器关闭其页面(同步)之前发送尽可能多的请求。
<html>
<body>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<script>
function request() {
return $.ajax({
type: "GET",
url: "http://localhost:3030/" + Date.now(),
async: true
}).responseText;
}
window.onbeforeunload = () => {
while (true) {
request();
}
return null;
}
</script>
</body>
</html>
铬输出:
GET /1480451321041 404 0.389 ms - 32
GET /1480451321052 404 0.219 ms - 32
...
GET /hello/1480451322998 404 0.328 ms - 32
1957ms ≈ 2 seconds // we assume it's 2 seconds since requests can take few milliseconds to be sent.
也试试这个
window.onbeforeunload = function ()
{
if (pasteEditorChange) {
var btn = confirm('Do You Want to Save the Changess?');
if(btn === true ){
SavetoEdit();//your function call
}
else{
windowClose();//your function call
}
} else {
windowClose();//your function call
}
};
var validNavigation = false;
jQuery(document).ready(function () {
wireUpEvents();
});
function endSession() {
// Browser or broswer tab is closed
// Do sth here ...
alert("bye");
}
function wireUpEvents() {
/*
* For a list of events that triggers onbeforeunload on IE
* check http://msdn.microsoft.com/en-us/library/ms536907(VS.85).aspx
*/
window.onbeforeunload = function () {
debugger
if (!validNavigation) {
endSession();
}
}
// Attach the event keypress to exclude the F5 refresh
$(document).bind('keypress', function (e) {
debugger
if (e.keyCode == 116) {
validNavigation = true;
}
});
// Attach the event click for all links in the page
$("a").bind("click", function () {
debugger
validNavigation = true;
});
// Attach the event submit for all forms in the page
$("form").bind("submit", function () {
debugger
validNavigation = true;
});
// Attach the event click for all inputs in the page
$("input[type=submit]").bind("click", function () {
debugger
validNavigation = true;
});
}`enter code here`
评论