1. 程式人生 > >react系列(五)在React中使用Redux

react系列(五)在React中使用Redux

上一篇展示了Redux的基本使用,可以看到Redux非常簡單易用,不限於React,也可以在Angular、Vue等框架中使用,只要需要Redux的設計思想的地方,就可以使用它。
這篇主要講解在React中使用Redux,首先是安裝。

安裝React Redux

yarn add redux
yarn add react-redux

有兩個概念:
1.容器元件(Container Components)
2.展示元件(Presentational Components)

展示元件

  • 更關注資料展示,所以會寫一些DOM巢狀和CSS
  • 通常不依賴Redux,直接從props中獲取資料
  • 通常沒有state,偶爾會用state來儲存一些展示狀態,如class等
  • 互動也通過props回調發起,不直接發起action

容器元件

  • 通常作為資料來源,做資料分發工作
  • 依賴Redux
  • 通過和store互動進行資料變更
  • 通過react-redux生成

在我們的專案中,一般來說,會編寫很多展示元件,少量的容器元件來包裹這些展示元件。
接下來寫一個簡單的計數器應用,先來劃分容器元件和展示元件。
計數器有三個按鈕,加、減、重置;一個展示區。
由於按鈕既要觸發action,又要負責展示,所以需要做成混合組件。
先來編寫展示元件,就是顯示一下當前計數。

import React from 'react';
const Counter = ({
    count
}) => (
    <p>當前計數為:<span style={{color: 'red'}}>count</span></p>
)

export default Counter;

一般來說,容器元件就是通過store.subscribe傳入回撥,訂閱store的變化,再去把值通過props傳入各個元件中。
在react-redux中實現了connect方法,它生成一個高階元件,就是前面提到的容器元件。這個方法做了效能優化避免不必要的重複渲染,建議使用該方法。

connect([mapStateToProps], [mapDispatchToProps], [mergeProps], [options])

mapStateToProps是一個Function,用來監聽Redux Store的變化,將store的值,對映為對應的props屬性。

const mapStateToProps = ({count}) => {count};
// 或者
const mapStateToProps2 = (state) => {
    count: state.count
}

接下來生成一個容器元件。

import { connect } from 'react-redux';

const ConnectCounter = connect(
  mapStateToProps
)(Counter);

export default ConnectCounter;

接下來是按鈕元件,按鈕元件既需要展示,又有資料互動,做成混合組件。
由於,需要dispatch,所以需要給connect傳入第二個引數。
mapDispatchToProps可以是Object或者Function。用來將dispatch對映到props上。

const mapDispatchToProps = dispatch => {
    return {
        plus: () => dispatch({
            type: 'PLUS'
        })
    }
}
// 或者結合上篇提到的bindActionCreators合成一個物件
function plus() {
  return {
    type: "PLUS"
  };
}

function minus() {
  return {
    type: "MINUS"
  };
}

const mapDispatchToProps2 = dispatch => {
    return bindActionCreators({ plus, minus }, dispatch)
}
import React from 'react';

let Button = ({plus, minus}) => {
    return (
        <>
            <button onClick={plus}>{'plus'}</button>
            <button onClick={minus}>{'minus'}</button>
        </>
    )
};

Button = connect(()=>{}, mapDispatchToProps2)(Button);
export default Button;

最後,提供一個Provider用來提供全域性store。完整例子在這裡-codesandbox
感謝閱讀。