组件如何使用钩子在 redux 中重新渲染

时间:2020-12-21 18:47:41

标签: reactjs redux react-redux

我正在尝试将 redux 及其工作概念化,经过一些测试,我注意到了一件事。我想引用这个例子

比方说,我有一个减速器(一个布尔变量)。基于该变量,发生以下代码。

减速器

const initState = { isLoggedIn: false };
const isLoggedInReducer = (state = initState, action) => {
  switch (action.type) {
    case "LOG_IN":
      return { ...state,isLoggedIn: true };
    case "LOG_OUT":
      return { ...state,isLoggedIn: false };
    default:
      return state;
  }
};

export default isLoggedInReducer;

动作

export const logIn = () => {
    return {
        type:'LOG_IN'
    }
}

export const logOut = () => {
    return {
        type:'LOG_OUT'
    }
}

index.js

<Provider store={createStore(isLoggedInReducer)}>
      <Router>
        <Switch>
          <Route path="/" exact>
            <AppScreen />
          </Route>
          <Route path="/auth">
            <AuthScreen />
          </Route>
          <Route path="*">
            <NotFoundScreen />
          </Route>
        </Switch>
      </Router>
    </Provider>

因此,我的应用程序首先将用户引导至名为“mainScreen”的组件,如下所示

const AppScreen = () => {
  let isLoggedIn = useSelector((state) => state.isLoggedIn);
  if (isLoggedIn)
    return (
      <>
          <button onClick={() => dispatch(logOut())}>unauthenticate</button>
          <NavBar />
          <Content />
          <BottomBar />
      </>
    );
  else{
    return (
      <>
        <Redirect to="/auth" push />
      </>
    );
  }
};

因此,如果 reducer 状态的值为 TRUE ,则​​显示我的导航栏和内容,否则用户将被重定向到“authScreen”,即

const AuthScreen = () => {
  let isLoggedIn = useSelector((state) => state.isLoggedIn);
  const dispatch = useDispatch();
  return isLoggedIn ? (
    <>
        <Redirect to="/" push />
    </>
  ) : (
    <>
      <h1> auth is {isLoggedIn?"true":"false"}</h1>
      <button onClick={() => dispatch(logIn())}>authenticate</button>
    </>
  );
};

这会创建一个设置,其中“authScreen”可以将 reducer 切换为 TRUE 并重新呈现,并发现 reducer 为 TRUE,因此它呈现“mainScreen”。 “主屏幕”反之亦然

现在,实际上重新渲染了哪些组件?如果我将我的身份验证按钮放在“导航栏”而不是“导航栏”的同级中,它会重新呈现“导航栏”还是“主屏幕”?

当状态改变时,redux 如何计算要重新渲染的组件?当我什至没有使用“connect”时,useSelector 是如何适应的。

在 redux 中使用 hooks 非常令人困惑。如果我的解释难以理解,我很抱歉。该代码实际上有效,我只是不知道如何。 感谢您提供任何信息!

1 个答案:

答案 0 :(得分:1)

Using Redux with a UI always follows the same basic steps

  • 使用初始状态渲染组件
  • 调用 store.subscribe() 以在分派操作时收到通知
  • 调用store.getState()读取最新数据
  • 区分此组件所需的旧值和新值,以查看是否有任何实际更改。如果没有,组件不需要做任何事情
  • 使用最新数据更新用户界面

React-Redux 在内部为你做这件事。

因此,useSelector 决定是否应根据在选择器函数中返回的任何数据重新渲染组件:

https://redux.js.org/tutorials/fundamentals/part-5-ui-react#reading-state-from-the-store-with-useselector

如果在调度操作后选择器返回值发生变化,useSelector 会强制该组件重新渲染。从那里,normal React rendering behavior kicks in, and all child components are re-rendered by default

请阅读我的帖子 The History and Implementation of React-Redux 并讨论 A Deep Dive into React-Redux 以详细了解 React-Redux 如何实际实现此行为。