关于iframe一些问题汇总
关于实现iframe功能替代方案
使用iframe能很好的嵌入其他的网页或者网站,但是iframe每次加载都会浪费好多的时间,且会阻止其他元素的加载,搜索引擎也不能识别页面ifram框架中被调用的链接、文本、图片等等内容的。
Html代码
<ul class="list-side">
<li><a target="a.html" >about</a></li>
<li><a target="b.html" >news</a></li>
<li><a target="c.html" >product</a></li>
<li><a href="http://ucmic.blogspot.com/" target="_blank" >contact</a></li>
</ul>
<div id="iframe">
<!--jquery 插入html 位址-->
</div>
实现功能的Javascript代码
$(document).ready(function(){
$.get("a.html",function(data){ //初始將a.html include div#iframe
$("#iframe").html(data);
});
$(function(){
$('.list-side li').click(function() {
// 找出 li 中的超链接 href(#id)
var $this = $(this),
_clickTab = $this.find('a').attr('target'); // 找到链接a中的targer的值
$.get(_clickTab,function(data){
$("#iframe").html(data);
});
});
});
iframe 父子通信
同域: 数据交换和DOM元素互访就简单的多 , 其实质是DOM元素的访问 父 =>子 : window.parent window.top 子 => 父: window.getElementsByName('iframe')
注意事项 要确保在Iframe加载完成后再进行操作,如果Iframe还未加载完成就开始调用里面的方法或变量,无疑会产生错误。判断Iframe是否加载完毕有两种方法: 1.在Iframe上用onload事件; 2.用document.readyState=="complete"来判断
跨域: 安全机制则不能使用同域名下的通信方式 跨域iframe是实现前端微服务最简单易行的方式。
父页面向子页面传递数据
实现的技巧就是利用 location 对象的 hash 值,通过它传递通信数据,我们只需要在父页面设置 iframe的 src 后面多加个#data 字符串(data就是你要传递的数据),然后在 子页面 中通过某种方式能即时的获取到这儿 data 就可以了,其实常用的一种方式就是:
- 在 子页面 中通过 setInterval 方法设置定时器, 监听 location.href 的变化即可获得上面的 data 信息
- 然后 子页面 就能根据这个 data 信息进行相应的逻辑处理。
子页面向父页面传递数据 [比较复杂]
实现的技巧就是利用一个代理 Iframe C,它嵌入到 子页面中,并且和父页面必须保持是同域,然后我们通过它充分利用上面第一种通信方式的实现原理就能把 子页面的数据传递给 iframeC,接下来的问题就是怎么让iframeC把数据传递给主页面A ,因为,iframeC 和主页面是同域的,所以它们之间传递数据就变得简单多了,属于同域名下的通信问题了,如前面所讨论的,在这里的可以使用一个经常使用的属性 window.top (也可以使用window.parent.parent),它返回对载入浏览器得最顶层 window 对象的引用,这样我们就能直接条用父页面中方法啦。
这种页面代理的方式有个显著问题: 不可避免的要产生网络请求,我们原本希望它们能够直接在客户端通信,避免不必要的网络请求开销
postMessage 方案 : IE8以上
- 定义 trustedOrigin
- 发送信息: document.getElementById("widget").contentWindow.postMessage(data, trustedOrigin);
- 订阅信息: window.addEventListener('message', msgHandler(data) {
})