offsetHeight 和 clientHeight 的区别

IT技术 javascript
2021-02-27 03:53:35

在 javascript dom 中 - 元素的 offsetHeight 和 clientHeight 有什么区别?

4个回答

客户高度

返回对象可见区域的高度(以像素为单位)。该值包含带内边距的高度,但不包含滚动条、边框和边距。

偏移高度

返回对象可见区域的高度(以像素为单位)。该值包含带有内边距、滚动条和边框的高度,但不包含边距。

所以,offsetHeight包括滚动条和边框,clientHeight没有。

@disc0dancer - 我的猜测就这么多。但这是一个实现 - 不确定所有浏览器都是这样。
2021-04-22 03:53:35
@disc0dancer - 可能是因为浏览器已经有了clientSize现成的(毕竟,它是视口),但需要offsetHeight在重排整个文档后进行计算
2021-04-27 03:53:35
我注意到的另一件事是 clientHeight 比 offsetHeight 快得多。你知道为什么吗?
2021-05-03 03:53:35
好吧,webkit 检查员说回流也在整个文档中,即使在要求 clientHeigh 时也是如此。
2021-05-08 03:53:35

Oded 的答案是理论。但是理论和现实并不总是相同的,至少对于 <BODY> 或 <HTML> 元素而言,这可能对 javascript 中的滚动操作很重要。

微软在MSDN 中有一个很好的图片

客户端高度、偏移高度、滚动高度

如果您有一个显示垂直滚动条的 HTML 页面,那么您会期望 <BODY> 或 <HTML> 元素的 ScrollHeight 比 OffsetHeight 高,如图所示。这适用于所有旧版本的 Internet Explorer。

但它不适用于 Internet Explorer 11 和 Firefox 36。至少在这些浏览器中,OffsetHeight 与 ScrollHeight 几乎相同,这是错误的。

虽然 OffsetHeight 可能是错误的,但 ClientHeight 总是正确的。

在不同的浏览器上试试下面的代码,你会看到:

<!DOCTYPE html>
<html>
<body>
<br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br>
<br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br>
<br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br><br>
<script>
    document.write("Body off: " + document.body.offsetHeight 
             + "<br>Body cli: " + document.body.clientHeight
             + "<br>Html off: " + document.body.parentElement.offsetHeight               
             + "<br>Html cli: " + document.body.parentElement.clientHeight);
</script>
</body>
</html>

虽然较旧的 Internet Explorer 显示正确:

Body off: 1197
Body cli: 1197
Html off: 878
Html cli: 874  

Firefox 和 Internet Explorer 11 的输出是:

Body off: 1260
Body cli: 1260
Html off: 1276   // this is completely wrong
Html cli: 889

这清楚地表明 offsetHeight 在这里是错误的。OffsetHeight 和 ClientHeight 应该仅相差几个像素或相同。


请注意,对于不可见的元素,ClientHeight 和 OffsetHeight 也可能有很大不同,例如 <FORM>,其中 OffsetHeight 可能是 FORM 的实际大小,而 ClientHeight 可能为零。

在此处输入图片说明

代码笔

从内到外,一个元素布局的顺序是:[(内容→内边距)→滚动条→边框]→外边距。

(..) area 指的是被称为 的区域client,而 [..] area 指的是offset.

Margin 被认为是元素之外的,永远不会参与任何 JS 布局 API。


获取元素布局的 JS API 的详尽列表是:

  • 对于Element类(包括 HTML 元素和 svg 元素):

    • getClientRects()

    • getBoundingClientRect().{left,top,right,bottom,x,y,width,height}

    • client{Height,Width,Left,Top}

    • scroll{Height,Width,Left,Top,LeftMax,TopMax}

  • 对于HTMLElement类(不包括SVG元素): offset{Height,Width,Left,Top}

  • 针对window对象:scroll{X,Y}page{X,Y}Offsetinner{Height,Width}outer{Height,Width}screen{Left,X,Top,Y}

  • 针对screen对象:avail{Top,Left,Height,Width}heightwidthlefttop


因为根元素无法获得滚动条(浏览器滚动条停留在根元素的边框之外)。代码笔

根据规范,对于元素是根元素client{Height,Width}以及scroll{Left,Top}何时有特殊定义


client*等忽略变换并将值舍入为整数,而getClientRects()/getClientBoundingRect()涉及变换并返回浮点值。

这个答案还有很多方面不适合,所以我在这里总结并发了一篇博文

clientHeight = 元素的高度 + 垂直填充。

offsetHeight = 元素的高度 + 垂直填充 + 顶部和底部边框 + 水平滚动条(如果可用)。

加上另一个:

scrollHeight = 元素内容的高度(包括屏幕上不可见的内容)+垂直填充。