开头几张图,剩下全靠编
Redux形象图
Redux的在react-redux的架构
Store
import { createStore } from 'redux';
const store = createStore(fn);
State
import { createStore } from 'redux';
const store = createStore(fn);
const state = store.getState();
Action
const action = {
type: 'ADD_TODO',
payload: 'Learn Redux'
};
Action Creator
import { createStore } from 'redux';
const store = createStore(fn);
store.dispatch()
import { createStore } from 'redux';
const store = createStore(fn);
store.dispatch({
type: 'ADD_TODO',
payload: 'Learn Redux'
});
//结合 Action Creator
store.dispatch(addTodo('Learn Redux'));
Reducer
// 基本形式
const reducer = function (state, action) {
// ...
return new_state;
};
// 创建、使用
const defaultState = 0;
const reducer = (state = defaultState, action) => {
switch (action.type) {
case 'ADD':
return state + action.payload;
default:
return state;
}
};
const state = reducer(1, {
type: 'ADD',
payload: 2
});
// store.dispatch方法会触发 Reducer 的自动执行,需要将 Reducer 传入createStore方法
import { createStore } from 'redux';
const store = createStore(reducer);
// 实际调用
const actions = [
{ type: 'ADD', payload: 0 },
{ type: 'ADD', payload: 1 },
{ type: 'ADD', payload: 2 }
];
const total = actions.reduce(reducer, 0); // 3
store.subscribe()
// 对于 React 项目,就是组件的render方法或setState方法)放入listen,就会实现 View 的自动渲染。
import { createStore } from 'redux';
const store = createStore(reducer);
store.subscribe(listener);
// unsubscribe
let unsubscribe = store.subscribe(() =>
console.log(store.getState())
);
unsubscribe();
Store 实现方式
import { createStore } from 'redux';
let { subscribe, dispatch, getState } = createStore(reducer);
###### Reducer 的拆分合并——combineReducers
```javascript
import { combineReducers } from 'redux';
const chatReducer = combineReducers({
chatLog,
statusMessage,
userName
})
export default todoApp
//
const reducer = combineReducers({
a: doSomethingWithA,
b: processB,
c: c
})
// 分拆到单个文件
import { combineReducers } from 'redux'
import * as reducers from './reducers'
const reducer = combineReducers(reducers)
主要使用方式
store.dispatch(action);
let nextState = todoApp(previousState, action);
// 设置监听函数
store.subscribe(listener);
//其中
function listerner() {
let newState = store.getState();
component.setState(newState); // 更新component局部的state
}
中间件
在store.dispatch改造:Action
方法: applyMiddlewares[作用是将所有中间件组成一个数组,依次执行], applyMiddleware
同步、异步操作
同步操作只要发出一种 Action 即可,异步操作的差别是它要发出三种 Action。
- 操作发起时的 Action
- 操作成功时的 Action
- 操作失败时的 Action
useReducer
代码片段(用于函数组件),参考用 useReducer 代替 Redux
使用 useReducer 创建状态机
const [state, dispatch] = useReducer(reducer, {
filter: filterOptions.SHOW_ALL,
todoList: []
});
使用 createContext 和 useContext 暴露状态机接口
// Context
import {createContext} from 'react';
const Context = createContext(null);
export default Context
// App
function App() {
const [state, dispatch] = useReducer(reducer, {
filter: filterOptions.SHOW_ALL,
todoList: []
});
return (
<Context.Provider value={{ state, dispatch }}>
<div className="App">
我是 APP,要点:useReducer 的初始值不要传 null,要初始化,否则使用 ajax fetch 不成功
<AddTodo/>
<TodoList/>
<Filter/>
</div>
</Context.Provider>
);
}
// TodoList Component
const TodoList = () => {
const {state, dispatch} = useContext(Context);
useEffect(()=> {
fetchTodoList(dispatch)
},[])
const getVisibleTodoList = (state, filter)=>{
switch (filter) {
case filterOptions.SHOW_ALL:
return state.todoList
case filterOptions.SHOW_COMPLETE:
return state.todoList.filter(todo => todo.isComplete)
case filterOptions.SHOW_UNCOMPLETE:
return state.todoList.filter(todo => !todo.isComplete)
}
}
return state.todoList.length > 0 ? (
<ul>
{getVisibleTodoList(state, state.filter).map((todo, index) => (
<li key={index} onClick={() => dispatch(toggleTodo(index))}
style={{textDecoration: todo.isComplete ? 'line-through' : 'none'}}>{todo.text}</li>
))}
</ul>
) : (<div>加载中...</div>);
};
后面的看文章用 useReducer 代替 Redux