主頁面main.htmlhtml
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>Insert title here</title> </head> <body> <form> <input type='text' id='sr'> <button type='button' id='submit'>提交</button> </form> <div id='message'></div> <iframe src='./msgIframe.html'></iframe> <script> //通道通訊 var port; var ifr = document.querySelector('iframe'); var eleBox = document.querySelector("#message"); var submit = document.querySelector("#submit"); submit.onclick=function(){ var srinput = document.querySelector("#sr"); //window.frames[0].postMessage(srinput.value, '*'); port.postMessage(srinput.value);//iframe加載後向本頁面父窗口發送消息,從e中獲取通道端口信息,而後能夠經過此port向iframe窗口中發送消息 } window.addEventListener("message", function(e){ eleBox.innerHTML = '接受到的信息是:' + e.data; if(e.ports){ port=e.ports[0]; } }, false); //跨文檔通訊 /*var eleBox = document.querySelector("#message"); var submit = document.querySelector("#submit"); submit.onclick=function(){ var srinput = document.querySelector("#sr"); postMessage(srinput.value, '*'); } window.addEventListener("message", function(e){ eleBox.innerHTML = '接受到的信息是:' + e.data; }, false);*/ </script> </body> </html>
加載iframe頁面,sub.htmlwindows
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>Insert title here</title> </head> <body> <div id='message'></div> <script> var port; var eleBox = document.querySelector("#message"); var channel = new MessageChannel(); window.addEventListener('DOMContentLoaded', function(e) { //向父窗口發送消息, window.parent.postMessage('發送頁加載完畢', '*',[channel.port2]); /* channel.port1.addEventListener('message', function(e){ eleBox.innerHTML='通道獲取的消息爲:'+e.data; }, false); */ channel.port1.onmessage(function(e){ eleBox.innerHTML='通道獲取的消息爲:'+e.data; }) channel.port1.start(); } ,false); </script> </body> </html>
window.postMessage() 方法能夠安全地實現跨源通訊。一般,對於兩個不一樣頁面的腳本,只有當執行它們的頁面位於具備相同的協議(一般爲https),端口號(443爲https的默認值),以及主機 (兩個頁面的模數 Document.domain
設置爲相同的值) 時,這兩個腳本才能相互通訊。window.postMessage() 方法提供了一種受控機制來規避此限制,只要正確的使用,這種方法就很安全。安全
window.postMessage() 方法被調用時,會在全部頁面腳本執行完畢以後(e.g., 在該方法以後設置的事件、以前設置的timeout 事件,etc.)向目標窗口派發一個 MessageEvent
消息。 該MessageEvent
消息有四個屬性須要注意: message 屬性表示該message 的類型; data 屬性爲 window.postMessage 的第一個參數;origin 屬性表示調用window.postMessage() 方法時調用頁面的當前狀態; source 屬性記錄調用 window.postMessage() 方法的窗口信息。app
postMessage語法
otherWindow.postMessage(message, targetOrigin, [transfer]);
targetOrigin:經過窗口的origin屬性來指定哪些窗口能接收到消息事件,其值能夠是字符串"*"(表示無限制)或者一個URI。在發送消息的時候,若是目標窗口的協議、主機地址或端口這三者的任意一項不匹配targetOrigin提供的值,那麼消息就不會被髮送;
transfer:
可選是一串和message 同時傳遞的 Transferable
對象. 這些對象的全部權將被轉移給消息的接收方,而發送一方將再也不保有全部權。框架
Channel Messaging API容許兩個獨立的腳本在不一樣的瀏覽環境(瀏覽上下文)中鏈接到同一個文檔(例如兩個iframes框架或主文檔和一個iframe框架,或兩個文檔經過SharedWorker
一個共享工做線程或 兩個線程)進行直接通訊,經過兩端各有一個端口port的雙向通道channel(或管道)來傳遞消息。dom
使用MessageChannel()
構造器建立消息通道。一旦建立,管道的兩個端口能夠經過MessageChannel.port1
和MessageChannel.port2
屬性來訪問。建立該通道的應用app使用port1,而應用app端口的另外一端使用port2,你發送一個消息到port2,使用window.postMessage和兩個參數(要發送的消息,以及傳輸全部權對象,本例中指端口自己)將端口轉移到另外一個瀏覽上下文。ide
當這些可傳輸的對象被轉移時,它們在以前的上下文中被「停止」—它們以前所屬的上下文。例如,一個端口在發送時不能被原始上下文使用。注意,目前只能傳輸ArrayBuffer
和MessagePort
對象。post
其餘瀏覽上下文可使用 MessagePort.onmessage
來監聽消息,並使用事件的data屬性來獲取消息內容。而後您可使用MessagePort.postMessage
將消息發送回原始文檔。this
當你想中止發送消息時,能夠調用MessagePort.close
來關閉端口。spa
Channel messaging interfaces/消息通道接口
建立一個新的消息通道來發送消息。
控制消息通道上的端口,容許從一個端口發送消息,並偵聽到達另外一個端口的消息。
一組MessagePorts; 一個容許同時向多個端口廣播消息的實驗性解決方案。
參考:
https://developer.mozilla.org/en-US/docs/Web/API/Channel_Messaging_API
https://developer.mozilla.org/en-US/docs/Web/API/Web_Workers_API