useState在next.js中没有正确更新我的setState。

huangapple go评论71阅读模式
英文:

useState doesn't update my setState correctly in next.js

问题

我在英雄部分有一些使用 framer.motion 的动画我只想在第一次加载时播放

我想在本地存储中存储一些内容以跟踪是否显示动画使用 useState  useEffect 进行工作

useEffect 会像预期的那样影响本地存储但我不确定为什么我的英雄部分仍然显示相同的内容就好像 useState 没有改变

        async function Hero() {
    
        const [animate, setAnimate] = useState(true);
    
        useEffect(() => {
            if(localStorage.getItem('animate') != null){
                 localStorage.setItem('animate', 'false')
                 setAnimate(false)
              }else{
                 localStorage.setItem('animate', 'true')
              }
            }
        }, []);
    
      return (
         <div>
         <motion.h1 animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}}>Some text</motion.h1>
         </div>
        )
    }
    
    export default Hero

在第一次加载时本地存储中的 'animate'  true然后切换为 false但它不会影响动画

我使用了一小段简单的代码来确保它不是来自我的 framer 代码但结果是一样的

    {animate == true?<h1>True</h1>:<h1>False</h1>}

我尝试改变了依赖项数组但仍然不起作用

使用以下代码

    async function Hero() {

    const [animate, setAnimate] = useState(true);
    console.log(animate)

    useEffect(() =&gt; {
            if(localStorage.getItem('animate') != null){
                localStorage.setItem('animate', 'false')
                setAnimate(false)
            }else{
                localStorage.setItem('animate', 'true')
            }
    }, []);


它首先记录 true然后当我导航到其他地方并返回时它记录 true然后无限记录 false每秒约 1000 )。

有任何想法吗
英文:

I have a few animations on my hero section with framer.motion that I want only on the first load.

I wanted to store someting in the local storage to track if yes or not I display the animations, working with a useState and useEffect.

The useEffect does affect the local storage as expected but then I'm not sure why my hero section still display the same thing as if useState didn't change.

    async function Hero() {
const [animate, setAnimate] = useState(true);
useEffect(() =&gt; {
if(localStorage.getItem(&#39;animate&#39;) != null){
localStorage.setItem(&#39;animate&#39;, &#39;false&#39;)
setAnimate(false)
}else{
localStorage.setItem(&#39;animate&#39;, &#39;true&#39;)
}
}
}, []);
return (
&lt;div&gt;
&lt;motion.h1 animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}}&gt;Some text&lt;/motion.h1&gt;
&lt;/div&gt;
)
}
export default Hero

On the first load 'animate' in the localStorage is true and then switch on false, but it doesn't affect the animation.

I checked with a simple piece of code to be sure it doesn't come from my framer code but it's the same

{animate == true?&lt;h1&gt;True&lt;/h1&gt;:&lt;h1&gt;False&lt;/h1&gt;}

I tried to change the dependancies array but still doesn't work.

with this code :

async function Hero() {
const [animate, setAnimate] = useState(true);
console.log(animate)
useEffect(() =&gt; {
if(localStorage.getItem(&#39;animate&#39;) != null){
localStorage.setItem(&#39;animate&#39;, &#39;false&#39;)
setAnimate(false)
}else{
localStorage.setItem(&#39;animate&#39;, &#39;true&#39;)
}
}, []);

It first logs true than when I navigate elsewhere and come back it logs true then infinite false (like 1000 times a second)

Any idea?

Edit

Here is the full code.
This component is insdide a components direcotry itself inside the app directory.
I don't know why but when I had a useEffect to the component it makes the whole page slow and even crash the window.

 &#39;use client&#39;
import {React, useState, useEffect} from &#39;react&#39;
import Link from &#39;next/link&#39;
import { IoIosPin } from &quot;react-icons/io&quot;;
import { IoMdBus } from &quot;react-icons/io&quot;;
import { motion } from &quot;framer-motion&quot;
export default async function Hero() {
const [animate, setAnimate] = useState(true);
useEffect(() =&gt; {
if(localStorage.getItem(&#39;animate&#39;) != null){
localStorage.setItem(&#39;animate&#39;, &#39;false&#39;)
setAnimate(false)
}else{
localStorage.setItem(&#39;animate&#39;, &#39;true&#39;)
}
},[])
return (
&lt;div className=&#39;px-2 pt-3 mdl:px-8 lgl:px-12 xl:px-16&#39;&gt;
&lt;div className=&#39;relative w-full bg-[url(&quot;/hero/cabinet-paysage.jpg&quot;)] bg-cover bg-center bg-no-repeat sml:min-h-[300px] mdl:min-h-[400px] lg:min-h-[450px] lgl:min-h-[500px]&#39;&gt;
&lt;motion.div className=&quot;w-full h-full bg-bgwhite sml:min-h-[300px] mdl:min-h-[400px] lg:min-h-[450px] lgl:min-h-[500px]&quot; animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{ease: &quot;linear&quot;, duration:0.5}}&gt;
&lt;div className=&#39; w-full h-full max-w-[1000px] sml:min-h-[300px] mdl:min-h-[400px] p-5 mx-auto grid grid-cols-1 grid-rows-8 auto-rows-fr auto-cols-fr sml:grid-cols-3 sml:grid-rows-2&#39;&gt;
&lt;div className=&#39;row-span-4 flex flex-col justify-center gap-3 mdl:gap-4 lg:gap-5 xl:gap-6 sml:col-start-1 sml:col-end-3 sml:row-span-2 &#39;&gt;
&lt;motion.h1 animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{delay:0.2, ease: &quot;linear&quot;, duration:0.3}}&gt;Some text&lt;/motion.h1&gt;
&lt;motion.h2 animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{delay:0.4, ease: &quot;linear&quot;, duration:0.3}}&gt;Some text&lt;/motion.h2&gt;
&lt;motion.p className=&#39;sml:max-w-[450px] headertext&#39; animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{delay:0.6, ease: &quot;linear&quot;, duration:0.3}}&gt;Le Lorem Ipsum est simplement du faux texte employ&#233; dans la composition et la mise en page avant impression. Le Lorem Ipsum est le faux texte et&lt;/motion.p&gt;
&lt;/div&gt;
&lt;div className=&#39;row-span-3 flex flex-col justify-center items-center gap-2 sml:col-start-3 sml:row-span-2&#39;&gt;
&lt;div className=&#39;flex justify-center gap-4&#39;&gt;
&lt;motion.div className=&#39;flex flex-col items-center w-24 text-center&#39; animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{delay:0.2, ease: &quot;linear&quot;, duration:0.3}}&gt;
&lt;IoIosPin className=&#39;reacticons&#39;/&gt;
&lt;p className=&#39;headertext&#39;&gt;Some text&lt;/p&gt;
&lt;/motion.div&gt;
&lt;motion.div className=&#39;flex flex-col items-center w-24 text-center&#39; animate={{opacity:1}} initial={animate == true ? {opacity:0} : {opacity:1}} transition={{delay:0.4, ease: &quot;linear&quot;, duration:0.3}}&gt;
&lt;IoMdBus className=&#39;reacticons&#39;/&gt;
&lt;p className=&#39;headertext&#39;&gt;Some text&lt;/p&gt;
&lt;/motion.div&gt;
&lt;/div&gt;
&lt;Link href=&quot;/#contact&quot; className=&#39;buttonheader inline-block text-center self-center&#39;&gt;
Prendre Rendez-Vous
&lt;/Link&gt;
&lt;/div&gt;
&lt;/div&gt;
&lt;/motion.div&gt;
&lt;/div&gt;
&lt;/div&gt;
)
}

答案1

得分: 1

尝试从函数中移除异步关键字,因为它不会起作用。

英文:

try removing async from the function, because it won't work

function Hero() {
const [animate, setAnimate] = useState(true);
useEffect(() =&gt; {
if(localStorage.getItem(&#39;animate&#39;) != null){
localStorage.setItem(&#39;animate&#39;, &#39;false&#39;)
setAnimate(false)
}else{
localStorage.setItem(&#39;animate&#39;, &#39;true&#39;)
}
}
}, []);
return (
&lt;div&gt;
&lt;motion.h1 animate={{opacity:1}} initial={{opacity:animate?0:1}}&gt;Some text&lt;/motion.h1&gt;
&lt;/div&gt;
)
}
export default Hero```
</details>

huangapple
  • 本文由 发表于 2023年6月22日 20:13:00
  • 转载请务必保留本文链接:https://go.coder-hub.com/76531771.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定