上面代码我们可以看到是调用了bindActionCreators方法把action绑定到了connect方法中,其中connect方法的作用是连接react组件和redux store,也就是说通过connect方法子组件可以获取store中的state和dispatch。
感觉还是没找到在哪调用的dispatch方法,所以把注意力集中在bindActionCreators方法中,搜了下看到一些解释:bindActionCreators的作用是将一个或多个action和dispatch组合起来生成mapDispatchToProps需要生成的内容。
看代码:
不使用bindActionCreators时候:
let actions = {
onIncrement : {
type: types.ADD_ITEM,
text
}
}
function mapDispatchToProps(dispatch) {
return {
onIncrement: (...args) => dispatch(actions.onIncrement(...args)),
}
}
使用时:
let actions = {
onIncrement : {
type: types.ADD_ITEM,
text
}
}
function mapDispatchToProps(dispatch) {
return bindActionCreators({ actions.onIncrement }, dispatch);
}
bindActionCreator 的作用其实就是用来将一个对象的值是action creators转成一个同样key的对象,但是转化的这个对象的值,是将action creator包裹在dispatch里的函数。
也就是说,假设下面的actionCreator.js 我们import进来这个对象
export function addTodo(text) {
return {
type: 'ADD_TODO',
text
}
}
export function removeTodo(id) {
return {
type: 'REMOVE_TODO',
id
}
}
得到的对象为
{
addTodo : text =>
{
type: 'ADD_TODO',
text
},
removeTodo : id => {
type: 'REMOVE_TODO',
id
}
}
经过bindActionCreator就会变成
{
addTodo : text => dispatch(addTodo('text'));
removeTodo : id => dispatch(removeTodo('id'));
}
相当于会dispatch这个action
参数:
1、actionCretors 可以是一个对象,也可以是一个单个函数
2、dispatch函数
返回:
单个函数,或者是一个对象。
传入一个function
如果只是传入一个function,返回的也是一个function
例如:
const toggleTodo = (id) => {
return {
type: 'TOGGLE_TODO',
id
};
};
export { toggleTodo };
let boundActionCreators = bindActionCreators(toggleTodo, dispatch);
//此时boundActionCreators = (id) => dispatch(toggleTodo(id));
所以bindActionCreator比较简单:
1、判断传入的参数是否是object,如果是函数,就直接返回一个包裹dispatch的函数
2、如果是object,就根据相应的key,生成包裹dispatch的函数即可
bindActionCreators源码解析
function bindActionCreator(actionCreator, dispatch) {
// 这个函数的主要作用就是返回一个函数,当我们调用返回的这个函数的时候,就会自动的dispatch对应的action
// 这一块其实可以更改成如下这种形式更好
// return function(...args) {return dispatch(actionCreator.apply(this, args))}
return function() { return dispatch(actionCreator.apply(this, arguments)) }
}
/**
参数说明:
actionCreators: action create函数,可以是一个单函数,也可以是一个对象,这个对象的所有元素都是action create函数
dispatch: store.dispatch方法
*/
export default function bindActionCreators(actionCreators, dispatch) {
// 如果actionCreators是一个函数的话,就调用bindActionCreator方法对action create函数和dispatch进行绑定
if (typeof actionCreators === 'function') {
return bindActionCreator(actionCreators, dispatch)
}
// actionCreators必须是函数或者对象中的一种,且不能是null
if (typeof actionCreators !== 'object' || actionCreators === null) {
throw new Error(
`bindActionCreators expected an object or a function, instead received ${actionCreators === null ? 'null' : typeof actionCreators}. ` +
`Did you write "import ActionCreators from" instead of "import * as ActionCreators from"?`
)
}
// 获取所有action create函数的名字
const keys = Object.keys(actionCreators)
// 保存dispatch和action create函数进行绑定之后的集合
const boundActionCreators = {}
for (let i = 0; i < keys.length; i++) {
const key = keys[i]
const actionCreator = actionCreators[key]
// 排除值不是函数的action create
if (typeof actionCreator === 'function') {
// 进行绑定
boundActionCreators[key] = bindActionCreator(actionCreator, dispatch)
}
}
// 返回绑定之后的对象
/**
boundActionCreators的基本形式就是
{
actionCreator: function() {dispatch(actionCreator.apply(this, arguments))}
}
*/
return boundActionCreators
}