useEffect
回调在react渲染组件之后执行,并且确保回调不会阻止浏览器绘制(异步的)
执行过程是这样的:
- 触发了一个导致重新渲染的操作(改变state、props改变)
- react重新渲染组件(调用)
- 屏幕可以看到更新
- useEffect的回调执行
useLayoutEffect
在react渲染组件之后同步执行
执行过程是这样的:
- 触发了一个导致重新渲染的操作(改变state、props改变)
- react重新渲染组件(调用)
- useLayoutEffect回调函数执行
- 屏幕看到更新
代码示例
import React, { useState, useEffect } from "react";
import ReactDOM from "react-dom";
import "./styles.css";
const BlinkyRender = () => {
const [value, setValue] = useState(0);
useEffect(() => {
if (value === 0) {
setValue(10 + Math.random() * 200);
}
}, [value]);
console.log("render", value);
return (
<div onClick={() => setValue(0)}>value: {value}</div>
);
};
ReactDOM.render(
<BlinkyRender />,
document.querySelector("#root")
);
复制代码
上面这样的代码,点击div,有可能导致页面更新两次(闪烁),使用useLayoutEffect就不会了
useEffect执行过程:
- 点击div
- state改变,导致react组件重新执行
- 屏幕更新
- useEffect执行,state再次改变
- react组件重新执行,屏幕更新
useLayoutEffect执行过程:
- 点击div
- state改变,react组件重新执行
- useLayoutEffect,state改变
- react组件再次执行更新
- 屏幕更新
总结
- useLayoutEffect是同步的,在回调执行后才会浏览器才会更新,如果回调执行时间过长,就会导致画面迟迟不能更新,大部分情况使用useEffect
- 如果发现了屏幕闪烁的问题,请尝试下useLayoutEffect
© 版权声明
文章版权归作者所有,未经允许请勿转载。
THE END