2012-09-27 48 views
1

我目前正在開發一個小書籤,它可以打開一個iframe,並來回設置postMessage的通信。這一切都很好。 但是,貌似是因爲小書籤是作爲一個匿名函數加載的,如果我在頁面上多次運行小書籤,監聽器就會成倍增長。保持小書籤生成多個事件監聽器

是否有某種方式來跟蹤這些addEventListeners,以便它們不會加倍?

我是否需要在匿名函數之外定義rp_receive_message?

下面的代碼示例:

var rp_receive_message = function (e) { 
    var response = e.data; 
    console.log("got message with "+ response); 
    }; 

if (window.addEventListener) { 
    window.addEventListener('message', rp_receive_message, false); 
} else { 
    window.attachEvent('onmessage', rp_receive_message); 
} 

var s1 = window.document.createElement('iframe'); 

s1.setAttribute('src', 'http://mydomain.com/iframe.html'); 
s1.setAttribute('id', 'testiframe'); 
s1.setAttribute('width', '700'); 
s1.setAttribute('height', '550'); 
s1.setAttribute('frameBorder', '0'); 
s1.setAttribute('onload', 'this.contentWindow.postMessage(window.location.href, "http://mydomain.com/iframe.html");'); 


document.getElementById('container').appendChild(s1); 

回答

0

也許這將解決這個問題:

window.onmessage = rp_receive_message; 

正如你提到的,下面的代碼可能本身是不夠的。我不知道addEventListener和attachEvent是否會多次添加相同的函數,但如果他們願意,我一點也不會感到驚訝。我建議只測試它。

window.rp_receive_message = function(){...} 

如果你不喜歡任何一個解決方案,你就必須建立一個全局變量,這似乎不是任何不同或大大優於以上。 global可以是一個簡單的布爾值來檢查事件是否已被附加,或者它可以是您自己更新的附加事件的列表。 AFAIK,我敢肯定,沒有原生的JS解決方案來獲取事件監聽器列表已附加到特定的事件。像jQuery這樣的庫可以維護列表並讓你閱讀它們;並可能有其他技術,是您的一般問題的優雅解決方案。

+0

簡單但可行的解決方案!看來多次運行使用新的rp_receive_message有效地覆蓋window.onmessage,而不是每次都對新的匿名函數的rp_receive_message創建一個新的偵聽器。我將不得不在各種環境中嘗試。謝謝! – sinbonders

+0

任何人都知道爲什麼在IE8的window.onmessage上調用window.postMessage似乎不通過事件?在我上面的例子中(使用window.onmessage),e是未定義的,並且e.data當然不存在,但函數被觸發。 – sinbonders

+0

' window.onmessage = function(e){alert(e.data)}; window.postMessage('hey','https://www.google.com'); ' 結果在'SCRIPT5007:無法獲取屬性'數據'的值:對象爲空或未定義'在IE9模式下的IE9。 postMessage調用該函數,但'e'未定義。有任何想法嗎? – sinbonders