這個項目是第一次使用Redux的實例,並不具備專業性的理論知識。純粹分享一次開發過程與心得。以前寫了一篇沒有加入Redux的React Native ToDoList的小博文。這個項目也是在原來的基礎上進行裝修完成的。目的是爲了體驗一下高深莫測的Redux。
總之,在各位網友的友情支持下,我依然沒有看懂redux數據流的走向,勉勉強強通了一點。react
根據本身的習慣和固定套路,拆分目錄結構和組件結構。git
├── public ├── todos-redux │ ├── actions │ │ └── index.js │ ├── components │ │ ├── todoItem.js │ │ └── todoList.js │ ├── containers │ │ ├── add.js │ │ ├── all.js │ │ ├── completed.js │ │ └── incomplete.js │ ├── reducers │ │ ├── index.js │ │ └── todos.js │ ├── store │ │ └── configureStore.js │ ├── utils │ │ └── utils.js │ ├── index.js │ ├── router.js
把react-navigation的導航組件集中放在router.js純粹是我的習慣。
components中的組件是展現組件,不直接使用Redux。而containers中的是直接使用 Redux的組件。在這裏能夠當作components是containers的子組件。github
redux-persist是用來作redux的數據持久化。使用方法直接參考在GitHub上的基本示例。這裏的代碼基本上都是固定套路。redux
// index.js import React, {Component} from 'react' import { Provider } from 'react-redux' import { TodosReduxStack } from './router' import { PersistGate } from 'redux-persist/integration/react' import configureStore from './store/configureStore' const { persistor, store } = configureStore() export default class TodolistRedux extends Component { render(){ return ( <Provider store={store}> <PersistGate loading={null} persistor={persistor}> <TodosReduxStack /> </PersistGate> </Provider> ) } }
// action/index.js import Utils from '../utils/utils' export const addTodo = (text) => { return { type: 'ADD_TODO', id: Utils.uniqueId(), content: text } } export const toggleTodo = (id) => { return{ type:'TOGGLE_TODO', id } }
// reducers/todos.js var initState = []; const todos = (state = initState, action)=>{ switch(action.type){ case 'ADD_TODO': return[ ...state, { id: action.id, content: action.content, completed: false } ] case 'TOGGLE_TODO': return state.map((t) => { if (t.id !== action.id) { return t } return Object.assign({},t,{completed:!t.completed}) }) default: return state } } export default todos
connect()() 這個寫法叫函數的柯里化,漲知識啦。segmentfault
// containers/all.js const mapStateToprops = (state) => { return { todos: state.todos } } const mapDispatchToProps = (dispatch) =>{ return { onTodoClick: (id) => { dispatch(toggleTodo(id)) } } } export default connect(mapStateToprops, mapDispatchToProps)(AllScreen)
使用filter函數過濾數組,返回指定的值,這個地方有點雞肋哈,可是我不會其餘的寫法了。數組
// containers/completed.js const mapStateToprops = (state) => { return { todos: state.todos.filter(t => t.completed) } }
沒有使用Redux以前,項目使用了React Native內置的DeviceEventEmitter方法。添加事項後要通知其餘組件更新數據。還大量使用了AsyncStorage作數據的持久化,每一次的數據更新都須要用到它。若是是在稍複雜的項目中這樣寫,會死翹翹的!使用Redux 和 redux-persist 能夠輕鬆實現這個功能,效果是明顯的。在已完成頁面將事項切換爲未完成,該事項會直接消失,跑到未完成頁面中,這個地方並不須要作額外的處理。ide
這種連個圖都沒有也沒有深刻講解redux的文字都敢發出來,真的是表臉 (手動滑稽)。
完整的項目在這裏GitHub Todos Redux。函數