Trigger and listen events across iframes

最近作的幾個軟件項目,須要大量使用IFrame,IFrame與主窗體通訊的問題天然浮現。code

稍做研究,可知此問題的解決思路是這樣的:事件

  1. IFrame只在內部觸發消息和監聽事件,也就是說,在IFrame加載的網頁,並不知道本身被加載在IFrame中,它自顧自地觸發和監聽事件。
  2. 主窗體知道本身有IFrame,會主動向IFrame觸發事件,同時向IFrame監聽本身感興趣的事件。

IFrame觸發消息

function trigger(name, payload){
    $.event.trigger({
        type: name,
        payload: payload
    });
}

調用示例:get

trigger('Event-B', {words: 'Hello! I\'m B.'});

IFrame監聽事件

function listen(name, callback){
    function warn(warning){
        console && console.warn && console.warn('listen:', warning);
    }
    $(document).on(name, function(event){
        if(callback && callback.constructor === Function){
            callback(event.payload);
        }else{
            console.warn('callback should be a "Function" object');
        }
    });
}

調用示例:iframe

listen('Event-A', function(payload){
    console && console.log && console.log('Event-A receieved. The payload is ' + JSON.stringify(payload));
    });

主窗體向IFrame觸發事件

function triggerOnIFrame(iframe, name, payload){
    function warn(warning){
        console && console.warn && console.warn('triggerOnIFrame:', warning);
    }
    if(!name){
        warn('"name" of the event is excepted.');
    }else{
        var $iframe = $(iframe);
        if($iframe.length>0){
            $iframe.each(function(i, item){
                item.contentWindow.$(item.contentWindow.document).trigger({
                    type: name,
                    payload: payload
                });
            });
        }else{
            warn('\'jQuery selector \'' + iframe + '\')\' not found in DOM.' );
        }
    }
}

調用示例:string

triggerOnIFrame('iframe#map', 'Event-A', {word: 'Hello! I\'m A.'});

主窗體監聽IFrame事件

function listenOnIFrame(iframe, name, callback){
    function warn(warning){
        console && console.warn && console.warn('listenOnIFrame:', warning);
    }

    var $iframe = $(iframe);

    if($iframe.length>0){
        $iframe.each(function(i, item){
            $(item).on('load', function(){
                item.contentWindow.$(item.contentWindow.document).on(name, function(event){
                    if(callback && callback.constructor === Function){
                        callback(event.payload);
                        }else{
                            warn('"callback" should be a "Function" object');
                        }
                    });
            });
        });
    }else{
        warn('\'jQuery selector \'' + iframe + '\')\' not found in DOM.' );
    }
}

調用示例:it

listenOnIFrame('iframe#map', 'Event-B', function(payload){
    console && console.log && console.log(payload);
});

參考連接:io

相關文章
相關標籤/搜索