web-dev-qa-db-ja.com

JavaScript:イベントリスナーを削除する

リスナー定義内のイベントリスナーを削除しようとしています。

canvas.addEventListener('click', function(event) {
    click++;
    if(click == 50) {
        // remove this event listener here!
    }
// More code here ...

どうすればそれができますか? this = event ...ありがとうございます。

110
thomas

名前付き関数を使用する必要があります。

また、click変数は、インクリメントするためにハンドラーの外側にある必要があります。

var click_count = 0;

function myClick(event) {
    click_count++;
    if(click_count == 50) {
       // to remove
       canvas.removeEventListener('click', myClick);
    }
}

// to add
canvas.addEventListener('click', myClick);

編集:次のようにclick_counter変数を閉じることができます:

var myClick = (function( click_count ) {
    var handler = function(event) {
        click_count++;
        if(click_count == 50) {
           // to remove
           canvas.removeEventListener('click', handler);
        }
    };
    return handler;
})( 0 );

// to add
canvas.addEventListener('click', myClick);

これにより、複数の要素にわたってカウンタを増分できます。


それが望ましくなく、それぞれに独自のカウンターが必要な場合は、次のようにします。

var myClick = function( click_count ) {
    var handler = function(event) {
        click_count++;
        if(click_count == 50) {
           // to remove
           canvas.removeEventListener('click', handler);
        }
    };
    return handler;
};

// to add
canvas.addEventListener('click', myClick( 0 ));

編集:最後の2つのバージョンで返されるハンドラーの名前を忘れていました。修正済み

107
user113716
   canvas.addEventListener('click', function(event) {
      click++;
      if(click == 50) {
          this.removeEventListener('click',arguments.callee,false);
      }

それを行う必要があります。

73
edeverett

次のように、名前付き関数式(この場合、関数の名前はabc)を使用できます。

let click = 0;
canvas.addEventListener('click', function abc(event) {
    click++;
    if (click >= 50) {
        // remove event listener function `abc`
        canvas.removeEventListener('click', abc);
    }
    // More code here ...
}

迅速で汚い作業例: http://jsfiddle.net/8qvdmLz5/2/

名前付き関数式の詳細: http://kangax.github.io/nfe/

40
Tama
element.querySelector('.addDoor').onEvent('click', function (e) { });
element.querySelector('.addDoor').removeListeners();


HTMLElement.prototype.onEvent = function (eventType, callBack, useCapture) {
this.addEventListener(eventType, callBack, useCapture);
if (!this.myListeners) {
    this.myListeners = [];
};
this.myListeners.Push({ eType: eventType, callBack: callBack });
return this;
};


HTMLElement.prototype.removeListeners = function () {
if (this.myListeners) {
    for (var i = 0; i < this.myListeners.length; i++) {
        this.removeEventListener(this.myListeners[i].eType, this.myListeners[i].callBack);
    };
   delete this.myListeners;
};
};
7
Vinyl Windows

誰かがjqueryを使用する場合、次のように実行できます。

var click_count = 0;
$( "canvas" ).bind( "click", function( event ) {
    //do whatever you want
    click_count++;
    if ( click_count == 50 ) {
        //remove the event
        $( this ).unbind( event );
    }
});

それが誰かを助けることができることを願っています。 @ user113716によって与えられた答えがうまく機能することに注意してください:)

4
youssman

@Cyber​​nateのソリューションが機能しない場合は、参照できるようにトリガーを独自の関数に分割してみてください。

clickHandler = function(event){
  if (click++ == 49)
    canvas.removeEventListener('click',clickHandler);
}
canvas.addEventListener('click',clickHandler);
4
Brad Christie

次のように、ハンドラ関数を事前に定義する必要があると思います。

var myHandler = function(event) {
    click++; 
    if(click == 50) { 
        this.removeEventListener('click', myHandler);
    } 
}
canvas.addEventListener('click', myHandler);

これにより、内部から名前でハンドラーを削除できます。

1
Ender