【问题标题】:how to detect if a link was clicked when window.onbeforeunload is triggered?触发window.onbeforeunload时如何检测是否点击了链接?
【发布时间】:2013-02-23 00:26:03
【问题描述】:

我有 window.onbeforeunload 正确触发。它显示一个确认框,以确保用户知道他们正在导航(关闭)窗口,并且所有未保存的工作都将被删除。

我有一个独特的情况,如果用户通过单击链接离开页面,我不希望触发这种情况,但我不知道如何检测是否在函数内单击了链接以停止功能。这就是我的代码:

window.onbeforeunload = function() {
var message = 'You are leaving the page.';

/* If this is Firefox */
if(/Firefox[\/\s](\d+)/.test(navigator.userAgent) && new Number(RegExp.$1) >= 4) {
  if(confirm(message)) {
    history.go();
  } 
  else {
    window.setTimeout(function() {
      window.stop();
    }, 1);
  }
}
/* Everything else */
else {
  return message;
}
}

【问题讨论】:

    标签: javascript


    【解决方案1】:

    您正在寻找延迟事件处理。我将使用 jQuery 进行解释,因为它的代码更少:

    window._link_was_clicked = false;
    window.onbeforeunload = function(event) {
      if (window._link_was_clicked) {
        return; // abort beforeunload
      }
      // your event handling
    };
    
    jQuery(document).on('click', 'a', function(event) {
      window._link_was_clicked = true;
    });
    

    一个没有 jQuery 方便的委托处理的(非常)穷人的实现可能看起来像:

    document.addEventListener("click", function(event) {
      if (this.nodeName.toLowerCase() === 'a') {
        window._link_was_clicked = true;
      }
    }, true);
    

    这允许您页面上的所有链接离开而不调用beforeunload 处理程序。我相信您可以弄清楚如何自定义它,如果您只想为一组特定的链接允许这个(您的问题不是特别清楚)。

    【讨论】:

    • 非常感谢您的回复。我试图在没有 jQuery 的情况下使用它 - 我试图弄清楚如何集成poormans 实现但似乎无法弄清楚(请原谅我,我有点 JS 新手)。跨度>
    • 您的代码是半正确的。我已经用完整的答案回答了这个问题。
    • 如果有人在 IE 中运行时遇到问题,我必须返回 undefined 而不是 null。适用于 ie 和 chrome。
    • 第二个代码块:this 在该处理程序中将始终引用document,这显然永远不会是a 元素。在 2013 年,您需要一个从 event.target 开始并在 this 停止并检查其间的每个元素的循环。在 2018 年,在真正最新的现代浏览器上,您可以使用 DOM 的新 closest 函数(非常类似于 jQuery):if (event.target.closest("a"))...
    【解决方案2】:
    var link_was_clicked = false;
    document.addEventListener("click", function(e) {
      if (e.target.nodeName.toLowerCase() === 'a') {
        link_was_clicked = true;
      }
    }, true);
    
    window.onbeforeunload = function() {
      if(link_was_clicked) {
        link_was_clicked = false;
        return;
      }
      //other code here
    }
    

    【讨论】:

      【解决方案3】:

      您可以使用计时器区分link unloadreload/user entering a different address unload。这样你就知道beforeunload是在点击链接后直接触发的。

      使用 jQuery 的示例:

      $('a').on('click', function(){
        window.last_clicked_time = new Date().getTime();
        window.last_clicked = $(this);
      });
      
      $(window).bind('beforeunload', function() {
        var time_now = new Date().getTime();
        var link_clicked = window.last_clicked != undefined;
        var within_click_offset = (time_now - window.last_clicked_time) < 100;
      
        if (link_clicked && within_click_offset) {
          return 'You clicked a link to '+window.last_clicked[0].href+'!';
        } else {
          return 'You are leaving or reloading the page!';
        }
      });
      

      (在 Chrome 中测试)

      【讨论】:

      • IE、Edge、Firefox ?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2018-11-26
      • 2012-06-06
      • 1970-01-01
      • 1970-01-01
      • 2013-10-14
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多