この記事の例では、JavaScript がリスニング関数をイベント ハンドラーにバインドする方法について説明します。参考のために皆さんと共有してください。詳細は次のとおりです:
JavaScript でイベント リスニング関数を Dom 要素にバインドすることは非常に一般的なことですが、ここには多くのバグもあります。さまざまなブラウザーがイベント バインディング用の多くのメソッドを提供していますが、信頼できるのは 3 つだけです:
1. 従来のバインディング方法:
elem.onclick = function( event ){ alert(event.type + 'this.innerHTML'); };
a. 従来のバインド方法は非常にシンプルで安定しています。関数本体内のこれは、イベントを処理しているノード (現在イベント ハンドラーを実行しているノードなど) も指します。
b. 要素のイベント ハンドラーは 1 つの関数しか登録できません。また、繰り返し登録すると、従来のバインド方法はイベント バブリングでのみ実行されます。
2. W3C 標準バインド方法:
var elem = document.getElementById('ID'); elem.addEventListener('click' , function( event ){ alert(event.type + ' ' + this.innerHTML + 1); } , false //冒泡阶段执行 ); elem.addEventListener('click' , function( event ){ alert(event.type + ' ' + this.innerHTML + 2); } , false );
a. このバインディング メソッドは、時間処理のキャプチャ ステージとバブリング ステージの両方をサポートします。複数のリスニング関数を同じ要素の同じイベント ハンドラーに登録でき、リスニング関数内で現在の要素を指します。
b. ただし、一般的な IE ブラウザはこの登録方法をサポートしていません。
3. IE イベントハンドラーの登録方法:
var elem = document.getElementById('a'); elem.attachEvent('onclick' , function(){ alert(window.event.srcElement.innerHTML + ' ' + this.innerHTML + 1); } ); elem.attachEvent('onclick' , function(){ alert(window.event.srcElement.innerHTML + ' ' + this.innerHTML + 2); } );
a. このバインディング メソッドは、同じイベント ハンドルを複数回登録できます。
b. IE のイベント モデルはイベント キャプチャをサポートしていません。リスニング関数本体では現在の要素を指しません。また、window.event.srcElement は現在のノードではなく、イベントが発生するノードを指します。 IE のイベント オブジェクトには同等の DOM currentTarget プロパティがありません。
4. クロスブラウザーの方法 1:
function addEvent(element, type, handler) { if (!handler.$$guid) handler.$$guid = addEvent.guid++; if (!element.events) element.events = {}; var handlers = element.events[type]; if (!handlers) { handlers = element.events[type] = {}; if (element["on" + type]) { handlers[0] = element["on" + type]; } } handlers[handler.$$guid] = handler; element["on" + type] = handleEvent; }; addEvent.guid = 1; function removeEvent(element, type, handler) { if (element.events && element.events[type]) { delete element.events[type][handler.$$guid]; } }; function handleEvent(event) { var returnValue = true; event = event || fixEvent(window.event); var handlers = this.events[event.type]; for (var i in handlers) { this.$$handleEvent = handlers[i]; if (this.$$handleEvent(event) === false) { returnValue = false; } } return returnValue; }; function fixEvent(event) { event.preventDefault = fixEvent.preventDefault; event.stopPropagation = fixEvent.stopPropagation; return event; }; fixEvent.preventDefault = function() { this.returnValue = false; }; fixEvent.stopPropagation = function() { this.cancelBubble = true; };
5. クロスブラウザーの方法 2:
function addEvent( obj, type, fn ) { if ( obj.attachEvent ) { obj['e'+type+fn] = fn; obj[type+fn] = function(){obj['e'+type+fn]( window.event );} obj.attachEvent( 'on'+type, obj[type+fn] ); } else obj.addEventListener( type, fn, false ); } function removeEvent( obj, type, fn ) { if ( obj.detachEvent ) { obj.detachEvent( 'on'+type, obj[type+fn] ); obj[type+fn] = null; } else obj.removeEventListener( type, fn, false ); }
この記事が JavaScript プログラミングのすべての人に役立つことを願っています。