我有一个耗时的循环,用于一个表格,输出大约300个单元格,每个单元格上都有一些自定义计算,加载需要4-5秒,这是有意义的。因此,我想要显示一个加载模式,同时它这样做。然而,只有在昂贵的循环结束后才会显示模式吗?
const [loading, setLoading] = useState<boolean>(false);
useEffect(() => {
if(loading){
console.log(loading, "Loading has started")
}
}, [loading])
return(
<>
<Modal show={loading}>Loading....</Modal>
<a onClick={() => setLoading(true)}>Load more</a>
// Expensive loop
array.map(() => {
// HMTL
<div>
----
</div>
})
</>
)
我可以从控制台日志中看到“加载”的状态已经更新,但是模式还没有显示,所以我假设它在等待循环结束(我不想要的)。有没有办法让它先输出模式的html,或者我是否遗漏了React的一个基本原理?
发布于 2021-02-26 20:07:03
如果这是一个很慢的计算,你可能不想在每次渲染时都这样做,因为组件可以渲染相当多次。理想情况下,您只希望在输入数据发生变化时渲染这些昂贵的计算,这可以通过分离处理和渲染来实现。
我不确定我完全理解这个加载部分是如何工作的,但是像下面这样的例子应该会有所帮助:
const [loading, setLoading] = useState<boolean>(false);
const [computedArray, setComputedArray] = useState([]);
useEffect(() => {
setComputedArray(array.map(//expensive loop here))
setLoading(false)
}, [array])
useEffect(() => {
if(loading){
console.log(loading, "Loading has started")
}
}, [loading])
return(
<>
<Modal show={loading}>Loading....</Modal>
<a onClick={() => setLoading(true)}>Load more</a>
// Cheap loop, turn data into markup
computedArray.map(() => {
// HTML
<div>
----
</div>
})
</>
)
发布于 2021-02-26 20:42:20
我不知道Modal是从什么来的,所以从一般的角度来回答:
就我个人而言,我会保持数组的状态,并在一个单独的函数中更新它,并使用&&符号来显示加载元素。这样,您就可以将所有关于昂贵的计算和加载/卸载的逻辑放在一个地方。
export default function App() {
const [loading, setLoading] = useState(false);
const [array, setArray] = useState([]);
const getExpensiveCalculation = async () => {
setLoading(true);
const resultOfExpensiveCalculation = await ... // something here
// assuming result is a spreadable array too
setArray([...array, ...resultOfExpensiveCalculation]);
setLoading(false);
};
return (
<>
{loading && <Modal>Loading....</Modal>}
<a onClick={getExpensiveCalculation}>Load more</a>
{array.map(element => (
<div>
---
</div>
))}
</>
);
}https://stackoverflow.com/questions/66385208
复制相似问题