跨浏览器事件对象

2022-02-28  本文已影响0人  _静夜听雨_

虽然 DOM 和 IE 的事件对象并不相同,但它们有足够的相似性可以实现跨浏览器方案。DOM 事件对象中包含 IE 事件对象的所有信息和能力,只是形式不同。这些共性可让两种事件模型之间的映射成 为可能。本章前面的 EventUtil 对象可以像下面这样再添加一些方法:

var EventUtil = {
    addHandler: function(element, type, handler) {
// 为节省版面,删除了之前的代码 },
    getEvent: function(event) {
      return event ? event : window.event;
    },
    getTarget: function(event) {
      return event.target || event.srcElement;
    },
    preventDefault: function(event) {
      if (event.preventDefault) {
        event.preventDefault();
      } else {
        event.returnValue = false;
      }
    },
    removeHandler: function(element, type, handler) { 
        //......省略 
    },
    stopPropagation: function(event) {
        if (event.stopPropagation) {
            event.stopPropagation();
        } else {
            event.cancelBubble = true;
        }
    }
};

这里一共给 EventUtil 增加了 4 个新方法。首先是 getEvent(),其返回对 event 对象的引用。 IE 中事件对象的位置不同,而使用这个方法可以不用管事件处理程序是如何指定的,都可以获取到 event 对象。使用这个方法的前提是,事件处理程序必须接收 event 对象,并把它传给这个方法。下 面是使用 EventUtil 中这个方法统一获取 event 对象的一个例子:

btn.onclick = function(event) {
      event = EventUtil.getEvent(event);
};

在 DOM 合规的浏览器中,event 对象会直接传入并返回。而在 IE 中,event 对象可能并没有被 定义(因为使用了 attachEvent()),因此返回 window.event。这样就可以确保无论使用什么浏览器, 都可以获取到事件对象。
第二个方法是 getTarget(),其返回事件目标。在这个方法中,首先检测 event 对象是否存在 target 属性。如果存在就返回这个值;否则,就返回 event.srcElement 属性。下面是使用这个方 法的示例:

btn.onclick = function(event) {
    event = EventUtil.getEvent(event);
    let target = EventUtil.getTarget(event);
};

第三个方法是 preventDefault(),其用于阻止事件的默认行为。在传入的 event 对象上,如果 有 preventDefault()方法,就调用这个方法;否则,就将 event.returnValue 设置为 false。下 面是使用这个方法的例子:

let link = document.getElementById("myLink"); 
link.onclick = function(event) {
  event = EventUtil.getEvent(event);
  EventUtil.preventDefault(event);
};

以上代码能在所有主流浏览器中阻止单击链接后跳转到其他页面。这里首先通过 EventUtil. getEvent()获取事件对象,然后又把它传给了 EventUtil.preventDefault()以阻止默认行为。
第四个方法 stopPropagation()以类似的方式运行。同样先检测用于停止事件流的 DOM 方法,如果没有再使用 cancelBubble 属性。下面是使用这个通用 stopPropagation()方法的示例:

let btn = document.getElementById("myBtn");
btn.onclick = function(event) {
 console.log("Clicked");
 event = EventUtil.getEvent(event);
 EventUtil.stopPropagation(event);
};
document.body.onclick = function(event) {
 console.log("Body clicked");
};

同样,先通过 EventUtil.getEvent()获取事件对象,然后又把它传给了 EventUtil.stop Propagation()。不过,这个方法在浏览器上可能会停止事件冒泡,也可能会既停止事件冒泡也停止 事件捕获。

上一篇下一篇

猜你喜欢

热点阅读