connect
首先,如果正常的实现redux在react的应用。以类组件为例子,
- 一般是在constructor()里面听过this.stae={storeState:store.getState()}来获取redux中的state值
- 接着通过方法来派发action,比如点击事件,然后触发stote.patch(action),听过dispatch来修改redux里面的state的值,
- 然后在componentDidMount里面通过监听store.subscribe(()=>{this.setState()})来实时修改类组件的状态。
- 并且需要在componentWillUnmount()里面来注册该监听。
如果这样的话每个组件都会写重复类似的代码,造成代码冗余也不方便维护。
react-redux提供了connect高阶组件来帮助我们简洁方便的完成上述操作。
大多数高阶组件,其实就是一个函数,这个函数让你传入一个组件,然后自己内部再创建一个新组件,把你传入的组件作为新组件的子组件用,其外还添加了一些新的东西,比如在生命周期函数做些别的事,多传入一些props等等,变相的增强你传入的组件,使本来这个平平无奇的组件通过高阶组件修饰后,变得多姿多彩。
connect也是做这样的事,我们先来定义一个connect函数。
这是最简单的一个connect,现在开始逐渐完善其功能。首先是两个参数,我们用A与B来代替,一般
A就是
const mapStateToProps = state => {
return {
counter: state.counter
}
}
一个箭头函数,这个state就是等会我们要传的值,先知道他长什么样就行。
B就是
const mapDispatchToProps = dispatch => {
return {
addNumber: function(number) {
dispatch(addAction(number));
}
}
}
我们现在只要大概知道是两个箭头函数就行
我们要知道为什么有connect,就是因为不想在每个组件中的componentDidUnmonut中去写store.subcribe和引入store,所以,我们得把这些步骤,写在我们的高阶组件,connect中。来看看代码
先看骚操作
我们利用高阶组件的传递props的一个特性,将store里面的数据,还有一些action方法,选择性的传递给我们的组件,这样在我们的组件中就不用再引入store了。
这时候再看看我们的两个参数
我们可以选择,将counter传给我们的组件,而不传其他数据,也可以选择将addNumber传给组件,而不传其他方法。这样在组件就可以通过this.props.counter去获取store里面的值。
但这只是一个过渡,没有大大我们刚才要的监听,修改数据。其实,只需要在connect返回的这个组件中,通过constructor来初始化数据,通过生命周期函数来监听值改变,通过this.setState()来改变值并重新render,这样就相当于connect内部帮我们做了监听以及改变,我们就不用手动自己添加了。看代码
但sotre,我们还得自己引入,如果我们将这个函数封装成库,难道还要用户自己修改你的源码?显然这并不现实,那怎么办呢?
这时候就要利用我们的context对象了。
首先,创建我们的要给context对象,
其实这时候思路已经出来了,我们只需要
然后我们只需要在入口的Index文件中,
将我们要的store传给value,这时候我们只需要修改connect函数里面的代码,将sotre全部改为this.context即可,
这样我们connect的封装就基本完成了。
其实react-redux中的conncet与Provider也大概这个道理,不过他做的事情更多,而且他的store是传给store的,不是value.