【问题标题】:set time dynamic time for set interval in react为反应中的设置间隔设置时间动态时间
【发布时间】:2023-01-12 22:46:32
【问题描述】:

您好,我正在努力为 React js 中的 settimeout 函数设置动态时间。 我有一长串时间和消息的键值oair。我想在特定时间显示每条消息并循环遍历整个列表。 这是我正在尝试的,但没有工作。

'''

const [timer, setTimer] = useState(0)
   const [time, setTime] = useState(5000)// this is default value to start which need to update  with str time value

const str=[{name:"rammy", time:1000},
             {name:"james", time:4000},
             {name:"crown", time:2000}]
            useEffect(()=>{
            const getTime= str[timer].time
            setTime(getTime)

          },[timer]) 
//when timer change it should update  update time state which will be used to update time for time settime out
 
function increment() {  
  useEffect(()=>{    
setTimeout(() => {
  setTimer((ele)=>ele+1)
  
 }, time);
},[timer])
} // above code is for increment time state on each iteration

function ButtonHandle(){
  //setRealString(itr)
  increment()
  
} //button handler for start  timer

'''

【问题讨论】:

  • 你的意思是你想通过自己的延迟时间来延迟显示的通知?
  • “不工作”没有帮助。你看到什么行为?

标签: javascript reactjs settimeout setinterval


【解决方案1】:

首先,你不能把钩子放在函数中(除了你的组件函数)。 https://reactjs.org/docs/hooks-rules.html

所以从 increment() 中取出 useEffect

useEffect(()=>{
    increment()
},[timer])

function increment() {  
    setTimeout(() => {
        setTimer((ele)=>ele+1)
    }, time);
}

但是你还需要清除超时。我们可以返回超时函数来引用它,并通过在 useEffect 中返回来清除超时。 Clearing timeouts and intervals in react

useEffect(()=>{
    const myTimeout = increment()

    return () => {
        clearTimeout(myTimeout)
    }
},[timer])

function increment() {

    return setTimeout(() => {
        setTimer((ele) => ele + 1);
    }, time);
}

然后我们可以组合 useEffects,它们都有一个 [timer] 的依赖数组。

useEffect(() => {
    const getTime = str[timer].time;
    setTime(getTime);

    const myTimeout = increment();

    return () => {
        clearTimeout(myTimeout);
    };
}, [timer]);

【讨论】:

    【解决方案2】:

    您不需要使用 useEffect 来执行此操作。您误解了 useEffect 的用法,它是实现副作用的反应挂钩,您不能在函数内部使用反应挂钩,它应该在组件范围内。

    我可以直接从 ButtonHandle 函数递增。

    // On the index state is necessary in this implementation
    const [index, setIndex] = useState(-1)
    
    const guys=[
      {name: "rammy", time:1000},
      {name: "james", time:4000},
      {name: "crown", time:2000}
    ]
    
    // useCallback memoize the increment function so that it won't
    // change the instance and you can use it in the useEffect 
    // dependency array
    const increment = useCallback(() => {
      setIndex((i) => i+1)
    }, [])
    
    useEffect(() => {
       // change the state if the timer is greater than -1
       if (index !== -1) {
         if (index >= guys.length) {
           setIndex(-1);
         } else {
           setTimeout(() => {
             increment();
           }, guys[index].time); // <-- you get the time from your array
         }
       }
     }, [index, increment]);
    
     function handleClick(){
       //setRealString(itr)
       increment()
     }
    

    虽然我帮了你,但我不知道你想做什么。这个实现听起来有点代码味。如果您解释您正在尝试做的解决方案而不只是代码的和平,我们可以更好地帮助您。

    你不需要设置时间状态,因为你已经在数组中有了时间;避免不必要的状态变化是好的。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-06-21
      • 2022-01-25
      • 2016-08-21
      • 2023-03-04
      • 1970-01-01
      • 1970-01-01
      • 2018-06-26
      相关资源
      最近更新 更多