Redux

Redux

专注于状态管理的库

  1. Redux专注于状态管理和react解耦
  2. 单一状态,单向数据流
  3. 核心概念:store,state,action,reducer

使用

  1. 安装
    npm install redux --save
  2. 基础使用
import {createStore} from 'redux';

//新建store
//通过reducer建立
//根据老的state和action 生成新的state
function counter(state = 0, action) {
    switch (action.type) {
        case '赚了1块钱':
            return state + 1;
        case '花了1块钱':
            return state - 1;
        default:
            //初始状态
            return 10;
    }
}

const store = createStore(counter);

console.log("开始手里有" + store.getState() + "块钱");


function listenner() {
    const current = store.getState();
    console.log(`现在手里有${current}块钱`);
}

//订阅,每次状态更换都会触发linstenner函数
store.subscribe(listenner);
//派发事件 传递action
store.dispatch({
    type: '赚了1块钱'
});
store.dispatch({
    type: '赚了1块钱'
});
store.dispatch({
    type: '赚了1块钱'
});
运行结果

Redux 和 React 一起使用

  1. 把store.dispatch方法传递给组件,内部可以调用修改状态。
  2. Subscribe订阅render函数,每次修改都重新渲染。
  3. Redux相关内容,移到单独的文件index.redux.js单独管理。
index.js
import React from 'react';
import ReactDom from 'react-dom';
import {createStore} from 'redux';
import {counter} from './index.redux';
import App from './App';

//创建store
const store = createStore(counter);
function render() {
    ReactDom.render(
        <App store = {store} />,
        document.getElementById('root')
    );
}
render();
//重新渲染render
store.subscribe(render);
index.redux.js
const makeMoney = "赚了1块钱";
const spendMoney = "花了1块钱";

//状态管理
export function counter(state = 0, action) {
    switch (action.type) {
        case makeMoney:
            return state + 1;
        case spendMoney:
            return state - 1;
        default:
            //初始状态
            return 10;
    }
}

//action creator 创建action
export function MakeMoney() {
    return {type:makeMoney}
}
export function SpendMoney() {
    return {type:spendMoney}
}
App.js
import React, {Component} from 'react';
import {
    Button
} from 'antd-mobile';

export default class App extends Component {
    // constructor(props){
    //     super(props);
    // }
    render() {
        //属性获取可以直接用
        const store = this.props.store;
        //获取当前状态
        const money = store.getState();
        //获取方法
        const MakeMoney = this.props.MakeMoney;
        const SpendMoney = this.props.SpendMoney;
        return (
            <div>
                <h1 align='center'>现在手里有{money}块钱</h1>
                <Button type='primary' onClick={() => store.dispatch(MakeMoney())}>赚钱</Button>
                <br/>
                <Button type='primary' onClick={() => store.dispatch(SpendMoney())}>花钱</Button>
            </div>
        )
    }
}
运行结果

处理异步、调试工具、更优雅的和react结合

处理异步

  1. redux-thunk插件
    npm install redux-thunk --save
  2. index.js添加和修改代码
//增加applyMiddleware模块
import {createStore,applyMiddleware} from 'redux';
//引入thunk
import thunk from 'redux-thunk';
  1. index.redux.js添加函数
export function MakeMoneyAsync() {
    return dispatch=>{
        setTimeout(()=>{
            dispatch(MakeMoney());
        },2000);
    };
}

2.使用applyMiddleware开启thunk中间件

  1. Action可以返回函数,使用dispatch提交action

调试工具

  1. 在chrome安装Redux调试工具
    Redux DevTools
  2. 使用
    - 新建store的时候判断window.devToolsExtension
    - 使用compose结合thunk和window.devToolsExtension
    - 开发者工具中的Redux选项卡下可以看到实时state
  3. 代码修改index.js文件
import React from 'react';
import ReactDom from 'react-dom';
//增加applyMiddleware模块
import {createStore,applyMiddleware,compose} from 'redux';
//引入thunk
import thunk from 'redux-thunk';
import {counter,MakeMoney,SpendMoney,MakeMoneyAsync} from './index.redux';
import App from './App';

//修改代码判断系统是否存在函数,若没有则返回空
const ReduxDevTools = window.devToolsExtension?window.devToolsExtension():f=>f;
//创建store
const store = createStore(counter,compose(
    applyMiddleware(thunk),
    ReduxDevTools
));

function render() {
    ReactDom.render(
        <App store = {store} MakeMoney={MakeMoney} SpendMoney={SpendMoney} MakeMoneyAsync={MakeMoneyAsync}/>,
        document.getElementById('root')
    );
}
render();
//订阅render函数,状态变化重新渲染
store.subscribe(render);
  1. 运行结果


使用react-redux优雅的链接react和redux

  1. 安装
    npm install react-rudex --save
  2. 具体使用
    • Provide组件在应用最外层,传入store即可,只用一次
    • Connect负责从外部获取组件需要的参数
    • Connect可以用装饰器的方式来写
  3. 修改后的代码
//index.js
import React from 'react';
import ReactDom from 'react-dom';
//增加applyMiddleware模块
import {createStore, applyMiddleware, compose} from 'redux';
//引入thunk
import thunk from 'redux-thunk';
//引入Provider组件
import {Provider} from 'react-redux';
import {counter} from './index.redux';
import App from './App';

//创建store
const store = createStore(counter, compose(
    applyMiddleware(thunk),//创建异步Redux
    //引入Chrome中的Redux开发者工具
    //修改代码判断系统是否存在函数,若没有则返回空
    window.devToolsExtension ? window.devToolsExtension() : f => f
));
//最外层使用Provide组件,属性只传store,内部App组件内不需要任何属性
ReactDom.render(
    (<Provider store={store}>
        <App/>
    </Provider>),
    document.getElementById('root')
);
//App.js
import React, {Component} from 'react';
import {
    Button
} from 'antd-mobile';
//引入connect专门用来连接
import { connect } from 'react-redux';
//引入动作
import {
    MakeMoneyAsync,
    MakeMoney,
    SpendMoney
} from './index.redux';

class App extends Component {
    render() {
        return (
            <div>
                <h1 align='center'>现在手里有{this.props.money}块钱</h1>
                <Button type='primary' onClick={this.props.MakeMoney}>赚钱</Button>
                <br/>
                <Button type='primary' onClick={this.props.SpendMoney}>花钱</Button>
                <br/>
                <Button type='primary' onClick={this.props.MakeMoneyAsync}>过了2秒又赚钱</Button>
            </div>
        )
    }
}
//使用connect装饰器
const mapStatetoProps = (state) => {
    return {money: state};
};
const actionCreators = {
    MakeMoneyAsync,
    MakeMoney,
    SpendMoney
};
//传递属性和方法
App = connect(mapStatetoProps,actionCreators)(App);
export  default App;

使用装饰器优化connect

  1. 弹出配置文件
    npm run eject
  2. 使用插件
    npm install babel-plugin-transform-decorators-legacy --save-dev
  3. 在package.json中加上plugins配置
    在babel下的plugins内添加
   [
        "transform-decorators-legacy"
   ]
  1. 代码修改 App.js
//使用connect装饰器
// const mapStatetoProps = (state) => {
//     return {money: state};
// };
// const actionCreators = {
//     MakeMoneyAsync,
//     MakeMoney,
//     SpendMoney
// };
//传递属性和方法
//App = connect(mapStatetoProps,actionCreators)(App);
//删除上面代码并改为如下
//将@connect挪到class上面
@connect(
    //需要的属性
    state=>({money:state}),
    //需要的方法,自动dispatch
    { MakeMoneyAsync, MakeMoney, SpendMoney}
)
export default class App extends Component {
      ...
}
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,324评论 5 476
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,303评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,192评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,555评论 1 273
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,569评论 5 365
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,566评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,927评论 3 395
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,583评论 0 257
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,827评论 1 297
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,590评论 2 320
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,669评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,365评论 4 318
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,941评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,928评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,159评论 1 259
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 42,880评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,399评论 2 342

推荐阅读更多精彩内容