- 基础:redux 是将全局的状态和方法集中存储在一个仓库里。
仓库中存放有 state(状态)和action(动作),state和action作为参数传入reducer。
然后将reducer传入 redux 中的 createStore 生成仓库。
import { createStore } from "redux";
function reducer(state = {
count: 1
}, action) {
//console.log(state,action);
switch (action.type) {
case "add":
return {
count: state.count + 1
}
case "minus":
return {
count: state.count - 1
}
}
return state;
}
const store = createStore(reducer);
利用 store.getState()
可以获得 store中的 state,用 store.dispatch({type:"add"})
来触发 reducer 的 add 操作。
可以通过 store.subscribe(()=>fn())
来取消 对 fn的监听,如果要重新添加监听,则需要调用()=>unSunscribe=store.subscribe(()=>fn())
<button onClick={unSubscribe}>取消监听</button>
<button onClick={() => {
unSubscribe = store.subscribe(() => {
render();
});
}}>添加监听</button>
-
react-redux
-
在顶层文件index.js中引入react-redux中的Provider 可以将 store 传递给全局。
import store from "./store"; // react-redux redux 在 react 项目中的绑定库,可以让 react 项目在使用 redux 时更方便; ReactDOM.render( <Provider store={store} > <App /> </Provider>, document.querySelector("#root") );
-
如果有两个不同的reducer函数,在创建store时,需要用
combineReducers
来将两个reducer组合成createStore
的参数import { createStore,combineReducers } from "redux"; import count from "./count"; import todo from "./todo"; // 应用多了之后 reducer 会变得极其庞大 // function reducer(state={ // count:1, // todo:[] // },action) { // return { // count:count(state.count,action), // todo:todo(state.todo,action) // } // } // const reducer = combineReducers({ // count:count, // todo:todo // }); // const reducer = combineReducers({ // count, // todo // }); // console.log(reducer); const store = createStore(combineReducers({count,todo})); export default store;
-
hooks
-
useSelector:使用
useSelector(state=>mapState)`来获取 store 中的 state -
useDispatch
:使用useDispatch()
来获取dispatch方法,从来利用dispatch方法传入参数触发store中reducer中的action。 -
useStore
:可以获取store对象,一般不会使用。import { useDispatch, useSelector, useStore} from "react-redux"; function Count() { const count = useSelector(state=>state.count); const d = useDispatch(); console.log(useStore()); return <> <p>{count}</p> <button onClick={()=>{ d({ type: "add" }) }}>+</button> <button onClick={()=>{ d({ type: "minus" }) }}>-</button> </> } export default Count;
-
-
如果两个不同的reducer在触发时,有相同的触发type,则都会触发,产生冲突,注意触发的type是否相同。如果相同,注意修改,一般建议添加前缀。
-