mobx基本使用

来源:互联网 发布:如何升级linux 编译器 编辑:程序博客网 时间:2024/05/21 09:10

mobx是一个简单可扩展的状态管理库

基本概念

  1. state(状态) 状态是驱动应用的数据,像有数据的excel表格

2.derivations(衍生) 任何源自状态并且不会再进一步相互作用的东西。比如用户界面,待办事件的数量,把变化发送到服务端

两种类型的衍生

(1)computed values 是可以使用pure function从state中推导的值,mobx可以自动更新,并且在不在使用时将其优化掉,比如

@computed get completedTodos(){    return this.todos.filter(todo => todo.done)}

(2)reactions很像computed values,会对state的变化做出反应,例如更新UI

const Todos = observer({todos} =>    <ul>        todos.map( todo =>            <li>{todo.title}</li>        )    </ul>)

3.actions动作 动作 是任一一段可以改变状态的代码。用户事件、后端数据推送、预定事件、等等。 动作类似于用户在excel单元格中输入一个新的值。

actions可以改变state,并且是唯一改变state的东西

原则

MobX 支持单向数据流,也就是动作改变状态,而状态的改变会更新所有受影响的视图。

当状态改变时,所有衍生都会进行原子级的自动更新,不能观测到中间值。

所有衍生默认的都是同步更新。动作可以在改变状态之后直接安全的检查计算值???

计算值是延迟更新的,不使用的计算值不更新,直到使用时。

所有的计算值都是纯净的,不应该用来改变state


mobx工作流程




事件调用actions,actions可以改变state,并且唯一能改变state的就是action

@action onClick = () => {    this.props.todo.done = true;}

state是可观察的,并且不包含冗余的数据

@observable todos = [{    title: 'learn mobx',    done: false}]

computed values 是可以使用pure function从state中推导的值,mobx可以自动更新,并且在不在使用时将其优化掉

@computed get completedTodos(){    return this.todos.filter(todo => todo.done)}

reactions很像computed values,会对state的变化做出反应,例如更新UI

const Todos = observer({todos} =>    <ul>        todos.map( todo =>            <li>{todo.title}</li>        )    </ul>)

一个例子

1.定义状态并使其可观察

所有改变的属性打上,mobx的标记使其变得可观察。

import {observable} from 'mobx';var appState = observable({    timer:0});

2.创建视图以响应状态的变化

创建视图,在appState中相关数据发生改变时视图会自动更新。

import {observer} from 'mobx-react';@observerclass TimerView extends React.Component{    render(){        return (<button onClick={this.onReset.bind(this)}>          Seconds passed: {this.props.appState.timer}</button>);    }    onReset () {        this.props.appState.resetTimer();    }};ReactDOM.render(<TimerView appState={appState} />,document.body);

定义一个按钮,显示timer,当点击这个按钮时,调用reset函数,重置时间。

3.更改状态

每秒都修改数据,当需要的时候UI自动更新

appState.resetTimer = action(function reset(){    appState.timer = 0;});setInterval(action(function tick(){    appState.timer +=1;}),1000);

API

1.observable 用法:

--observable(value)--@observable classProperty = value

Observable 值可以是JS基本数据类型、引用类型、普通对象、类实例、数组和映射

const list = observable([1, 2, 4]);list[2] = 3;

@observable装饰器可以在 ES7 或者 TypeScript 类属性中属性使用,将其转换成可观察的。

import { observable, computed } from "mobx";class OrderLine {    @observable price = 0;    @observable amount = 1;    @computed get total() {        return this.price * this.amount;    }}

2.computed

计算值(computed values)是可以根据现有的状态或其它计算值衍生出的值。计算值还是高度优化过的,所以尽可能的多使用它们。

import {observable, computed} from "mobx";class OrderLine {    @observable price = 0;    @observable amount = 1;    constructor(price) {        this.price = price;    }    @computed get total() {        return this.price * this.amount;    }}

计算值的 setter

还可以为计算值定义 setter。注意这些 setters 不能用来直接改变计算属性的值,但是它们可以用来作“逆向”衍生。

注意永远在 getter 之后 定义 setter
class Foo {    @observable length = 2;    @computed get squared() {        return this.length * this.length;    }    set squared(value) { // 这是一个自动的动作,不需要注解        this.length = Math.sqrt(value);    }}

(暂时没有用到过,不知道用来干什么需要使用)

3.autorun

当你需要从反应式代码桥接到命令式代码的情况,例如打印日志、持久化或者更新UI的代码,应该使用autorun

当使用 autorun 时,所提供的函数总是立即被触发一次,然后每次它的依赖关系改变时会再次被触发

var numbers = observable([1,2,3]);var sum = computed(() => numbers.reduce((a, b) => a + b, 0));var disposer = autorun(() => console.log(sum.get()));// 输出 '6'numbers.push(4);// 输出 '10'
  1. action

动作是任何用来修改状态的东西

action.bound 来自动地将动作绑定到目标对象

class Ticker {    @observable tick = 0    @action.bound    increment() {        this.tick++ // 'this' 永远都是正确的    }}const ticker = new Ticker()setInterval(ticker.increment, 1000)
注意: action.bound 不要和箭头函数一起使用;箭头函数已经是绑定过的并且不能重新绑定。
runInAction

runInAction 是个简单的工具函数,它接收代码块并在(异步的)动作中执行。这对于即时创建和执行动作非常有用,例如在异步过程中。

如果你使用async function来处理业务,需要使用runInAction。

computed 和 autorun

它们都是响应式调用的表达式,但是,如果你想响应式的产生一个可以被其它 observer 使用的值,请使用 @computed.

使用 autorun达到某种效果,比如像打印日志、发起网络请求等



原创粉丝点击