使用mobx入门
mobx是和redux,vuex一样的状态管理工具,但是mobx更接近于面向对象的风格相比redux更易懂(个人觉得)
本代码介绍了函数组件和class组件的两种写法,大概代码如下:
第一步需要安如下插件:
mobx
mobx-react
react-app-rewired或者@craco/craco
个人觉得克拉克好像更好用一点,更贴近于vue.config.js的写法
第二步,建立store,如圖:
其中store是一些action就是處理數據的一些方法,entity就是數據的實體,以user为例代码如下:
entity.js
//store的类,要声明一下字段的类型 export const UserInfo = { name:String, password:String }
store:
import { action, makeObservable, observable } from "mobx"; class userMobx { constructor() { makeObservable(this); } //默认属性值 @observable userInfo = {}; //箭头函数确保this 指向不变,不使用箭头函数在函数组件可能会出现this是undefined的情况 @action setUserInfo=(info)=> { //修改后会存入mobx的状态中 this.userInfo = info; } } export default new userMobx();
mobx的store:
import userMobx from "./User/store"; import accountMobx from './Account/store' const store = { userMobx, accountMobx }; export default store;
然后再index.js中注入
import React from 'react'; import ReactDOM from 'react-dom'; import {Provider} from 'mobx-react' import './index.css'; import App from './App'; import store from './Mobx/index' ReactDOM.render( // <React.StrictMode> <Provider {...store}> <App /> </Provider>, // </React.StrictMode>, document.getElementById('root') );
最后可以运行的完整例子:
import React, { useState } from "react"; import { inject, observer } from "mobx-react"; function Test(props) { const [user, setUser] = useState({ name: "张三", age: 18, sex: "男" }); const modifyUserInfo = () => { const {userMobx:{setUserInfo}} =props setUserInfo(user) }; const setUserState = (key, val) => { let obj = { ...user, [key]: val.target.value, }; setUser(obj); }; const { userMobx: { userInfo }, } = props; return ( <> <div> <div>用户原信息:</div> <ul> <li> <span>姓名:</span> <span>{userInfo.name}</span> </li> <li> <span>年龄:</span> <span>{userInfo.age}</span> </li> <li> <span>性别:</span> <span>{userInfo.sex}</span> </li> </ul> </div> <div> <div>要修改的信息:</div> <ul> <li> <span>姓名:</span> <span> <input type="text" value={user.name} onChange={(val) => setUserState("name", val)} /> </span> </li> <li> <span>年龄:</span> <input type="text" value={user.age} onChange={(val) => setUserState("age", val)} /> </li> <li> <span>性别:</span> <input type="text" value={user.sex} onChange={(val) => setUserState("sex", val)} /> </li> </ul> <button onClick={modifyUserInfo}>修改信息</button> </div> </> ); } /** * 函数组件不可以写注解的方式,可以使用如下写法注入store,只有一个的时候也可以使用inject("store的名字")这样的字符串写法 * 使用类的写法时,可以用装饰器的写法进行如下格式的书写 * @inject('store')//这里是注入 Provider store={userStore}中的那个store * 參數也可以使用方法返回一个json * @observer * class Test1 extends React.Component {...} */ export default inject(store=>{ return { userMobx:store.userMobx, accountMobx:store.accountMobx } })(observer(Test));
这里要注意的是react目前不支持装饰器(JAVA叫注解,C#叫序列化标记)的语法,所以要是用
react-app-rewired
或者克拉克.js
这里对两个分别做一下简要说明,克拉克:
新建一个
craco.config.js
然后加入如下代码:
module.exports = { babel: { //用来支持装饰器 plugins: [["@babel/plugin-proposal-decorators", { legacy: true }]], }, };
其中
@babel/plugin-proposal-decorators
需要安装,
package.json要换成如下的配置:
"scripts": { "start": "craco start", "build": "craco build", "test": "craco test", "eject": "react-scripts eject" },
react-app-rewired:
新建 config-overrides.js
然后加入如下代码:
const { override, addDecoratorsLegacy } = require('customize-cra')
module.exports = override(addDecoratorsLegacy()),
其中
customize-cra
需要安装
积累小的知识,才能成就大的智慧,希望网上少一些复制多一些原创有用的答案