useState 钩子的行为与预期不同
我的 React 应用程序中使用 i18next 有一个简单的语言选择器(en、cs)。语言的更改(应用所有翻译并重新渲染应用程序)大约需要 2 秒。
与此同时,我想显示一个加载程序,但这似乎没有按预期工作。
我有两种情况。第一个不显示 Loader
:
const [isLoading, setIsLoading] = useState(false)
const [language, setLanguage] = useState(userPreferences.lang);
const handleChangeLanguage = (lang) => {
setIsLoading(true);
setLanguage(lang);
}
useEffect(() => {
i18n.changeLanguage(language).then(() => setIsLoading(false) );
},[language])
return (
<>
{isLoading ? <Loader /> : <div>lang selector here</div> }
</>
)
但是当我在 setLanguage
上使用 setTimeout(即使时间为零)时,会显示加载程序,直到语言发生变化:
const [isLoading, setIsLoading] = useState(false)
const [language, setLanguage] = useState(userPreferences.lang);
const handleChangeLanguage = (lang) => {
setIsLoading(true);
setTimeout(() => setLanguage(lang), 0); // <= change here
}
useEffect(() => {
i18n.changeLanguage(language).then(() => setIsLoading(false) );
},[language])
return (
<>
{isLoading ? <Loader /> : <div>lang selector here</div> }
</>
)
为什么它的行为是这样的,我可以以某种方式设置它以避免 setTimeout
吗?
谢谢。
I have a simple language selector (en, cs) in my React app using i18next. The change of the language (applying all the translations and re-rendering the app) takes around 2 seconds.
In the meantime, I want to display a loader, but that doesn't seem to work as expected.
I have two scenarios. The first one does not display Loader
:
const [isLoading, setIsLoading] = useState(false)
const [language, setLanguage] = useState(userPreferences.lang);
const handleChangeLanguage = (lang) => {
setIsLoading(true);
setLanguage(lang);
}
useEffect(() => {
i18n.changeLanguage(language).then(() => setIsLoading(false) );
},[language])
return (
<>
{isLoading ? <Loader /> : <div>lang selector here</div> }
</>
)
But when I use setTimeout (even with zero time) on setLanguage
the loader is displayed until the lang changes:
const [isLoading, setIsLoading] = useState(false)
const [language, setLanguage] = useState(userPreferences.lang);
const handleChangeLanguage = (lang) => {
setIsLoading(true);
setTimeout(() => setLanguage(lang), 0); // <= change here
}
useEffect(() => {
i18n.changeLanguage(language).then(() => setIsLoading(false) );
},[language])
return (
<>
{isLoading ? <Loader /> : <div>lang selector here</div> }
</>
)
Why does it behave like that, and can I set it somehow to avoid setTimeout
?
Thanks.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
尝试此代码而不是您的函数并删除 useEffect
try this code instead of your function and remove useEffect
尝试使用
setImmediate()
而不是setTimeout()
Try using
setImmediate()
instead ofsetTimeout()