如何设置iframe高度自适应在跨域情况下的可用方法


Posted in Javascript onSeptember 06, 2013

在页面上使用iframe来动态加载页面内容是网页开发中比较常见的方法。在父页面中给定一个不带滚动条的iframe,然后对属性src指定一个可加载的页面,这样当父页面被访问的时候,子页面可以被自动加载。iframe的高度需要根据子页面的实际高度来进行调整。如果iframe的高度小于子页面的实际高度,超出的部分无法显示;相反,如果iframe的高度过高,则页面上会出现大量的空白区域。我们可以通过属性或者CSS来设置iframe的高度,当不确定子页面内容的高度时,也可以通过脚本来进行动态指定。但是如果子页面不在同一域中怎么办?这时候脚本没有办法获取到子页面的高度,存在JavaScript跨域的问题!

如题所述,本文在介绍可用方法的同时,也向大家询问除下文列出来的方法之外是否还有其它方法可寻?

通过属性或CSS来设置iframe的高度这里就不再具体介绍了。首先来看看如何通过脚本进行设置。

function ChangeFrameHeight(id) { 
var count = 1; (function() { 
var frm = document.getElementById(id); 
var subWeb = document.frames ? document.frames[id].document : frm.contentDocument; 
if (subWeb != null) { 
var height = Math.max(subWeb.body.scrollHeight, subWeb.documentElement.scrollHeight); 
frm.height = height; 
} 
if (count < 3) { 
count = count + 1; 
window.setTimeout(arguments.callee, 2000); 
} 
})(); 
}

假设iframe子页面和父页面都在同一域内,通过该脚本可以对给定id的iframe高度进行动态调整。为了防止父页面在子页面之前加载完成,该函数会每隔2秒重新执行一次,一共执行3次。极端情况下子页面的加载速度会慢于父页面,可适当对执行次数和时间做调整。
<iframe frameborder="0" width="450" marginheight="0" marginwidth="0" scrolling="no" id="frm1" name="frm1" src="abc.html" onload="ChangeFrameHeight('frm1')"></iframe>

如果遇到子页面跨域的问题,可通过HTML5的postMessage来实现,但前提是子页面需要主动向父页面发送信息。下面是子页面部分:
<!DOCTYPE html> 
<head> 
</head> 
<body onload="parent.postMessage(document.body.scrollHeight, 'http://target.domain.com');"> 
<h3>Got post?</h3> 
<p>Lots of stuff here which will be inside the iframe.</p> 
</body> 
</html>

在父页面中获取到子页面传递过来的信息,然后对iframe的高度进行调整。
<script type="text/javascript"> 
function resizeCrossDomainIframe(id, other_domain) { 
var iframe = document.getElementById(id); 
window.addEventListener('message', function(event) { 
if (event.origin !== other_domain) return; // only accept messages from the specified domain 
if (isNaN(event.data)) return; // only accept something which can be parsed as a number 
var height = parseInt(event.data) + 32; // add some extra height to avoid scrollbar 
iframe.height = height + "px"; 
}, false); 
} 
</script> <iframe src='abc.html' id="frm1" onload="resizeCrossDomainIframe('frm1', 'http://example.com');"> 
</iframe>

有关如何使用HTML5的postMessage()方法可以查看这篇文章http://dev.w3.org/html5/postmsg/#web-messaging

但是在大多数情况下,iframe中所引用的子页面除了和父页面不在同一域之外,我们可能根本无法对子页面进行任何操作,或者说子页面根本没有提供Corss-document messaging功能。在这种情况下,通过postMessage()方法也无法获取到子页面的任何信息。由于无法和子页面进行任何交互,也就没有办法得知子页面的document对象,从未无法根据子页面的实际高度来调整父页面iframe的height属性了。

目前没有其它实际有效的方法来处理上面遇到的问题。默认情况下可以给iframe指定一个比较大的高度,这样假设所引用的子页面内容不会超出范围,除了在页面上会留下部分空白区域外,内容显示基本不会有问题。

那是否还存在其它比较有效的解决方法呢?期待!

Javascript 相关文章推荐
jQuery 事件的命名空间简单了解
Nov 22 Javascript
node.js中的fs.renameSync方法使用说明
Dec 16 Javascript
javascript实现手机震动API代码
Aug 05 Javascript
基于jquery实现图片相关操作(重绘、获取尺寸、调整大小、缩放)
Dec 25 Javascript
JavaScript学习笔记整理之引用类型
Jan 22 Javascript
Vue.js第三天学习笔记(计算属性computed)
Dec 01 Javascript
详解angularJs指令的3种绑定策略
Apr 13 Javascript
js断点调试经验分享
Dec 08 Javascript
js中apply()和call()的区别与用法实例分析
Aug 14 Javascript
jQuery事件绑定和解绑、事件冒泡与阻止事件冒泡及弹出应用示例
May 13 jQuery
node.JS二进制操作模块buffer对象使用方法详解
Feb 06 Javascript
vue项目中使用rem,在入口文件添加内容操作
Nov 11 Javascript
JQuery对id中含有特殊字符的转义处理示例
Sep 06 #Javascript
关于jQuery中.attr()和.prop()的问题探讨
Sep 06 #Javascript
正负小数点后两位浮点数实现原理及代码
Sep 06 #Javascript
jQuery实现列表自动循环滚动鼠标悬停时停止滚动
Sep 06 #Javascript
jquery实现metro效果示例代码
Sep 06 #Javascript
JS去除数组重复值的五种不同方法
Sep 06 #Javascript
JavaScript判断密码强度(自写代码)
Sep 06 #Javascript
You might like
用Php实现链结人气统计
2006/10/09 PHP
php ZipArchive压缩函数详解实例
2013/11/06 PHP
wordpress网站转移到本地运行测试的方法
2017/03/15 PHP
PHP写API输出的时用echo的原因详解
2019/04/28 PHP
js使用eval解析json(js中使用json)
2014/01/17 Javascript
javascript里使用php代码实例
2014/12/13 Javascript
原生js实现图片层叠轮播切换效果
2016/02/02 Javascript
jQuery ajax请求返回list数据动态生成input标签,并把list数据赋值到input标签
2016/03/29 Javascript
AngularJS实现ajax请求的方法
2016/11/22 Javascript
jQuery实现给input绑定回车事件的方法
2017/02/09 Javascript
js脚本编写简单刷票投票系统
2017/06/27 Javascript
React组件生命周期详解
2017/07/03 Javascript
Python实现windows下模拟按键和鼠标点击的方法
2015/03/13 Python
Python加密方法小结【md5,base64,sha1】
2017/07/13 Python
pyqt5自定义信号实例解析
2018/01/31 Python
python 图像平移和旋转的实例
2019/01/10 Python
python os模块在系统管理中的应用
2020/06/22 Python
python利用文件时间批量重命名照片和视频
2021/02/09 Python
基于css3仿造window7的开始菜单
2010/06/17 HTML / CSS
倩碧美国官网:Clinique美国
2016/07/20 全球购物
ALDO加拿大官网:加拿大女鞋品牌
2018/12/22 全球购物
PREMIUM-MALL法国:行李、箱包及配件在线
2019/05/30 全球购物
定义一结构体数组表示分数,并求两个分数相加之和
2013/06/11 面试题
建筑个人求职信范文
2014/01/25 职场文书
银行办公室岗位职责
2014/03/10 职场文书
英文自荐信常用句子
2014/03/26 职场文书
社区义诊活动总结
2014/04/30 职场文书
关于环保的标语
2014/06/13 职场文书
党支部反对四风思想汇报
2014/10/10 职场文书
物价局领导班子四风问题整改措施
2014/10/26 职场文书
2015年度护士个人工作总结
2015/04/09 职场文书
帝企鹅日记观后感
2015/06/10 职场文书
使用Redis实现实时排行榜功能
2021/07/02 Redis
Javascript中Microtask和Macrotask鲜为人知的知识点
2022/04/02 Javascript
Java十分钟精通进阶适配器模式
2022/04/06 Java/Android
Windows server 2012 配置Telnet以及用法详解
2022/04/28 Servers