目录结构:
src/index.js
src/App.js
redux/action-types.js
redux/actions.js
redux/reducers.js
redux/store.js
1. 下载redux依赖包
cnpm i --save redux
2. action-types.js
/*
* 包含所有的action type的常量字符串
*/
export const INCREMENT = 'INCREMENT'
export const DECREMENT = 'DECREMENT'
3. actions.js
import {DECREMENT, INCREMENT} from "./action-types";
/*
* 包含所有的action creator
*/
export const increment = number => ({
type: INCREMENT,
data: number
})
export const decrement = number => ({
type: DECREMENT,
data: number
})
4. reducers.js
/*
* 包含多个reducer函数的模块
*/
import {DECREMENT, INCREMENT} from "./action-types";
export function counter(state = 0, action) {
switch (action.type) {
case INCREMENT:
return state + action.data
case DECREMENT:
return state - action.data
default:
return state
}
}
5. store.js
import {createStore} from "redux";
import {counter} from "./reducers";
//生成一个store对象
const store = createStore(counter)
console.log(store, store.getState())
export default store
6. App.js
import React, {Component} from 'react';
// import {decrement, increment} from "./redux/react_redux_counter/actions";
import * as actions from './redux/react_redux_counter/actions'
//非受控组件select的使用
class App extends Component {
// 增加
increment = () => {
const number = this.select.value * 1
// const {count} = this.state
// this.setState({count: count + number})
// 调用store的方法更新状态
this.props.store.dispatch(actions.increment(number))
}
// 减少
decrement = () => {
const number = this.select.value * 1
// const count = this.props.store.getState()
// this.setState({count: count - number})
this.props.store.dispatch(actions.decrement(number))
}
// 偶数增加(满足条件后再增加)
incrementIfOdd = () => {
const number = this.select.value * 1
const count = this.props.store.getState()
if (count % 2 === 1) {
// this.setState({count: count + number})
this.props.store.dispatch(actions.increment(number))
} else {
alert(`${count}不是奇数呦!`)
}
}
// 异步增加(设置延时定时器)
incrementAsync = () => {
const number = this.select.value * 1
setTimeout(() => {
this.props.store.dispatch(actions.increment(number))
}, 1000)
}
render() {
// const {count} = this.state
// 得到原本的count状态
const count = this.props.store.getState()
return (
<div>
<p>click {count} times</p>
<div>
<select ref={select => this.select = select}>
<option value="1">1</option>
<option value="2">2</option>
<option value="3">3</option>
</select>
<button onClick={this.increment}>+</button>
<button onClick={this.decrement}>-</button>
<button onClick={this.incrementIfOdd}>increment if odd</button>
<button onClick={this.incrementAsync}>increment async</button>
</div>
</div>
);
}
}
export default App;
7. index.js
import React from 'react';
import ReactDOM from 'react-dom';
import App from "./App";
import store from "./redux/react_redux_counter/store";
function render() {
ReactDOM.render(
<App store={store}/>
,
document.getElementById('root')
);
}
// 初始化渲染
render()
//订阅监听(store中的状态变化了,就会自动调用进行重绘)
store.subscribe(render)
8. 效果图
9. 问题: 以上的代码还不是最优的
1)redux与react组件的代码耦合度太高
2)编码不够简洁
下一篇博客,结合react-redux编写counter应用~