前言
之前簡單的寫了對antd-pro的構建以及運行,並未對antd-pro等進行過多的描述,也不打算,畢竟官網會給出答案,個人奉承‘洞其萬理,致之一用’,接下來就大概的講解怎麼更好的使用umi/dva/antd的特色
序言
在一個項目中,狀態管理始終是最重要的,如同面試時候,vuex/react-redux/redux三者是必定問及的。而在單頁面應用中,狀態管理也是必須的,所以,我們也有必要學會使用dva
正文
改造一個空白的頁面
爲了不浪費篇幅去寫如何在antd中創建一個新的頁面,因爲個人感覺這個是比較方便的,
不太需要花費篇幅去描述,或則在後期,再寫一個博客去描述,
所以直接改動下面的文件夾中的文件
import { connect } from 'dva';
import { Button } from 'antd'
import React from 'react';
/*
點擊事件
*/
const TableList = props => {
const handleClick = async () => {
const { dispatch } = props;
dispatch({
type: 'test/effectTime'
})
}
const {
name, time
} = props;
return (
<div>
<div>用戶名:{name}</div>
<div>當前時間:{time}</div>
<Button type='primary' onClick={() => { handleClick() }}>更新當前時間</Button>
</div>
);
};
export default connect(({ test }) => ({
time: test.time,
name: test.name
}))(TableList);
修改model/xxx.js文件
這回爲了不影響原有的功能,直接在所示的地方創建了一個test的文件,顧名思義是測試的
const test = {
namespace: 'test',
state: {
time: +new Date(),
name: 'mkmin'
},
reducers: {
reducerTime(state, action) {
const { time } = action.payload;
return { ...state, time }
}
},
effects: {
*effectTime(_, { call, put }) {
const time = yield call(getnumber);
yield put({
type: 'reducerTime',
payload: {
time
}
})
}
},
subscriptions: {
changeTime({ dispatch, history }) { // 這裏的方法名可以隨便命名,當監聽有變化的時候就會依次執行這的變化,
window.onclick = () => {
console.log("頁面被點擊了");
}
},
}
}
export default test;
async function getnumber() {
return new Promise((resolve) => {
setTimeout(() => {
resolve(+new Date());
}, 3000);
})
}
效果
先給各位大佬看完頁面的效果再仔細的去描述
流程解說
1.搭建一個簡單至極的靜態頁面,使用hook+js的寫法
import { Button } from 'antd'
import React, { useState } from 'react';
/*
點擊事件
*/
const TableList = props => {
const [time] = useState(+new Date())
const [name] = useState('mkmin');
const handleClick = async () => {
}
return (
<div>
<div>用戶名:{name}</div>
<div>當前時間:{time}</div>
<Button type='primary' onClick={() => { handleClick() }}>更新當前時間</Button>
</div>
);
};
export default TableList;
2.構建我們的dva文件,並且綁定到component上去
component文件
import { connect } from 'dva';
import { Button } from 'antd'
import React from 'react';
/*
點擊事件
*/
const TableList = props => {
const handleClick = async () => {
}
const {
name, time
} = props;
return (
<div>
<div>用戶名:{name}</div>
<div>當前時間:{time}</div>
<Button type='primary' onClick={() => { handleClick() }}>更新當前時間</Button>
</div>
);
};
export default connect(({ test }) => ({
time: test.time,
name: test.name
}))(TableList);
model/xxx.js文件
const test = {
namespace: 'test',
state: {
time: +new Date(),
name: 'mkmin'
},
}
export default test;
3.在model/xxx文件中添加reducers以及effects,並且在component上觸發
model/xxx.js
const test = {
namespace: 'test',
state: {
time: +new Date(),
name: 'mkmin'
},
reducers: {
reducerTime(state, action) {
const { time } = action.payload;
return { ...state, time }
}
},
effects: {
*effectTime(_, { call, put }) {
const time = yield call(getnumber);
yield put({
type: 'reducerTime',
payload: {
time
}
})
}
},
}
export default test;
async function getnumber() {
return new Promise(resolve => {
setTimeout(() => {
resolve(+new Date());
}, 3000);
})
}
component.jsx
import { connect } from 'dva';
import { Button } from 'antd'
import React from 'react';
/*
點擊事件
*/
const TableList = props => {
const handleClick = async () => {
const { dispatch } = props;
dispatch({
type: 'test/effectTime'
})
}
const {
name, time
} = props;
return (
<div>
<div>用戶名:{name}</div>
<div>當前時間:{time}</div>
<Button type='primary' onClick={() => { handleClick() }}>更新當前時間</Button>
</div>
);
};
export default connect(({ test }) => ({
time: test.time,
name: test.name
}))(TableList);
4.model/xxx.js中添加訂閱事件
const test = {
namespace: 'test',
state: {
time: +new Date(),
name: 'mkmin'
},
reducers: {
reducerTime(state, action) {
const { time } = action.payload;
return { ...state, time }
}
},
effects: {
*effectTime(_, { call, put }) {
const time = yield call(getnumber);
yield put({
type: 'reducerTime',
payload: {
time
}
})
}
},
subscriptions: {
changeTime({ dispatch, history }) { // 這裏的方法名可以隨便命名,當監聽有變化的時候就會依次執行這的變化,
window.onclick = () => {
console.log("頁面被點擊了");
}
},
}
}
export default test;
async function getnumber() {
return new Promise((resolve) => {
setTimeout(() => {
resolve(+new Date());
}, 3000);
})
}
備註
1.在model/xxx.js中,reducer常用於更改我們的state,
2.在model/xxx.js中,effects用於異步操作,比如代碼中寫的異步返回(模擬調用接口)
3.在頁面中用connect去與models/xxx.js產生關係
4.將modes/xxx.js中的state放置在頁面上的方法與redux差不多,
5.多看文檔!!!!!多做測試!!!!
dva模塊解說
namespace
namespace 是 model state 在全局 state 所用的 key
state
state是默認數據
reducer
reducer 是唯一可以更新 state 的地方,是一個純函數,接收參數 state 和 action,返回新的 state,基本是在effects中調用
reducers:{
minus(state) {
return { ...state, current: state.current - 1};
}
}
connect
function mapStateToProps(state) {
return { count: state.count };
}
const HomePage = connect(mapStateToProps)(CountApp);
effects
異步請求
effects: {
*add(action, { call, put }) {
yield call(delay, 1000);//調用另外的effects
yield put({ type: 'minus' });//調用另外的reducer
},
},
在component中去觸發
this.props.dispatch({ type: 'count/add1' });
subscriptions
訂閱事件
setup({ dispatch, history }) { // 這裏的方法名可以隨便命名,當監聽有變化的時候就會依次執行這的變化,
window.onresize = () => { //頁面上觸發onsize方法的時候回觸發這個事件,
dispatch (type:"save")
}
},
後
多看文檔!!!!!!這個只是簡單的demo!!!!!!!