addEventListenerを使用してノードにアタッチされたイベントリスナーを取得する


106

私はすでにこれらの質問を見てきました:

ただし、いずれも、イベントリスナーが作成される前にプロトタイプaddEventListenerを変更せずに、を使用してノードにアタッチされたイベントリスナーのリストを取得する方法に答えていませんaddEventListener

VisualEventがすべてのイベントリスナー(iphone固有のもの)を表示しないため、これを(ある程度)プログラムで実行したいと考えています。



「ややプログラムで」と事実受け入れ答えこの質問については、デベロッパーツールの機能があるが、この列挙された質問の重複ます。JSソリューションを探している人にとっての答えは、「1つはありません」です
Nickolay

回答:


135

Chrome DevTools、Safari Inspector、FirebugはgetEventListeners(node)をサポートしています

getEventListeners(ドキュメント)


6
getEventListenersメソッドはFirefox 35バージョンをサポートしていないことに注意してください。
MURATSPLAT、2014

Firefoxでは機能しない可能性がありますが、開発者は複数のブラウザで開発します。既存のサイトを変更する必要がある場合は、これで確実に役立ちます。
JasonXA 2015年

1
ないことFirefoxの69
ヴィタリーZdanevich

65

できません。

ノードに接続されているすべてのイベントリスナーのリストを取得する唯一の方法は、リスナー接続呼び出しをインターセプトすることです。

DOM4 addEventListener

言う

リストに同じタイプ、リスナー、およびキャプチャーのイベントリスナーが既に存在する場合を除き、タイプがタイプに設定され、リスナーがリスナーに設定され、キャプチャーがキャプチャーに設定されたイベントリスナーの関連リストにイベントリスナーを追加します。

「イベントリスナーのリスト」にイベントリスナーが追加されることを意味します。それで全部です。このリストがどうあるべきか、どのようにアクセスすべきかという概念はありません。


12
それがなぜこのように機能しなければならないかについての正当化または推論を提供する可能性はありますか?明らかに、ブラウザはすべてのリスナーが何であるかを知っています。
Darth Egregious

3
@ user973810:どのように彼にこれを正当化させたいですか?DOM APIはそれを行う方法を提供しておらず、現在のブラウザでそれを行う非標準的な方法はありません。なぜそうなのか、私にはよくわかりません。やりたいことは理にかなっているようです。
Tim Down、

このためにDOMにAPIを追加することについて、いくつかのスレッドが横になっているのを見てきました。
Raynos

@TimDown編集が役立ちます。「getEventListeners」などの仕様がないことがわかると、そのようなことがない理由が正当化されます。
Darth Egregious

24

これを行うネイティブの方法がないため、ここで私が見つけたそれほど煩わしくないソリューションがあります(「古い」プロトタイプメソッドを追加しないでください)。

var ListenerTracker=new function(){
    var is_active=false;
    // listener tracking datas
    var _elements_  =[];
    var _listeners_ =[];
    this.init=function(){
        if(!is_active){//avoid duplicate call
            intercep_events_listeners();
        }
        is_active=true;
    };
    // register individual element an returns its corresponding listeners
    var register_element=function(element){
        if(_elements_.indexOf(element)==-1){
            // NB : split by useCapture to make listener easier to find when removing
            var elt_listeners=[{/*useCapture=false*/},{/*useCapture=true*/}];
            _elements_.push(element);
            _listeners_.push(elt_listeners);
        }
        return _listeners_[_elements_.indexOf(element)];
    };
    var intercep_events_listeners = function(){
        // backup overrided methods
        var _super_={
            "addEventListener"      : HTMLElement.prototype.addEventListener,
            "removeEventListener"   : HTMLElement.prototype.removeEventListener
        };

        Element.prototype["addEventListener"]=function(type, listener, useCapture){
            var listeners=register_element(this);
            // add event before to avoid registering if an error is thrown
            _super_["addEventListener"].apply(this,arguments);
            // adapt to 'elt_listeners' index
            useCapture=useCapture?1:0;

            if(!listeners[useCapture][type])listeners[useCapture][type]=[];
            listeners[useCapture][type].push(listener);
        };
        Element.prototype["removeEventListener"]=function(type, listener, useCapture){
            var listeners=register_element(this);
            // add event before to avoid registering if an error is thrown
            _super_["removeEventListener"].apply(this,arguments);
            // adapt to 'elt_listeners' index
            useCapture=useCapture?1:0;
            if(!listeners[useCapture][type])return;
            var lid = listeners[useCapture][type].indexOf(listener);
            if(lid>-1)listeners[useCapture][type].splice(lid,1);
        };
        Element.prototype["getEventListeners"]=function(type){
            var listeners=register_element(this);
            // convert to listener datas list
            var result=[];
            for(var useCapture=0,list;list=listeners[useCapture];useCapture++){
                if(typeof(type)=="string"){// filtered by type
                    if(list[type]){
                        for(var id in list[type]){
                            result.push({"type":type,"listener":list[type][id],"useCapture":!!useCapture});
                        }
                    }
                }else{// all
                    for(var _type in list){
                        for(var id in list[_type]){
                            result.push({"type":_type,"listener":list[_type][id],"useCapture":!!useCapture});
                        }
                    }
                }
            }
            return result;
        };
    };
}();
ListenerTracker.init();

また、ウィンドウイベントリスナーをインターセプトする必要があります。それ以外は、これはうまくいきます!

2

$ ._ data($( '[selector]')[0]、 'events');を使用して、すべてのjQueryイベントを取得できます。[selector]を必要なものに変更します。

eventsReportと呼ばれるjQueryによって添付されたすべてのイベントを収集するプラグインがあります。

また、私はこれをより良いフォーマットで行う独自のプラグインを書きます。

しかし、とにかく、addEventListenerメソッドによって追加されたイベントを収集できないようです。addEventListener呼び出しをラップして、ラップ呼び出しの後に追加されたイベントを格納できる場合があります。

これは、開発ツールで要素に追加されたイベントを確認するための最良の方法のようです。

ただし、委任されたイベントは表示されません。そこで、jQuery eventsReportが必要です。

更新:これで、addEventListenerメソッドによって追加されたイベントを確認できます。この質問に対する正しい回答を参照してください。


これは非公開の非公開インターフェースであり、間もなく廃止される可能性があるため、それに依存しないでください。
mgol 2014

1
うん、でも私が答えたとき、開発ツールにはそのような能力はありませんでした。したがって、選択できるものは何もありませんでした。
ランティエフ2014年

@Rantievは非推奨です。その回答を削除できますか?
Julio Marins、2015

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.