JS 中 offsetHeight/scrollHeight/clientHeight 的区别

简介: client* clientWidth/clientHeight 返回的是元素的内部宽度,它的值只包含 content + padding,如果有滚动条,不包含滚动条 clientTop 返回的是上边

JS 基于 DOM 对象可以拿到元素的宽高的属性有 offset 系、scroll 系、client 系(以其名称作为前缀得名),IDE 提示如下(以 VS Code 为准)

接下来就以如下顺序介绍一下这三种获取宽高的方法,以及它们的不同

  1. client*
  2. offset*
  3. scroll*

client

  1. client*

    1. clientWidth/clientHeight 返回的是元素的内部宽度,它的值只包含 content + padding,如果有滚动条,不包含滚动条
    2. clientTop 返回的是上边框的宽度
    3. clientLeft 返回的左边框的宽度
<body>
  <div class="demo" style="height: 100px; width: 100px; padding: 10px;"></div>
</body>
<script>
  const div = document.querySelector(".demo");
  console.log(div.clientWidth, div.clientHeight, div.clientTop, div.clientLeft);
  // 120 120 10 10
</script>

可能有人想问了,clientBottom 是不是就是 border 底部的值呢?实际上结果是 undefiend 因为并没有这个值,clientRight 同理

注意一个小细节

clientHeightclientWidth 不包括滚动条,如果有滚动条,那么 clientHeight = content + padding - scroll (元素内容本身的高度加上内边距再减去水平滚动条的高度)

<body>
  <div
    class="demo"
    style="
      height: 100px;
      width: 100px;
      padding: 10px;
      border: 10px solid black;
      overflow: auto;
    "
  >
    <div style="height: 200px"></div>
  </div>
</body>
<script>
  const div = document.querySelector(".demo");
  console.log(div.clientWidth, div.clientHeight); // 103 120
  // 此时滚动条宽度为 17px
</script>

offset

  1. offset*

    1. offsetWidth/offsetHeight 返回的是元素的布局宽度,它的值包含 content + padding + border 包含了滚动条
    2. offsetTop 返回的是当前元素相对于其 offsetParent 元素的顶部的距离
    3. offsetLeft 返回的是当前元素相对于其 offsetParent 元素的左部的距离

不过有点奇怪的是,VS CodeWebStorm 都没有对 offset* 做任何提示(希望评论区能够给出答案)

依旧是上面的例子

<body>
  <div style="height: 100px"></div>
  <div
    class="demo"
    style="
      height: 100px;
      width: 100px;
      padding: 10px;
      border: 10px solid black;
      overflow: auto;
    "
  >
    <div style="height: 200px"></div>
  </div>
</body>
<script>
  const div = document.querySelector(".demo");
  console.log(div.offsetHeight, div.offsetWidth, div.offsetTop, div.offsetLeft);
  // 140 140 108 8
</script>

此时 divoffsetParent 就是 body

scroll

  1. scroll*

    1. scrollWidth/scrollHeight 返回值包含 content + padding + 溢出内容的尺寸
    2. scrollTop 属性返回的是一个元素的内容垂直滚动的像素数
    3. scrollLeft 读写元素左侧已滚动的距离,即位于元素左边界与元素中当前可见内容的最左端之间的距离。

scrollWidth/Height 不多讲了,和 offset 差不多以及 client 系差不多,接下来用两个动图介绍一下 scrollTopscrollLeft

scrollLeft 的数值就是已经滑动、消失的部分和当前可见区域最左边的距离

代码如下

<body>
  <div
    class="demo"
    style="
      transform: translate(0, 0);
      height: 200px;
      width: 200px;
      padding: 10px;
      border: 10px solid black;
      overflow: auto;
    "
  >
    <div style="height: 50px; width: 800px; background: black"></div>
    <div class="count" style="position: sticky; left: 0">scrollLeft: 0</div>
  </div>
</body>
<script>
  const div = document.querySelector(".demo");
  const count = document.querySelector(".count");
  div.addEventListener("scroll", () => {
    count.innerHTML = "scrollLeft: " + parseInt(div.scrollLeft);
  });
</script>

参考资料

  1. JS scrollLeft和scrollTop属性:读写元素左侧和顶部已滚动的距离
  2. 浅谈JS各种宽高(clientHeight、scrollHeight、offsetHeight等)- CSDN - 骆小胖
相关文章
|
3月前
|
JavaScript 前端开发 索引
js遍历的方法与区别
js遍历的方法与区别
58 3
|
3月前
|
JavaScript 前端开发 索引
js的循环中foreach、for in和for of的区别
js的循环中foreach、for in和for of的区别
144 0
|
12天前
|
设计模式 JavaScript 前端开发
js中new和object.creat区别
【10月更文挑战第29天】`new` 关键字和 `Object.create()` 方法在创建对象的方式、原型链继承、属性初始化以及适用场景等方面都存在差异。在实际开发中,需要根据具体的需求和设计模式来选择合适的方法来创建对象。
|
2月前
|
前端开发 JavaScript UED
JavaScript防抖和节流的使用及区别
JavaScript防抖和节流的使用及区别
105 57
|
29天前
|
存储 JavaScript 前端开发
JavaScript 数据类型详解:基本类型与引用类型的区别及其检测方法
JavaScript 数据类型分为基本数据类型和引用数据类型。基本数据类型(如 string、number 等)具有不可变性,按值访问,存储在栈内存中。引用数据类型(如 Object、Array 等)存储在堆内存中,按引用访问,值是可变的。本文深入探讨了这两种数据类型的特性、存储方式、以及检测数据类型的两种常用方法——typeof 和 instanceof,帮助开发者更好地理解 JavaScript 内存模型和类型检测机制。
67 0
JavaScript 数据类型详解:基本类型与引用类型的区别及其检测方法
|
1月前
|
存储 JavaScript 前端开发
js中函数、方法、对象的区别
js中函数、方法、对象的区别
16 2
|
1月前
|
JavaScript 前端开发
【JavaScript】let,const和var的区别
总的来说,随着ECMAScript 6(ES6)及后续版本的推广,`let`和 `const`因其增强的块级作用域和对变量行为的更严格控制,逐渐成为现代JavaScript编码实践中推荐使用的变量声明方式。而 `var`由于其历史遗留的局限性,正逐渐被边缘化,但在维护老代码或处理特定兼容性需求时仍需了解。
32 3
|
2月前
|
前端开发 JavaScript 开发者
React 和 Vue.js 框架的区别是什么?
React 和 Vue.js 框架的区别是什么?
|
2月前
|
JavaScript 前端开发
JavaScript中单引号和双引号的效果的一点区别
JavaScript中单引号和双引号的效果的一点区别
|
2月前
|
前端开发 JavaScript API
JavaScript 的宏任务和微任务有什么区别
【9月更文挑战第6天】JavaScript 的宏任务和微任务有什么区别
58 4