IT博客汇
  • 首页
  • 精华
  • 技术
  • 设计
  • 资讯
  • 扯淡
  • 权利声明
  • 登录 注册

    getBoundingClientRect与transform的兼容

    王叨叨发表于 2023-05-15 15:38:44
    love 0

    先说结论

    getBoundingClientRect 会受到 transform 的影响,比如你的元素设置了 transform:scale(2),那么 getBoundingClientRect 返回的 width 会是元素实际宽度的2倍,top 等位置信息也会因为元素尺寸变化而发生变化。

    起因

    产品中有一个需求,要实现页面的缩放功能,考虑到兼容性就没有使用 zoom(火狐不支持),而是使用了 transfrom 的 scale。

    2023-05-15T07:12:21.png

    在页面缩放的时候,组件在计算截断宽度的时候出现了问题,导致如图:

    2023-05-15T07:14:07.png

    根据代码排查,组件在计算宽度的时候,使用 getBoundingClientRect:

    2023-05-15T07:17:20.png

    这里就不对 getBoundingClientRect 做过多的描述了,通过下图能看到一些注意事项:

    2023-05-15T07:21:38.png

    至于组件之前为啥用 getBoundingClientRect 就不得而知了。

    在修改之前也对比了这两种计算方式得出的宽高:

    • getBoundingClientRect:该方法返回的 DOMRect 对象中的 width 和 height 属性是包含了 padding 和 border-width 的,而不仅仅是内容部分的宽度和高度。在标准盒子模型中,这两个属性值分别与元素的 width/height + padding + border-width 相等。而如果是 box-sizing: border-box,两个属性则直接与元素的 width 或 height 相等。
    • offsetWidth:offsetWidth 是测量包含元素的边框 (border)、水平线上的内边距 (padding)、竖直方向滚动条 (scrollbar)(如果存在的话)、以及 CSS 设置的宽度 (width) 的值。

    然后查了下性能相关,貌似问题也不大:

    2023-05-15T07:34:36.png

    《What forces layout / reflow》:https://gist.github.com/paulirish/5d52fb081b3570c81e3a

    结尾

    文章到这里,差不多就没啥好说的了,考虑到组件的通用性,在使用 getBoundingClientRect 前确保有没有缩放的需求,如果有缩放需求,那就尽量避免吧……



沪ICP备19023445号-2号
友情链接