zoukankan      html  css  js  c++  java
  • 事件绑定(终极版)

    内容提纲:

    1.问题所在

    2.设置代码

    发文不易,转载注明出处!

     

    1.问题所在

    现代绑定中W3C使用的是:addEventListener和removeEventListener。IE使用的是attachEvent和detachEvent。我们知道IE的这两个问题多多,并且伴随内存泄漏。所以,解决这些问题非常有必要。

    那么我们希望解决非IE浏览器事件绑定哪些问题呢?

    1.支持同一元素的同一事件句柄可以绑定多个监听函数;

    2.如果在同一元素的同一事件句柄上多次注册同一函数,那么第一次注册后的所有注册都被忽略;

    3.函数体内的this指向的应当是正在处理事件的节点(如当前正在运行事件句柄的节点);

    4.监听函数的执行顺序应当是按照绑定的顺序执行;

    5.在函数体内不用使用 event = event || window.event; 来标准化Event对象;

    我们尝试着通过使用传统事件绑定对IE进行封装。

     

    2.设置代码

      1 //跨浏览器添加事件绑定
      2 
      3 function addEvent(obj, type, fn) {
      4 
      5        if (typeof obj.addEventListener != 'undefined') {
      6 
      7               obj.addEventListener(type, fn, false);
      8 
      9        } else {
     10 
     11               //创建事件类型的散列表(哈希表)
     12 
     13               if (!obj.events) obj.events = {};
     14 
     15               //创建存放事件处理函数的数组
     16 
     17               if (!obj.events[type]) {
     18 
     19                      obj.events[type] = []; 28 
     29                      //执行事件处理
     30 
     31                      obj['on' + type] = addEvent.exec;
     32 
     33               } else {
     34 
     35                      //同一个注册函数取消计数
     36 
     37                      if (addEvent.array(fn,obj.events[type])) return false;  
     38 
     39               }
     40 
     41               //通过计数器存储
     42 
     43               obj.events[type][addEvent.ID++] = fn;
     44 
     45        }
     46 
     47 }
     48 
     49  
     50 
     51 addEvent.array = function (fn, es){
     52 
     53        for (var i in es) {
     54 
     55               if (es[i] == fn) return true;
     56 
     57        }
     58 
     59        return false;
     60 
     61 }
     62 
     63  
     64 
     65 //每个事件处理函数的ID计数器
     66 
     67 addEvent.ID = 0;
     68 
     69  
     70 
     71 //事件处理函数调用
     72 
     73 addEvent.exec = function (event) {
     74 
     75        var e = event || addEvent.fixEvent(window.event);
     76 
     77        var es = this.events[e.type];
     78 
     79        for (var i in es) {
     80 
     81               es[i].call(this, e);
     82 
     83        }
     84 
     85 };
     86 
     87  
     88 
     89 //获取IE的event,兼容W3C的调用
     90 
     91 addEvent.fixEvent = function (event) {
     92   //为event添加preventDefault方法
     93        event.preventDefault = addEvent.fixEvent.preventDefault;
     95        event.stopPropagation = addEvent.fixEvent.stopPropagation;
     96 
     97        return event;
     98 
     99 };
    100 
    101  
    102 
    103 //兼容IE和W3C阻止默认行为
    104 
    105 addEvent.fixEvent.preventDefault = function () {
    106 
    107        this.returnValue = false;
    108 
    109 };
    110 
    111  
    112 
    113 //兼容IE和W3C取消冒泡
    114 
    115 addEvent.fixEvent.stopPropagation = function () {
    116 
    117        this.cancelBubble = true;
    118 
    119 };
    120 
    121  
    122 
    123 //跨浏览器删除事件
    124 
    125 function removeEvent(obj, type, fn) {
    126 
    127        if (typeof obj.removeEventListener != 'undefined') {
    128 
    129               obj.removeEventListener(type, fn, false);
    130 
    131        } else {
    132 
    133               var es = obj.events[type];
    134 
    135               for (var i in es) {
    136 
    137                      if (es[i] == fn) {
    138 
    139                             delete obj.events[type][i];
    140 
    141                      }
    142 
    143               }
    144 
    145        }
    146 
    147 }
  • 相关阅读:
    git ——visual studio code 工具之 Git Graph & git clone & git checkout
    docker中添加redis & 在程序中应用
    Configuring Redis for ASP.NET Core Session Store(转载)
    Configuring Redis Session State In ASP.NET Core(转载)
    http请求端口占用异常——处理思路
    在pods中添加有关httpclient的 压力测试 & 监控
    Singleton HttpClient? Beware of this serious behaviour and how to fix it
    HttpClient 之 CLOSE_WAIT
    HttpClient的使用
    HttpClient连接池之CLOSE_WAIT
  • 原文地址:https://www.cnblogs.com/ttcc/p/3963457.html
Copyright © 2011-2022 走看看