サンプル
以下のサンプルでは、http://localhost/messaging_sample2_1.html と http://localhost:8080/messaging_sample2_2.html とでやり取りをしている想定になっています。
オリジン、ファイル名は実際のものに合わせてください。同一オリジンのファイル同士で試した場合でも動作は変わりません。
IEとFireFoxはチャネルメッセージング未実装です。
また、Google Chromeではセキュリティ上、ローカルのHTMLファイルから他のローカルファイルの内容にアクセスする場合には、
ファイル読み込み自体を許可する「--allow-file-access」フラグと、
ローカルファイルからのファイル読み込みを許可する「--allow-file-access-from-files」フラグの両方を付けて起動する必要があります。
そのため、サンプルをローカルファイルとして実行する場合は、Google Chromeについては上記フラグを付けて起動したうえで実行してください。
Windowsの場合は以下のようになります。
<Google Chromeのインストールフォルダ>\chrome.exe --allow-file-access --allow-file-access-from-files
サンプル
インラインフレーム呼び出し側 http://localhost/messaging_sample2_1.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<style type="text/css">
#target_iframe{
width:500px;
height:200px;
}
</style>
<title>サンプル</title>
</head>
<body>
<div>
フレーム内のドキュメントの文字列と背景色が選択したものに変わります。<br>
文字列の通信と背景色の通信はそれぞれ独立したMessageChannelで行われます。<br>
<select name="text" id="textSelect">
<option value="メッセージ1">メッセージ1</option>
<option value="メッセージ2">メッセージ2</option>
<option value="メッセージ3">メッセージ3</option>
</select>
<select name="color" id="colorSelect">
<option value="white"> 白色 </option>
<option value="red"> 赤色 </option>
<option value="blue"> 青色 </option>
<option value="yellow"> 黄色 </option>
<option value="green"> 緑色 </option>
</select>
</div>
<div><iframe src="http://localhost:8080/messaging_sample2_2.html" id="target_iframe"></iframe></div>
<p id="output"></p>
<script type="text/javascript">
// HTML要素の参照を取得
var iframe = document.getElementById("target_iframe");
var output = document.getElementById("output");
var textSelect = document.getElementById("textSelect");
var colorSelect = document.getElementById("colorSelect");
// チャンネルの共通初期化処理関数
function initChannel(select){
// MessageChannel生成
var channel = new MessageChannel();
// チャンネルの各ポートの送受信を有効化
channel.port1.start();
channel.port2.start();
// 選択肢が変更されるたびに選択された値をフレームへ送信する
select.onchange = function(event){
channel.port1.postMessage(select.value);
}
// 返信されてきたメッセージを表示する
channel.port1.onmessage = function(event){
output.innerHTML = event.data;
}
// フレーム内のドキュメント側で使用するポートを返す
return channel.port2;
}
// インラインフレームの読み込み完了時のイベントハンドラ
iframe.onload = function(event){
// 文字列を指定する通信用のチャンネルの初期化処理
var textPort = initChannel(textSelect);
// 背景色を指定する通信用のチャンネルの初期化処理
var colorPort = initChannel(colorSelect);
// フレーム内のドキュメント側で使用するポートを配列に格納
var ports = [textPort,colorPort];
// クロスドキュメントメッセージングでポート配列をフレームに送信
try{
// Chrome、Safari用呼び出し
iframe.contentWindow.postMessage("",ports, "http://localhost:8080");
} catch(e){
// Opera用呼び出し
iframe.contentWindow.postMessage("","http://localhost:8080",ports);
}
}
</script>
</body>
</html>
インラインフレーム内 http://localhost:8080/messaging_sample2_2.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>サンプル インラインフレーム内のドキュメント</title>
</head>
<body>
<span id="output"></span>
<script type="text/javascript">
// HTML要素を取得
var body = document.getElementsByTagName('BODY')[0];
var output = document.getElementById('output');
// クロスドキュメントメッセージングの受信イベント
window.onmessage = function(event){
// 送信元のオリジンを確認
if(event.origin == "http://localhost"){
// 文字列変更のためのポートを取得
var textPort = event.ports[0];
// 受信時のイベントハンドラ定義
textPort.onmessage = function(ev){
output.innerHTML = ev.data;
textPort.postMessage("文字列を「"+ev.data+"」に変更しました");
}
// 背景色変更のためのポートを取得
var colorPort = event.ports[1];
// 受信時のイベントハンドラ定義
colorPort.onmessage = function(ev){
body.style.backgroundColor = ev.data;
output.style.backgroundColor = "white";
output.style.color = "black";
colorPort.postMessage("背景色を" + ev.data + "に変更しました");
}
}
}
</script>
</body>
</html>
関連項目