根据里面的内容制作iframe高度动态 - JQUERY/Javascript

kar*_*rry 193 javascript asp.net iframe jquery

我在iframe中加载一个aspx网页.Iframe中的内容可以比iframe的高度更高.iframe不应该有滚动条.

div在iframe中有一个包装器标签,基本上就是所有的内容.我写了一些jQuery来调整大小:

$("#TB_window", window.parent.document).height($("body").height() + 50);
Run Code Online (Sandbox Code Playgroud)

包含TB_window它的div在哪里 Iframe.

body - iframe中aspx的body标签.

此脚本附加到iframe内容.我TB_window从父页面获取元素.虽然这在Chrome上运行良好,但TB_window在Firefox中崩溃.我真的很困惑/失去了为什么会发生这种情况.

Ari*_*tos 199

您可以使用以下方法检索内容的高度IFRAME: contentWindow.document.body.scrollHeight

在之后IFRAME被加载,然后你可以通过以下步骤改变高度:

<script type="text/javascript">
  function iframeLoaded() {
      var iFrameID = document.getElementById('idIframe');
      if(iFrameID) {
            // here you can make the height, I delete it first, then I make it again
            iFrameID.height = "";
            iFrameID.height = iFrameID.contentWindow.document.body.scrollHeight + "px";
      }   
  }
</script>   
Run Code Online (Sandbox Code Playgroud)

然后,在IFRAME标记上,你像这样挂钩处理程序:

<iframe id="idIframe" onload="iframeLoaded()" ...
Run Code Online (Sandbox Code Playgroud)

我有一个情况在不久前,我还需要调用iframeLoadedIFRAME后内发生的形式提交自己.您可以通过在IFRAME内容脚本中执行以下操作来实现此目的:

parent.iframeLoaded();
Run Code Online (Sandbox Code Playgroud)

  • 它不支持跨域. (143认同)
  • 这解决了跨域iframe大小调整问题https://github.com/davidjbradshaw/iframe-resizer (15认同)
  • @Soumya寻找`X-FRAME-OPTIONS`添加一行:`Response.AddHeader("X-FRAME-OPTIONS","SAMEORIGIN");`或`response.addHeader("X-FRAME-OPTIONS") ,"允许来自https://some.othersite.com");` (8认同)
  • @Soumya跨域与此代码无关.您可以通过命令绕过安全问题. (3认同)
  • @DavidBradshaw - 你那里有很好的脚本,它甚至可以跨域工作,但 CORS 的最使用场景是当你无权访问远程加载的页面时。我正在尝试使用您的脚本将谷歌文档表单加载到网站(嵌入)中,但这不起作用;( (2认同)
  • @deebs您也可以尝试将`iFrameID.height ="";`更改为`iFrameID.height ="20px";`.默认的浏览器iframe高度为150px,这就是````将其重置为. (2认同)

Blu*_*ish 100

对Aristos的回答略有改善......

<script type="text/javascript">
  function resizeIframe(iframe) {
    iframe.height = iframe.contentWindow.document.body.scrollHeight + "px";
  }
</script>  
Run Code Online (Sandbox Code Playgroud)

然后在iframe中声明如下:

<iframe onload="resizeIframe(this)" ...
Run Code Online (Sandbox Code Playgroud)

有两个小的改进:

  1. 您不需要通过document.getElementById获取元素 - 因为您已经在onload回调中使用了它.
  2. iframe.height = ""如果您要在下一个声明中重新分配它,则无需设置.在处理DOM元素时,这样做实际上会产生开销.

  • 如果框架中的内容总是在变化,你会怎么做? (6认同)
  • 为此......解决方案是使用postMessage和receiveMessage.我用https://github.com/jeffomatic/nojquery-postmessage解决了这个问题 (4认同)

小智 53

我发现接受的答案是不够的,因为在safari或chrome中不支持 X-FRAME-OPTIONS:Allow-From .取而代之的是一种不同的方法,发现于来自Disqus的Ben Vinegar 的演示文稿中.想法是向父窗口添加一个事件监听器,然后在iframe内部,使用window.postMessage向父级发送一个事件,告诉它做某事(调整iframe的大小).

所以在父文档中,添加一个事件监听器:

window.addEventListener('message', function(e) {
  var $iframe = jQuery("#myIframe");
  var eventName = e.data[0];
  var data = e.data[1];
  switch(eventName) {
    case 'setHeight':
      $iframe.height(data);
      break;
  }
}, false);
Run Code Online (Sandbox Code Playgroud)

在iframe中,编写一个函数来发布消息:

function resize() {
  var height = document.getElementsByTagName("html")[0].scrollHeight;
  window.parent.postMessage(["setHeight", height], "*"); 
}
Run Code Online (Sandbox Code Playgroud)

最后,在iframe内部,向body标签添加onLoad以触发resize函数:

<body onLoad="resize();">
Run Code Online (Sandbox Code Playgroud)

  • 很好的解决方案,没有跨站点脚本错误。 (3认同)
  • 伟大的!但它只加载一次高度。如果你想让 iframe 真正响应,我更喜欢每秒调用 resize 方法,如下所示:`setInterval(resize, 1000);` (2认同)

Moh*_*eja 12

将此添加到iframe,这对我有用:

onload="this.height=this.contentWindow.document.body.scrollHeight;"
Run Code Online (Sandbox Code Playgroud)

如果您使用jQuery尝试此代码:

onload="$(this).height($(this.contentWindow.document.body).find(\'div\').first().height());"
Run Code Online (Sandbox Code Playgroud)

  • 在我们的时代不再有效。 (2认同)

use*_*818 8

您还可以将重复的 requestAnimationFrame 添加到您的 resizeIframe (例如来自 @BlueFish 的答案),它总是在浏览器绘制布局之前被调用,并且您可以在 iframe 的内容更改其高度时更新 iframe 的高度。例如输入表单、延迟加载内容等。

<script type="text/javascript">
  function resizeIframe(iframe) {
    iframe.height = iframe.contentWindow.document.body.scrollHeight + "px";
    window.requestAnimationFrame(() => resizeIframe(iframe));
  }
</script>  

<iframe onload="resizeIframe(this)" ...
Run Code Online (Sandbox Code Playgroud)

您的回调应该足够快,不会对您的整体性能产生太大影响


Dav*_*haw 6

您可以通过四种不同的属性来获取iFrame中内容的高度.

document.documentElement.scrollHeight
document.documentElement.offsetHeight
document.body.scrollHeight
document.body.offsetHeight
Run Code Online (Sandbox Code Playgroud)

可悲的是,他们都可以给出不同的答案,这些在浏览器之间是不一致的.如果将体边距设置为0,则document.body.offsetHeight给出最佳答案.要获得正确的值,请尝试此功能; 这是从iframe-resizer库中获取的,该库也会在内容更改或调整浏览器大小时保持iFrame的正确大小.

function getIFrameHeight(){
    function getComputedBodyStyle(prop) {
        function getPixelValue(value) {
            var PIXEL = /^\d+(px)?$/i;

            if (PIXEL.test(value)) {
                return parseInt(value,base);
            }

            var 
                style = el.style.left,
                runtimeStyle = el.runtimeStyle.left;

            el.runtimeStyle.left = el.currentStyle.left;
            el.style.left = value || 0;
            value = el.style.pixelLeft;
            el.style.left = style;
            el.runtimeStyle.left = runtimeStyle;

            return value;
        }

        var 
            el = document.body,
            retVal = 0;

        if (document.defaultView && document.defaultView.getComputedStyle) {
            retVal =  document.defaultView.getComputedStyle(el, null)[prop];
        } else {//IE8 & below
            retVal =  getPixelValue(el.currentStyle[prop]);
        } 

        return parseInt(retVal,10);
    }

    return document.body.offsetHeight +
        getComputedBodyStyle('marginTop') +
        getComputedBodyStyle('marginBottom');
}
Run Code Online (Sandbox Code Playgroud)