Reducer 和 Context
使用 Reducer 和 Context 拓展你的应用
Reducer 可以用来整合组件的状态更新逻辑。
Context 可以用来将数据深入传递给其他组件。
结合使用 Reducer 和 Context,可以共同管理一个复杂页面的状态。
基本用法
- 首先创建一个 Context 对象用于共享值。
- 然后创建一个 Reducer 函数用于处理状态更新逻辑。
- 接着创建一个 Provider 组件,将 Context 对象和 Reducer 函数传递给 Provider 组件。
- 最后在需要使用共享值的组件中使用
useContext()
消费共享值。
ts
import { createContext, Dispatch } from 'react';
interface CounterState {
count: number;
}
interface CounterAction {
type: string;
payload?: any;
}
export const CounterContext = createContext<{
state: CounterState;
dispatch: Dispatch<CounterAction>;
}>({
state: { count: 0 },
dispatch: () => undefined
});
ts
export function counterReducer(state: { count: number; }, action: {
type: string;
payload?: any;
}) {
switch (action.type) {
case 'increment':
return { count: state.count + 1 };
case 'decrement':
return { count: state.count - 1 };
default:
return state;
}
}
tsx
import { useReducer } from "react";
import { counterReducer } from "./CounterReducer";
import { CounterContext } from "./CounterContext";
export default function CounterProvider({
children,
}: {
children: React.ReactNode;
}) {
const [state, dispatch] = useReducer(counterReducer, {
count: 0,
});
return (
<CounterContext.Provider value={{ state, dispatch }}>
{children}
</CounterContext.Provider>
);
}
tsx
import { useContext } from "react";
import CounterProvider from "./CounterProvider";
import { CounterContext } from "./CounterContext";
function Counter() {
const { state, dispatch } = useContext(CounterContext);
return (
<div>
<p>Count: {state.count}</p>
<button onClick={() => dispatch({ type: "increment" })}>+</button>
<button onClick={() => dispatch({ type: "decrement" })}>-</button>
</div>
);
}
export default function CounterWithReducerContext() {
return (
<CounterProvider>
<Counter />
</CounterProvider>
);
}