• <fieldset id="8imwq"><menu id="8imwq"></menu></fieldset>
  • <bdo id="8imwq"><input id="8imwq"></input></bdo>
    最新文章專題視頻專題問答1問答10問答100問答1000問答2000關鍵字專題1關鍵字專題50關鍵字專題500關鍵字專題1500TAG最新視頻文章推薦1 推薦3 推薦5 推薦7 推薦9 推薦11 推薦13 推薦15 推薦17 推薦19 推薦21 推薦23 推薦25 推薦27 推薦29 推薦31 推薦33 推薦35 推薦37視頻文章20視頻文章30視頻文章40視頻文章50視頻文章60 視頻文章70視頻文章80視頻文章90視頻文章100視頻文章120視頻文章140 視頻2關鍵字專題關鍵字專題tag2tag3文章專題文章專題2文章索引1文章索引2文章索引3文章索引4文章索引5123456789101112131415文章專題3
    問答文章1 問答文章501 問答文章1001 問答文章1501 問答文章2001 問答文章2501 問答文章3001 問答文章3501 問答文章4001 問答文章4501 問答文章5001 問答文章5501 問答文章6001 問答文章6501 問答文章7001 問答文章7501 問答文章8001 問答文章8501 問答文章9001 問答文章9501
    當前位置: 首頁 - 科技 - 知識百科 - 正文

    react+redux的升級版todoList的實現

    來源:懂視網 責編:小采 時間:2020-11-27 22:23:23
    文檔

    react+redux的升級版todoList的實現

    react+redux的升級版todoList的實現:又是很久不寫博客了,最近在用螞蟻金服的ant-design-pro寫畢設,寫著寫著寫不下去了,很多東西都不理解,不得不說大神寫出來的東西都是需要花學習成本的,或者底子好,對于React新手來說就有點難了。所以就老老實實的認真看了下Redux到底如何使用,在這里推薦
    推薦度:
    導讀react+redux的升級版todoList的實現:又是很久不寫博客了,最近在用螞蟻金服的ant-design-pro寫畢設,寫著寫著寫不下去了,很多東西都不理解,不得不說大神寫出來的東西都是需要花學習成本的,或者底子好,對于React新手來說就有點難了。所以就老老實實的認真看了下Redux到底如何使用,在這里推薦

    又是很久不寫博客了,最近在用螞蟻金服的ant-design-pro寫畢設,寫著寫著寫不下去了,很多東西都不理解,不得不說大神寫出來的東西都是需要花學習成本的,或者底子好,對于React新手來說就有點難了。所以就老老實實的認真看了下Redux到底如何使用,在這里推薦一下自己最近在看的書,寫的算是比較詳細的:《深入React技術棧》。廢話不多說,今天就分享下自己如何使用redux來實現一個todoList的,希望對想要用redux的你會有所幫助。

    (為什么叫升級版呢?因為之前寫過一個沒有用redux的todoList)

    該項目使用react官方的create-react-app架構,每個目錄可以根據自己的需求來劃分。下面解釋下每個目錄的內容和功能。

    public:主要放靜態資源(入口html文件,圖片資源,JSON文件等);

    src/component:不同的組件;

    src/layouts:整個頁面的基本架構,主要就是Nav,Footer,Content。Nav里面顯示User和Notice的數據,Content中實現頁面路由的切換,Footer固定不變;

    src/redux:

    --src/redux/configureStore:生成整個應用的store;

    --src/redux/reducers:所有reducer的集合;

    src/routes:頁面的整體路由;

    src/utils:自己封裝的工具;

    views:存放項目中所要展示的所有頁面;

    index:整個項目的入口文件;

    二. 具體實現

    1. 整個應用中store中應存儲什么數據?

    const initialState = {
     taskListData: { //任務列表
     loading: false,
     error: false,
     taskList: [],
     }, 
     userData: { //用戶信息
     loading: false,
     error: false,
     user: {},
     },
     noticeListData: { //通知列表
     loading: false,
     error: false,
     noticeList: [],
     },
     taskData: { //任務詳情,在詳情頁使用
     loading: false,
     error: false,
     task: {},
     }
    };

    2. reducer的分布:

    每個state對應一個reducer,所以一共需要四個reducer,在src/redux/reducers中將所有的reducer合并,并且注意每個reducer的名字要和state同名:

    /*redux/reducers.js*/
    import { combineReducers } from 'redux';
    import userReducer from '../component/User/indexRedux';
    import noticeReducer from '../component/Notice/indexRedux';
    import todoListReducer from '../views/TodoList/indexRedux';
    import taskReducer from '../views/Detail/indexRedux';
    
    export default combineReducers({
     userData: userReducer,
     noticeListData: noticeReducer, 
     taskListData: todoListReducer,
     taskData: taskReducer,
    });
    

    每個state都對應一個reducer,所以和state一樣,reducer應在放在最頂級的父級組件的目錄中,所以將taskListData的reducer放在src/views/TodoList中,其他同理,代碼如下:

    /*views/TodoList/indexRedux.js*/
    const taskListData = {
     loading: true,
     error: false,
     taskList: []
    };
    //不同的action;
    const LOAD_TASKLIST = 'LOAD_TASKLIST';
    const LOAD_TASKLIST_SUCCESS = 'LOAD_TASKLIST_SUCCESS';
    const LOAD_TASKLIST_ERROR = 'LOAD_TASKLIST_ERROR';
    const ADD_TASK = 'ADD_TASK';
    const UPDATE_TASK = 'UPDATE_TASK';
    const DELETE_TASK = 'DELETE_TASK';
    function todoListReducer (state = { taskListData }, action) {
     switch(action.type) {
     case LOAD_TASKLIST: {
     return {
     ...state,
     loading: true,
     error: false,
     }
     }
     case LOAD_TASKLIST_SUCCESS: {
     return {
     ...state,
     loading: false,
     error: false,
     taskList: action.payload,
     };
     }
     case LOAD_TASKLIST_ERROR: {
     return {
     ...state,
     loading: false,
     error: true
     };
     }
     case UPDATE_TASK: {
     const index = state.taskList.indexOf(
     state.taskList.find(task => 
     task.id === action.payload.id));
     console.log(index);
     state.taskList[index].status = !state.taskList[index].status;
     return {
     ...state,
     taskList: state.taskList,
     };
     }
     case DELETE_TASK: {
     const index = state.taskList.indexOf(
     state.taskList.find(task => 
     task.id === action.payload.id));
     state.taskList.splice(index, 1);
     return {
     ...state,
     taskList: state.taskList,
     };
     }
     case ADD_TASK: {
     let len = state.taskList.length;
     let index = len > 0 ? len - 1 : 0;
     let lastTaskId = index !== 0 ? state.taskList[index].id : 0; 
     state.taskList.push({
     id: lastTaskId + 1,
     name: action.payload.name,
     status: false,
     });
     return {
     ...state,
     taskList: state.taskList,
     }
     } 
     default: {
     return state;
     }
     }
    }
    export default todoListReducer;
    

    3. action creator的分布:

    每個動作都代表一個action,action由組件發出,所以將action creator單獨一個文件,放在組件目錄中。例如:ListItem組件的action creator:

    /*ListItem/indexRedux.js*/
    //處理更新任務狀態后和刪除任務后的taskList的狀態;
    const UPDATE_TASK = 'UPDATE_TASK';
    const DELETE_TASK = 'DELETE_TASK';
    //action creator,更新和刪除任務
    export function updateTask (task) {
     return dispatch => {
     dispatch({
     type: UPDATE_TASK,
     payload: task,
     });
     }
    }
    export function deleteTask (task) {
     return dispatch => {
     dispatch({
     type: DELETE_TASK,
     payload: task,
     });
     }
    }
    


    三. 如何將redux和組件連接

    react-redux提供了connect方法,將state和action creator綁在組件上,然后在組價內部以props的方式獲取。下面是TodoList頁面的具體實現:

    import React, { Component } from 'react';
    import { connect } from 'react-redux';
    import { bindActionCreators } from 'redux';
    import List from '../../component/List';
    import { loadTaskList } from '../../component/List/indexRedux';
    import { updateTask, deleteTask } from '../../component/ListItem/indexRedux';
    import { addTask } from '../../component/SubmitDialog/indexRedux';
    class TodoList extends Component {
    
     render () {
     return (
     <List {...this.props} />
     );
     }
    }
    export default connect( state => {
     return {
     loading: state.taskListData.loading,
     error: state.taskListData.error,
     taskList: state.taskListData.taskList,
     };
    }, dispatch => {
     return {
     loadTaskList: bindActionCreators(loadTaskList, dispatch),
     updateTask: bindActionCreators(updateTask, dispatch),
     deleteTask: bindActionCreators(deleteTask, dispatch),
     addTask: bindActionCreators(addTask, dispatch),
     };
    })(TodoList);
    

    connect方法有四個參數,這里主要說下前兩個參數:

    (1)mapStateToProps:參數為state,返回頁面所需要的所有state;

    (2)mapDispatchToProps:參數為dispatch,返回頁面所要使用的異步回調函數。

    眼明手快的你肯定看到了,我們從redux包中導出了bindActionCreators方法,該方法將dispatch和action creator綁定,用來觸發action。

    四. 異步的action creator如何觸發呢?

    因為每個action creator都是異步函數,我們傳給組件的只是函數的聲明,所以就要引入我們的中間件,只用在生成store時加入就行了:

    /*redux/configureStore.js*/
    import { createStore, applyMiddleware } from 'redux';
    import thunk from 'redux-thunk';
    import reducers from './reducers';
    const initialState = {
     taskListData: {
     loading: false,
     error: false,
     taskList: [],
     }, 
     userData: {
     loading: false,
     error: false,
     user: {},
     },
     noticeListData: {
     loading: false,
     error: false,
     noticeList: [],
     },
     taskData: {
     loading: false,
     error: false,
     task: {},
     }
    };
    let enhancer = applyMiddleware(thunk);
    let store = createStore(
     reducers,
     initialState,
     enhancer,
    );
    export default store;
    

    在上面的代碼中thunk就是一個中間件,我們將引入的中間件傳入applyMiddleware就可以了。

    五. store在哪里傳入組件呢?

    我們肯定會想到,store在整個應用中都存在,所以應該在整個應用的最頂層,對于一般項目而言,當然就是最頂端的路由了:

    import React, { Component } from 'react';
    import { BrowserRouter as Router, Route } from 'react-router-dom';
    import { Provider } from 'react-redux';
    import BasicLayout from '../layouts';
    import store from '../redux/configureStore';
    class RouterApp extends Component {
     render () {
     return (
     <Provider store={store}>
     <Router>
     <Route path="/" component={BasicLayout} />
     </Router>
     </Provider>
     );
     }
    }
    export default RouterApp;
    


    Provider是react-redux的一個組件,作用就是用來將store傳入整個應用。

    基本要講的就是這些內容,完整的項目請看 github

    聲明:本網頁內容旨在傳播知識,若有侵權等問題請及時與本網聯系,我們將在第一時間刪除處理。TEL:177 7030 7066 E-MAIL:11247931@qq.com

    文檔

    react+redux的升級版todoList的實現

    react+redux的升級版todoList的實現:又是很久不寫博客了,最近在用螞蟻金服的ant-design-pro寫畢設,寫著寫著寫不下去了,很多東西都不理解,不得不說大神寫出來的東西都是需要花學習成本的,或者底子好,對于React新手來說就有點難了。所以就老老實實的認真看了下Redux到底如何使用,在這里推薦
    推薦度:
    標簽: 實現 升級版 red
    • 熱門焦點

    最新推薦

    猜你喜歡

    熱門推薦

    專題
    Top
    主站蜘蛛池模板: 最新国产乱人伦偷精品免费网站| 孩交VIDEOS精品乱子| 亚洲精品白浆高清久久久久久| 精品国产第1页| 久久精品aⅴ无码中文字字幕重口 久久精品a亚洲国产v高清不卡 | 国产精品毛片久久久久久久| 亚洲愉拍99热成人精品热久久| 好湿好大硬得深一点动态图91精品福利一区二区 | 无码精品人妻一区二区三区免费看 | 亚洲精品无码专区在线播放| 欧美一区二区精品久久| 久久99国产乱子伦精品免费| 亚洲日韩欧美制服精品二区| 精品一区二区三区色花堂| 91国内揄拍国内精品对白不卡| 91精品欧美综合在线观看| 国产精品第12页| 精品国产三级a∨在线欧美| 亚洲国产精品一区二区久久hs| 欧美成人精品欧美一级乱黄一区二区精品在线 | 久久成人国产精品二三区| 国产乱人伦偷精品视频AAA | 精品亚洲一区二区三区在线观看 | 亚洲国产精品久久电影欧美| 无码精品人妻一区| 久久中文精品无码中文字幕| 精品中文高清欧美| 久久精品二区| 久久精品国产色蜜蜜麻豆| 国产亚洲精品线观看动态图| 国产成人精品高清不卡在线| 8050免费午夜一级国产精品| 91精品国产高清久久久久久91| 久久青草国产精品一区| 国产精品久久久久无码av| 九九热这里只有在线精品视 | 影院无码人妻精品一区二区| 亚洲电影日韩精品| 亚洲欧美日韩国产成人精品影院 | 亚洲AV无码精品无码麻豆| 无码人妻精品一区二区三区在线 |