redux
redux就是將組件的數據放到一個公共的store裏,大家都可以去讀取,把數據的傳遞簡化了。一個組件改變了store的值,其他的組件就會知道,然後會去取改變之後的數據
redux=reducer+flux
redux工作流
Store的創建
1、src目錄下面創建store文件夾。
2、在store文件夾中,創建index,js用來創建公共倉庫,代碼如下
import { createStore } from 'redux';
import reducer from './reducer'
const store = createStore(reducer);//創建公共倉庫
export default store;
3、在store文件夾中,創建reducer.js,代碼如下
//reducer需要返回一個函數
//state就是整個倉庫裏存儲的數據
const defaultState={
inputValue:"",
list:[]
}//默認不存儲任何數據
export default (state=defaultState,action) => {
return state
}
4、組件中引入
import store from './store/index'
5、讀取store中的數據
組件中store.getState()就能獲取到公共庫中的所有存儲字段
6、修改store中的數據
下面代碼放到constructor
this.handleStoreChange=this.handleStoreChange.bind(this)
//store裏面的內容只要被改變,這個函數就會被執行
store.subscribe(this.handleStoreChange)
//放到方法裏
handleInputChange(e){
e.persist()
console.log(e.target)
const action = {
type:"change_input_value",//告訴action要做啥
value:e.target.value
}
store.dispatch(action)
}
handleStoreChange(){
console.log("store change"+"=========")
console.log(store.getState())
this.setState(store.getState())//重新獲取更新state,新的state替換原來的state
}
reducer文件
//reducer可以接收state,但是絕不能修改state 因此要去拷貝,改變新的state
export default (state=defaultState,action) => {
if(action.type=="change_input_value"){
//拷貝一份之前state裏面的數據--深拷貝
const newState=JSON.parse(JSON.stringify(state))
newState.inputValue=action.value
return newState;
}
return state
}
actionTypes的拆分
其實就是將action的Type作爲常量放到一個actionTypes.js中,
防止type太多導致的一些不必要的bug
在組件中不斷定義action的type,代碼比較繁瑣,這個時候可以使用actionCreators統一創建action
eg創建actionCreators.js,代碼如下
import { CHANGE_INPUT_VALUE, ADD_ITEM_TO_LIST, DEL_ITEM_FROM_LIST} from './actiontypes'
export const getInpuChangeAction = (value) => ({
type:CHANGE_INPUT_VALUE,
value
})
export const addItemToList = () => ({
type:ADD_ITEM_TO_LIST,
})
export const delItemFromList = (index) => ({
type:DEL_ITEM_FROM_LIST,
index
})
組件中
const action = addItemToList()
store.dispatch(action)
知識總結
redux設計和使用三大原則
1、store是唯一的
2、只有store能夠改變自己的內容
3、reducer必須是純函數
純函數是指給固定的輸入就一定有固定的輸出
遇到的問題
e.target是null
解決辦法:在調用e.target之前調用e.persist()
eg: e.persist()
console.log(e.target)