React,Redux學習筆記

@(StuRep)2016.06.10javascript

React的PropTypes使用方法

React.PropTypes.array // 數組

React.PropTypes.bool.isRequired // Boolean 且必要。 

React.PropTypes.func // 函式 

React.PropTypes.number // 數字

React.PropTypes.object // 對象 

React.PropTypes.string // 字符串 

React.PropTypes.node // 任何類型的: numbers, strings, elements 或者任何這種類型的數組

React.PropTypes.element // React 元素 

React.PropTypes.instanceOf(XXX) // 某種類型的實例

React.PropTypes.oneOf(['foo', 'bar']) // 其中一個字符串

React.PropTypes.oneOfType([React.PropTypes.string,React.PropTypes.array]) // 其中一種格式類型

React.PropTypes.arrayOf(React.PropTypes.string) // 某種類型的數組(字符串型) 

React.PropTypes.objectOf(React.PropTypes.string) // 具備某種屬性類型的對象(字符串類型) 

React.PropTypes.shape({ // 是否符合指定格式的對象
    color: React.PropTypes.string, 
    fontSize: React.PropTypes.number 
}); 

React.PropTypes.any.isRequired // 能夠是任何格式,且必要。

_java

react-redux中的connect方法

//綁定狀態到props上面
function mapStateToProps(state) {
    return {
        year: state.calendarReducer.year,
        month: state.calendarReducer.month,
        day: state.calendarReducer.day
    }
}

//把action全部方法綁定到props上面,同時action具備了dispatch能力
function mapDispatchToProps(dispatch) {
    return {actions: bindActionCreators(CalendarActions, dispatch)}
}

export default connect(mapStateToProps, mapDispatchToProps)(App)

mapStateToProps 監聽store變化,添加這個才能讓組件監聽到store裏面的狀態;node

Redux 有一個全局的state,經過將根組件包進Provider,將store分發給全部的子組件,而子組件經過connect方法,獲取dispatch事件分發函數,以及須要的props(若是有須要也能夠經過connect傳入想分發給子組件的action)
_react

如何用Redux去管理React的狀態

在不使用 Redux的時候, React組件間的狀態管理須要一層層地傳遞,使用 Redux能夠在最頂層的 store中存儲全部的狀態,每一個組件均可以得到這些狀態值。

Redux主要的三部分:

  • Store
  • Action
  • Reducer

簡單的流程:dispatch(action)把action分發到reducer,reducer更新狀態而後返回到store,總的容器組件(app)從store(this.props)中獲取的值有變,傳給子組件的屬性變化,觸發render從新渲染。編程

action

Redux中,action主要用來傳遞操做State的信息,以一個js對象的形式存在,除了其中的type字段爲必須的,其餘字段均可以定義。若是採用直接聲明action的方式,在action愈來愈多的時候就會很難管理,因此有了action的構造工廠:redux

//action建立函數
export function getNextMonth() {
    return {type: GET_NEXT_MONTH}
}

reducer

action用來傳遞信息,reducer就用來處理信息,傳入一箇舊的state來返回一個新的state。數組

reducer應該保持「純函數」特性,入參相同,出參結果必定相同。這也是函數式編程的特色。服務器

function calendarReducer(state = initialState, action) {

    switch (action.type) {
        case GET_NEXT_MONTH:
            return state.month >= 12 ? {...state, year: ++state.year, month: 1} : {...state, month: ++state.month};
        case GET_PRE_MONTH:
            return state.month <= 1 ? {...state, year: --state.year, month: 12} : {...state, month: --state.month};
        default:
            console.log("default calendarReducer state");
            return state;
    }
}

在reducer中,須要傳入一個默認的state參數,在dispatch一個action區觸發state修改的時候,若是reducer中並無匹配到該action,那就必定要返回一箇舊的state,否則會形成undefined。app

另外,在修改狀態的時候,不要經過直接修改當前state,而是經過建立一個副本去修改,能夠用ES6中的Object.assign方法:框架

return Object.assign({}, state, {
        XXX:XXX
})

或者使用ES7提案中的對象展開運算符(...):

switch (action.type) {
        case GET_NEXT_MONTH:
            return state.month >= 12 ? {...state, year: ++state.year, month: 1} : {...state, month: ++state.month};
        case GET_PRE_MONTH:
            return state.month <= 1 ? {...state, year: --state.year, month: 12} : {...state, month: --state.month};
        default:
            console.log("default calendarReducer state");
            return state;
    }

在使用ES7的展開運算符的時候須要添加一個插件來支持,由於目前該語法還處於stage2階段:

query: {
        presets: ['react', 'es2015'],
        plugins: ['transform-object-rest-spread']
}

store

在 Redux 項目中,Store 是單一的。維護着一個全局的 State,而且根據 Action 來進行事件分發處理 State。能夠看出 Store 是一個把 Action 和 Reducer 結合起來的對象。

Redux 提供了 createStore() 方法來 生產 Store,如:

let store = createStore(calendarApp);

react-redux 提供一個<Provider>組件把整個app包在裏面,以 React 組件的形式來爲 Provider 注入 store,從而使得其子組件可以在上下文中獲得 store 對象,共享同一個store,如:

let rootElement = document.getElementById('main');

render(
    <Provider store={store}>
        <App />
    </Provider>,
    rootElement
);

_

組件的生命週期

componentWillMount

componentWillMount()

服務器端和客戶端都只調用一次,在初始化渲染執行以前馬上調用。若是在這個方法內調用 setStaterender() 將會感知到更新後的 state,將會執行僅一次,儘管 state 改變了。

componentDidMount

componentDidMount()

在初始化渲染執行以後馬上調用一次,僅客戶端有效(服務器端不會調用)。在生命週期中的這個時間點,組件擁有一個 DOM 展示,能夠經過 this.getDOMNode() 來獲取相應 DOM 節點。

若是想和其它JavaScript 框架集成,使用setTimeout 或者setInterval 來設置定時器,或者發送 AJAX 請求,能夠在該方法中執行這些操做。

componentWillReceiveProps

componentWillReceiveProps(object nextProps)

在組件接收到新的 props 的時候調用。在初始化渲染的時候,該方法不會調用。

用此函數能夠做爲 reactprop 傳入以後, render() 渲染以前更新 state 的機會。老的 props 能夠經過 this.props 獲取到。在該函數中調用 this.setState() 將不會引發第二次渲染。

shouldComponentUpdate

boolean shouldComponentUpdate(object nextProps, object nextState)

在接收到新的 props 或者 state,將要渲染以前調用。該方法在初始化渲染的時候不會調用,在使用 forceUpdate 方法的時候也不會。

若是肯定新的 propsstate 不會致使組件更新,則此處應該 返回 false

shouldComponentUpdate: function(nextProps, nextState) {
  return nextProps.id !== this.props.id;
}

若是 shouldComponentUpdate 返回 false,則 render() 將不會執行,直到下一次 state 改變。(另外,componentWillUpdatecomponentDidUpdate 也不會被調用。)

默認狀況下,shouldComponentUpdate 總會返回 true,在 state 改變的時候避免細微的 bug,可是若是老是當心地把 state 當作不可變的,在 render() 中只從 props state 讀取值,此時能夠覆蓋 shouldComponentUpdate 方法,實現新老 propsstate 的比對邏輯。

若是性能是個瓶頸,尤爲是有幾十個甚至上百個組件的時候,使用 shouldComponentUpdate 能夠提高應用的性能。

componentWillUpdate

componentWillUpdate(object nextProps, object nextState)

在接收到新的 props 或者 state 以前馬上調用。在初始化渲染的時候該方法不會被調用。
使用該方法作一些更新以前的準備工做。

componentDidUpdate

componentDidUpdate(object prevProps, object prevState)

在組件的更新已經同步到 DOM 中以後馬上被調用。該方法不會在初始化渲染的時候調用。
使用該方法能夠在組件更新以後操做 DOM 元素。

componentWillUnmount

componentWillUnmount()

在組件從 DOM 中移除的時候馬上被調用。

在該方法中執行任何須要的清理,好比無效的定時器,或者清除在 componentDidMount中建立的 DOM 元素。

相關文章
相關標籤/搜索