1. 程式人生 > >淺入react-native使用redux

淺入react-native使用redux

Redux 是 JavaScript 狀態容器,提供可預測化的狀態管理。

初學這個,覺得網上有些文章並不那麼容易看懂,這裡用淺白的話簡單介紹一下Redux在react-native的使用。

說白了就三個主要東西,Action,Store以及Reducer。

Action:主要用來觸發一些事務改變state,平時都用setState改變狀態。
Reducer:在觸發上面的Action後,對Action進行處理,並返回一個新的state。

Store:每個程式有且只有一個Store,作為一個根節點管理state,很多個state等於子節點。Action和Reduce就是通過Store才能聯絡到一起。

直接來個事例,順便對比一下用傳統的setState方法和使用Redux來控制state的區別

先來搭配一下Redux環境

npm install --save redux 【redux的包】

npm install --save react-redux  【react-redux是redux需要依賴的包】

npm install --save redux-thunk   【redux-thunk是用來讓redux有非同步的action事務】

先看工程的目錄結構,有三個資料夾,就是上述三個東西。。。。。


Store留在最後才說,因為這是其他兩個連線的物件。

這三個東西的流程是這樣的,

1.Store不用多說,都是拷貝一份程式碼完事。然後把store的綁在根頁面的屬性內。

2.Reducer,先建一個索引的檔案作為繫結Reducer的(也是拷貝的功夫),然後就可以寫多個Reducer了。Reducer是通過Action分發過來的action,找到合適型別的Reducer,Reducer的邏輯程式碼就會生成新的一個state,最後return給Store。

3.Action,給頁面觸發用的,當頁面繫結好connect,就可以通過props獲取【dispatch分發器】和【Store管理的state】,dispatch分發器在頁面使用:(1)事件會傳到Action。(2)Action裡再用dispatch分發到Reducer。(3)Reducer已經綁定了Store,只要return一個state給Store,Store就會把新的state替換舊的。

4.從以上三步可以看出,這三個東西的運作流程,但會有點模糊,我看很多貼的時候都會有這個疑問,我現在很熟悉redux的原理了,我到底怎麼統一管理state呢?回顧一下這裡第1點,Store是要綁在根頁面的,因此我們可以獲得Store管理的state。再回顧一下第2點,Reducer需要一個索引繫結多個Reducer的,因此每個Reducer返回的新的state是都得經過繫結這個索引的。最後回顧第3點,頁面獲得Store管理的state。綜合以上分析,根據Reducer的索引可以找到對應的state,然後讓頁面獲得對應的state。

Redux其實說白了,比直接用傳統的state是要麻煩很多,因為寫多了很多程式碼才能達到使用傳統的state的效果。但是維護這個很關鍵,統一管理state,在維護上,絕對比傳統的state要快,因為有業務邏輯程式碼改動的話,不要再開啟那臃腫的介面慢慢找,在Redux框架可以快速找到相應程式碼,而且看到的程式碼是簡潔的。這大概是前期費那麼大勁也要使用Redux的原因吧。

先來Action

LoginAction.js是一個處理登入的action,這裡寫得很簡單,看看帳號密碼對不對。

import * as types from './ActionType';

export function performLoginAction(username, password) {
	return (dispatch) => {
		console.log("run......performLoginAction.....performLogin");
		dispatch(performLogin());
		if (username === 'ljy' && password === '123') {
			dispatch(receiveLoginResult("succeed"));
		} else {
			// dispatch(receiveLoginResult("fail"));
			dispatch(receiveLoginResult("fail"));
		}
	}
}

function performLogin() {
	return {
		type: types.PERFORM_LOGIN_ACTION,
	}
}
function receiveLoginResult(result) {
	return {
		type: types.RECEIVE_LOGIN_ACTION,
		data: result
	}
}

上面匯入的ActionType.js是下面這段你沒看錯,這個檔案主要是用來寫一些Action型別,為什麼需要這個呢?因為我們平時管理RN的資料,都是用state管理的,這個redux作為一箇中間件統一管理所有state,所以有個Action型別,讓Action能正確地分發給下一級Reducer。

export const PERFORM_LOGIN_ACTION = 'PERFORM_LOGIN_ACTION';
export const RECEIVE_LOGIN_ACTION = 'RECEIVE_LOGIN_ACTION';

先不說函式呼叫的問題,先要理解每個函式的作用,後面用到的時候會提到。

performLoginAction(username, password)這個方法是用來處理登入的,裡面return一個方法,可以看到方法裡面有多個dispatch方法。dispatch是用來傳遞給下一級的。action的下一級是Reducer,可見performLoginAction(username, password)方法下面有兩個方法,都是返回一個物件的,那就是把物件傳過去給Reducer。那最大的疑問是(dispatch)=>{}括號裡的dispatch從哪裡傳過來的,上面流程第3點,頁面繫結資料connect就能獲取dispatch,那這裡Action的dispatch當然是從頁面傳過來的啦。

再來Reducer

需要一個索引,建一個index.js,程式碼就是拷貝,要改的是combineReducers裡面的物件,比如login是索引(key),物件就是引入的LoginReducers。

import {combineReducers} from 'redux';
import LoginReducers from './LoginReducers';
import LoginReducers2 from './LoginReducers2';

const rootReducer = combineReducers({
	login: LoginReducers,
	login2: LoginReducers2
});

export default rootReducer;
從索引可以看到有兩個Reducer,這裡給出其中一個LoginReducers.js,另一個大同小異。
import * as types from '../action/ActionType';

const initialState = {
	loading: false,
	data: '',
}

export default function login(state = initialState, action) {
	switch (action.type) {
		case types.PERFORM_LOGIN_ACTION:
			return {
				...state,
				loading: true,
			};
		case types.RECEIVE_LOGIN_ACTION:
			return {
				...state,
				loading: false,
				data: action.data
			};
		default:
			return state;
	}
}

Action裡的dispatch傳到Reducer來了,在上面Action的dispatch只有一個引數,這個引數傳到這個Reducer的提供了的login方法的action引數,因為第一個引數是內建的state引數,這裡login方法有個switch,根據Action型別返回對應的state,否則返回原來的state。

這段是靠js功底,應該能看懂吧?...state是一個語法,意思是把state裡所有的鍵值對列出來,比如說:loading:false,data:"",

再來Store

configure-store.js,大部分是拷貝的,這個可能跟傳統的redux寫法有些不一樣,因為用了redux-thunk,這個的作用上面有說到啦。

import {createStore, applyMiddleware} from 'redux';
import thunkMiddleware from 'redux-thunk';
import rootReducer from '../reducers/index';

const createStoreWithMiddleware = applyMiddleware(thunkMiddleware)(createStore);

export default function configureStore(initialState) {
	const store = createStoreWithMiddleware(rootReducer, initialState);
	return store;
}

上面講到Reducer的索引檔案,在這裡用上了,關聯到Store了。匯入的rootReducer就是我們上面寫得索引。 

成功了一大半了,理解了Redux方面的原理,結合上述程式碼,Redux這塊就簡單入門了。還有什麼沒做呢?寫好Redux部分,就差在頁面上呼叫了。

最後到Page

頁面根目錄Root.js,用react-redux的Provider繫結Store。依舊是拷貝,作用是匯入Store繫結到介面。

import React, {Component} from 'react';
import{} from 'react-native';

import {Provider} from 'react-redux'
import configureStore from './store/configure-store'

import App from './App'

const store = configureStore();

export default class RootApp extends Component {

	render() {
		return (
			<Provider store={store}>
				<App />
			</Provider >
		)
	}
}

根目錄繫結好Store後就可以在子頁面使用了。這裡子頁面的Component匯出的話,需要用react-redux提供的connect匯出。下面詳細解釋繫結資料到子頁面。

為了更好對比setState和dispatch兩種方式改變state,以下TextInput控制元件的程式碼用到了setState,TouchableOpacity控制元件的程式碼用到了dispatch。

Provider包含的根頁面,App.js

import React, {Component} from 'react';
import {
	AppRegistry,
	StyleSheet,
	Text,
	View,
	TouchableOpacity,
	TextInput
} from 'react-native'
import {connect} from 'react-redux';
import {performLoginAction} from './action/LoginAction';

class App extends Component {
	constructor(props) {
		super(props);
		this.state = {
			username: '',
			psw: ''
		};
	}

	render() {
		const {dispatch, login} = this.props;
		return (
			<View style={{flex: 1, justifyContent: 'center'}}>
				<View style={{height: 100, margin: 10}}>
					<View style={{flex: 1}}>
						<TextInput
							style={{fontSize: 20}}
							underlineColorAndroid={'transparent'}
							placeholder={"帳號"}
							onChangeText={(username) => this.setState({username})}
							value={this.state.username}
						/>
					</View>
					<View style={{height: 1, backgroundColor: '#eee'}}/>
					<View style={{flex: 1}}>
						<TextInput
							style={{fontSize: 20}}
							underlineColorAndroid={'transparent'}
							placeholder={"密碼"}
							onChangeText={(psw) => this.setState({psw})}
							value={this.state.psw}
						/>
					</View>
					<View style={{height: 1, backgroundColor: '#eee'}}/>
				</View>
				<View style={{margin: 10, alignItems: 'center'}}>
					<TouchableOpacity onPress={()=> {
						dispatch(performLoginAction(this.state.username, this.state.psw));
					}}>
						<Text style={{fontSize: 30}}>登入</Text>
					</TouchableOpacity>
				</View>
				<View style={{height: 100, margin: 10, justifyContent: 'center', alignItems: 'center'}}>
					<Text style={{height: 30, fontSize: 20, margin: 10}}>{login.data}</Text>
				</View>
			</View>
		)
			;
	}
}
function mapStateToProps(state) {
	const {login} = state;
	return {
		login
	}
}
export default connect(mapStateToProps)(App);


最後一行的connect是在子頁面或者說控制元件吧,進行繫結資料到Store。connect需要mapStateToProps方法返回的一個Reducer,mapStateToProps方法有個引數state,這個是Store統一管理的state,也就是根節點。上面有一個Reducer的索引是login,學了js的這句應該看得懂的,const {login} = state;等於const  login = state.login;

有點感覺吧。。。。。。Reducer的索引就是這樣用的,把每個state區分開來,但是Store又是一個根節點,把所有用索引區分開來的state統一在一個根節點上。

function mapStateToProps(state) {
	const {login} = state;
	return {
		login
	}
}
export default connect(mapStateToProps)(App);
有了connect這一步,

這個頁面或者說控制元件,props屬性裡就有東西拿了。可以獲取dispatch,這個分發器太熟悉了,上面講到爛了。。。。。還有一個login,這個login哪裡來的?就是mapStateToProps方法返回的索引為login的Reducer,Reducer是返回state的,所以有這個引數login,本質上是一個state。這裡頁面的state就是login,login是隻讀的不能寫的,不能用setState去改變它,要用dispatch分發事件(並非state)給Action,Action分發(並非state)給Reducer,Reducer返回state給Store,Store再用新的state替換對應索引的state。

const {dispatch, login} = this.props;

拿到state,是隻讀,直接用就好了,把平時setState的習慣改為dispatch寫。redux就入門了。

簡單介紹了一下React-Native使用了一下Redux。相關原始碼百度搜,很多。。。。。。


相關推薦

react-native使用redux

Redux 是 JavaScript 狀態容器,提供可預測化的狀態管理。 初學這個,覺得網上有些文章並不那麼容易看懂,這裡用淺白的話簡單介紹一下Redux在react-native的使用。 說白了就三個主要東西,Action,Store以及Reducer。 Action:

包學會之出Vue.js:升學篇

css att 初始化 接下來 基本上 dos name return title 上一篇《包學會之淺入淺出Vue.js:開學篇》中,我們初步了解單頁面組件這個概念,現在通過一個項目,來進一步解析組件的應用吧,Go~ 需求背景 組件庫是做UI和前端日常需求中經常用到的,把一

包學會之出Vue.js:結業篇

如何 通過 官方文檔 學習過程 興趣 內容 cloud 實現 項目 在第一篇《包學會之淺入淺出Vue.js:開學篇》和上一篇《包學會之淺入淺出Vue.js:升學篇》的學習中,我們首先了解了Vue環境的搭建以及兩個重要思想——路由和組件的學習,通過組件庫中的按鈕組件和導航組件

react的初步試用

內部 是什麽 why 響應 可見 tar blog 前端框架 如果 現在最熱門的前端框架,毫無疑問是 React 。 上周,基於 React 的 React Native 發布,結果一天之內,就獲得了 5000 顆星,受矚目程度可見一斑。 React 起源於 Faceboo

深出之Java集合框架(上)

不重復 系統 left 子類 log 兩個 示例 c語言 重要 Java中的集合框架(上) 由於Java中的集合框架的內容比較多,在這裏分為三個部分介紹Java的集合框架,內容是從淺到深,如果已經有java基礎的小夥伴可以直接跳到<淺入深出之Java集合框架(下)&

React、Flux 與 Redux

合成 對象 aid -c clas 做的 獲取數據 很難 pro React React 是一個 View 層的框架,用來渲染視圖,它主要做幾件事情: 組件化利用 props 形成單向的數據流根據 state 的變化來更新 view利用虛擬 DOM 來提

深出』MySQL 中事務的實現

一點 隨著 保留 partially 並不會 它的 事件 all previous 在關系型數據庫中,事務的重要性不言而喻,只要對數據庫稍有了解的人都知道事務具有 ACID 四個基本屬性,而我們不知道的可能就是數據庫是如何實現這四個屬性的;在這篇文章中,我們將對事務的實現進

出』MySQL 和 InnoDB

分享圖片 忽略 位置 現在 連續 適合 如果 聚集 快速 作為一名開發人員,在日常的工作中會難以避免地接觸到數據庫,無論是基於文件的 sqlite 還是工程上使用非常廣泛的 MySQL、PostgreSQL,但是一直以來也沒有對數據庫有一個非常清晰並且成體系的認知,所以最近

React世界

style png 一個個 ren 也有 ons 分享圖片 pre html 一: React簡單介紹 React 專註於視圖層,和Angular等框架不同,React並不是完整的MVC/MVVM框架,它專註於提供清晰的簡潔的View(視圖)層解決方案。使用

深詳解獨立ip網站域名惡意解析的解決方案

網站 pos 靜態 tac 規則 來源 代碼 功能 解析 立IP空間的好處想必大家都能耳熟聞詳,穩定性強,利於seo等讓大家選擇了鼎峰網絡香港獨立IP空間。那麽, 網站獨享服務器IP地址,獨立IP空間利於百度收錄和權重的積累、不受牽連、穩定性強等諸多優勢為一身。然而,這些優

react -02

log lte product 出現 handle tex pro 需要 rip if 語句和 for 循環在 JavaScript 中不是表達式,因此它們不能直接在 JSX 中使用,所以你可以將它們放在周圍的代碼中(return裏不能出現for if,在render內 r

出數據結構(24)——最短路徑問題

簡單的 如何 指向 生效 解決 src 簡寫 關鍵字 單源最短路徑   上一篇博文我們提到了圖的最短路徑問題:兩個頂點間的最短路徑該如何尋找?其實這個問題不應該叫“最短”路徑問題,而應該叫“最便宜”路徑問題,因為有時候我們會為圖中的邊賦權(weight),也叫權重,相當於經

出數據結構(25)——最小生成樹問題

相交 其他 無向圖 基本 成本 不存在 自身 技術分享 回顧   上一篇博文我們提到了圖的最短路徑問題:http://www.cnblogs.com/mm93/p/8434056.html。而最短路徑問題可以說是這樣的一個問題:路已經修好了,該怎麽從這兒走到那兒?但是在和圖

【29】Python六個常用模塊

python sys pickle time() 模塊 1.使用copy模塊copy模塊包含了制作對象的拷貝的函數。當寫程序時,有時候你可能需要多個相同的對象。這時候就可以用copy模塊進行拷貝。例如:我們創建一個Ad類,它有一個init函數,參數為name(名字),school_reco

HashMap理解

map map接口 理解 效率 指針 能夠 異常 ont 否則 HashMap不能保證元素的順序,HashMap能夠將鍵設為null,也可以將值設為null,與之對應的是Hashtable,(註意大小寫:不是HashTable),Hashtable不能將鍵和值設為null

JavaScript基礎知識從深理解(一)

isn argument javascrip turn console bom || 將不 函數聲明 JavaScript的簡介   javascript是一門動態弱類型的解釋型編程語言,增強頁面動態效果,實現頁面與用戶之間的實時動態的交互。   javascript是

React

轉化 class string children highlight 語法 ons cli shadows 組件化 組件的封裝 組件的復用 組件的封裝 視圖 數據 視圖和數據之間的變化邏輯 import React, {Component}

React、Vue 部分異步

rip col ets 函數 打印 settime 最終 out con React中的setState setState為什麽需要異步? 無法限制何時使用異步,多次連續使用setState 防止多次渲染,異步rendering不僅僅是性能上的優化,而且這可能是r

出 Android 安全: Android Linux 核心層安全

轉載:https://www.jianshu.com/p/ac84963b9e48   來源:Yury Zhauniarovich | Publications 譯者:飛龍 協議:CC BY-NC-SA 4.0 作為最廣為人知的

出SQL Server 觸發器

什麼是觸發器 簡單的來說,在SQL Server裡面也就是對某一個表的一定的操作,觸發某種條件,從而執行的一段程式。觸發器是一個特殊的儲存過程。 觸發器的建立 常見的觸發器有三種,分別對應於Insert 、Update、Delete事件。 怎麼建立觸發器呢?在牛腩新聞釋出系統