在开发过程中我们会使用ifram
来嵌入一个页面或者通过window.open
打开一个新的窗口,这两个窗口之间有时候需要通信,下面我们看下具体会有哪些情况。
不同窗口之间通信有两种情况:
ifram:与通过ifram标签打开的窗口通信
window.open:与window.open打开的窗口通信
这两种情况又分为了同域下的窗口通信和不同域下的通信
同域下的窗口通信
ifram
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
// 通过js可以访问被包含页面的DOM元素
window.onload = function() {
var oBtn = document.getElementById('btn');
var oMyIframe = document.getElementById('myframe');
oBtn.onclick = function() {
// 如果我们要操作一个iframe里面的dom元素,需要通过 contentWindow 获取到iframe引入的页面的window对象
oMyIframe.contentWindow.document.body.style.background = 'red';
}
}
</script>
</head>
<body>
<input type="button" value="点击我,改变2.iframe.html的背景色" id="btn" />
<iframe id="myframe" src="2.iframe.html"></iframe>
</body>
</html>
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
window.onload = function() {
var oBtn = document.getElementById('btn');
/*
window : 当前窗口
parent : 父级窗口
top : 顶级窗口
*/
oBtn.onclick = function() {
//parent => window 如果当前页面是顶级,没有被其他页面所包含,那么parent就是当前页面的window对象,那么如果被包含了,则parent就是包含当前页面的父级页面的window对象
parent.document.body.style.background = 'green';
}
}
</script>
</head>
<body>
这里是2.iframe.html页面
<input type="button" value="点击我,改变1.iframe.html的背景色" id="btn" />
</body>
</html>
window.open
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
window.onload = function() {
var oBtn = document.getElementById('btn');
var oBtn2 = document.getElementById('btn2');
var newWindow = null;
oBtn.onclick = function() {
//window.open 返回被打开窗口的window对象
newWindow = window.open('2.window.open.html', '_blank');
}
oBtn2.onclick = function() {
newWindow.document.body.style.background = 'red';
}
}
</script>
</head>
<body>
<input type="button" value="点击我,开启一个新的窗口打开2.window.open.html页面" id="btn" />
<input type="button" value="点击我,改变2.window.open.html页面的背景色" id="btn2" />
</body>
</html>
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
window.onload = function() {
var oBtn = document.getElementById('btn');
oBtn.onclick = function() {
//window.opener : 通过window.open方法打开当前页面的窗口的window对象
window.opener.document.body.style.background = 'green';
}
}
</script>
</head>
<body>
这是4.window.open.html页面
<input type="button" value="点击我,改变1.window.open.html页面的背景色" id="btn" />
</body>
</html>
不同域下的窗口通信(跨文档通信)
问题:跨域之后之前同域下的操作都失效了,会产生跨域安全限制问题
解决:postMessage方法,通过这个方法给另外一个窗口发送信息 (注意:接收消息的窗口的window对象调用postMessage方法)
a域名
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
window.onload = function() {
var oBtn = document.getElementById('btn')
var oMyIframe = document.getElementById('myframe')
/*
postMessage : 可以通过这个方法给另外一个窗口发送信息
注意:接收消息的窗口的window对象调用postMessage方法
*/
oBtn.onclick = function() {
/*
第一个参数:发送的数据
第二个参数:接收数据的域名{带上协议}
*/
oMyIframe.contentWindow.postMessage('1', 'http://www.b.com')
}
}
</script>
</head>
<body>
<input type="button" value="点击我,www.b.com域名下postMessage.html的背景色" id="btn" />
<iframe id="myframe" src="http://www.b.com/postMessage.html"></iframe>
</body>
</html>
b域名
<!DOCTYPE HTML>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>无标题文档</title>
<script>
window.onload = function() {
// message事件 : 当窗口接收到通过postMessage发送过来的数据的时候触发
window.addEventListener('message', function(ev) {
/*
message事件的事件对象下保存了发送过来的内容
ev.data: 发送过来的数据
ev.origin: 发送消息的域名
*/
if (ev.data == '1') {
document.body.style.background = 'red';
}
}, false);
}
</script>
</head>
<body>
这是b.com的postMessage.html页面
</body>
</html>