反应 useState,useEffect 没有按预期工作

Tam*_*Bui 2 reactjs react-hooks

我有一个用例,我想用 React 钩子解决它,但它没有按我预期的那样工作。

  • 期望:不在顶部将在向下滚动时显示,并在回滚到文档顶部时消失。
  • 当前:向下滚动时不在顶部显示,但在文档顶部滚动时不会消失。代码沙箱链接:https : //codesandbox.io/s/wkroy1r2xl

提前致谢。

kin*_*aro 7

该组件添加一次事件侦听器:仅在安装时。那时,它会添加在该特定时间点handleScroll使用该特定isHeaderMoved值“捕获”的侦听器。每当页面滚动时,将调用的回调是具有该初始isHeaderMoved值的回调。当前代码基本上handleScrollfalse一遍遍地调用。

简而言之,您需要添加isHeaderMoved作为效果的依赖项。您还应该handleScroll在效果内移动侦听器,以便 hooks eslint 插件可以更正确地跟踪其依赖项。

  useEffect(
    () => {
      const handleScroll = () => {
        if (window.pageYOffset > 0) {
          if (!isHeaderMoved) {
            setIsHeaderMoved(true)
          }
        } else if (isHeaderMoved) {
          setIsHeaderMoved(false)
        }
      }

      window.addEventListener("scroll", handleScroll)
      return () => {
        window.removeEventListener("scroll", handleScroll)
      }
    },
    [isHeaderMoved],
  )
Run Code Online (Sandbox Code Playgroud)

请参阅 Dan Abromov 关于该主题的帖子中的这些部分(其中的示例可以比我更好地解释它):

如果您有时间,阅读整篇文章以完全理解事物是值得的。


根据 skyboxer 的评论,我想到这也可以,但我会保留以上所有内容以供参考。

  useEffect(() => {
    const handleScroll = () => {
      setIsHeaderMoved(window.pageYOffset > 0)
    }

    window.addEventListener("scroll", handleScroll)
    return () => {
      window.removeEventListener("scroll", handleScroll)
    }
  }, [])
Run Code Online (Sandbox Code Playgroud)