React App - Performace
起因
最近突然发现在大文件渲染预览的时候, 会卡顿很久, 连loading
都无法显示, 用浏览器的performance
查看, 发现是因为设置了loading
之后, 会再次重排(reflow
)一遍所有的子节点, 导致页面卡顿, 表现在performace
记录上是会出现很长的一条Layout Shift
记录
问题排查
仔细研究后发现这个问题触发的具体流程是:
- 打开一个比较大的页面
- 点击事件刷新页面数据
- 刷新时候触发
loading
动画 - 由于我们的
loading
动画在大页面的最外层, 会触发所有子节点reflow
, 导致Layout Shift
- 子节点
reflow
完成后, 数据加载回来, 取消loading
动画, 刷新数据 - 新数据再次触发
reflow
, 两次连续的Layout Shift
导致用户感觉卡顿
解决办法
项目中的loading
组件是直接使用的antd
的Spin
组件, 而包裹页面的用法一般如下, 而且为了支持自动适配大小, 有时会设置flex
相关的class
, 支持内层容器自动适配外层容器大小
1 | <Spin tip='Loading...'> |
而解决重绘reflow
的方法也很简单, 就是各处都讲过的: 绝对定位元素不会引起reflow
, 开发一套适配spin
的绝对定位的class
就可以了, 将真实的子元素放在Spin
外层, 就不会引起reflow
了
1 | .ant-spin-relative { |
1 | <div className='ant-spin-relative'> |
小结
虽然最终的解决办法很简单, 但是一路排查下来过程却挺麻烦, 特别是chrome
开了performance
后渲染性能感觉直接减少了两倍, 十分影响效率
React App - Performace
https://mosby-zhou.github.io/2020/12-10-react-app-performace-flex/