mobx-react 是通過組件將 mobx 和 react 進(jìn)行組合,導(dǎo)出了 observer 和一些開發(fā)工具. 詳細(xì)文檔參考MobX 支持react和 react-native
nstallation
npm install mobx-react --save
Or CDN: https://unpkg.com/mobx-react (namespace: mobxReact)
import {observer} from 'mobx-react';
// - or, for custom renderers without DOM: -
import {observer} from 'mobx-react/custom';
Boilerplate projects that use mobx-react
一些腳手架項(xiàng)目 :
- Minimal MobX, React, ES6, JSX, Hot reloading: MobX-React-Boilerplate
- TodoMVC MobX, React, ES6, JSX, Hot reloading: MobX-React-TodoMVC
- Minimal MobX, React, Typescript, TSX: MobX-React-Typescript-Boilerplate
- Minimal MobX, React, ES6(babel), JSPM with hot reloading modules: jspm-react
- React Native Counter: Mobx-React-Native-Counter
API documentation
observer(componentClass)
observer 是 轉(zhuǎn)換react組件定義的裝飾器, 將 react 組件 或 獨(dú)立渲染的函數(shù) 變成響應(yīng)式組件 , 在 一些可觀察的值發(fā)生變化的時候 ,這個響應(yīng)式組件會 追蹤 render 和 自動 re-render。
// ---- ES5 syntax ----
const TodoView = observer(React.createClass({
displayName: "TodoView",
render() {
return <div>{this.props.todo.title}</div>
}
}));
// ---- ES6 syntax ----
const TodoView = observer(class TodoView extends React.Component {
render() {
return <div>{this.props.todo.title}</div>
}
})
// ---- ESNext syntax with decorators ----
@observer class TodoView extends React.Component {
render() {
return <div>{this.props.todo.title}</div>
}
}
// ---- or just use a stateless component function: ----
const TodoView = observer(({todo}) => <div>{todo.title}</div>)
Observer 在你的組件中提供了一塊匿名區(qū)域,被作為一個唯一的子節(jié)點(diǎn)。在渲染過程中 會被追蹤和自動的重復(fù)渲染 可根據(jù)需要進(jìn)行手動調(diào)節(jié)。
render() {
return (
<div>
手動 {this.props.person.name}
自動 <Observer>
{() => <div>{this.props.person.name}</div>}
</Observer>
</div>
)
}
}
const person = observable({ name: "John" })
React.render(<App person={person} />, document.body)
person.name = "Mike" // will cause the Observer region to re-render
你可以通過 render屬性 或 子節(jié)點(diǎn)(children) 添加 但兩者不能同時存在。
render() {
return (
<div>
{this.props.person.name}
<Observer
render= {() => <div>{this.props.person.name}</div>}
/>
</div>
)
}
}
const person = observable({ name: "John" })
React.render(<App person={person} />, document.body)
person.name = "Mike" // will cause the Observer region to re-render
Observer 可以通過 inject 注入 store
const user = mobx.observable({
name: "Noa"
})
const UserNameDisplayer = ()=>(
<Observer
inject={(stores)=>({user:stores.userStore})}
render={props => (<NameDisplayer name={props.user.name}/>)}
/>
)
const App = () => (
<Provider userStore={user}>
<UserNameDisplayer />
</Provider>
)
如果一個組件拋出error 錯誤打印在控制臺上 沒有造成應(yīng)用crash ,可能會被忽略掉。 所以 mobx-react 提供一個錯誤的鉤子函數(shù) 來制作錯誤收集系統(tǒng)。
import { onError } from "mobx-react";
onError((error) => {
console.log(error);
});
哪些組件應(yīng)該 被標(biāo)記成 observer?
渲染observable data 的組件 應(yīng)該被標(biāo)記成 observer 。
About shouldComponentUpdate
可以設(shè)置自定義的shouldComponentUpdate 但通常應(yīng)該避免這種情況,因?yàn)閙obx 會基于PureRenderMixin 提供高度優(yōu)化的 shouldComponentUpdate的實(shí)現(xiàn)
如果 提供了自定義 shouldComponentUpdate 則在props發(fā)生改變的時候 或 state改變 時 會 咨詢它 但是 如果是一個observable發(fā)生改變 組件將會被re render 不會咨詢 shouldComponentUpdate
從版本4 開始 mobx 不在對 已經(jīng)發(fā)生深刻變化的 non-observable objects 進(jìn)行重新渲染。
componentWillReact(生命周期鉤子)
當(dāng)使用 mobx-react 時,您可以定義一個新的生命周期鉤子,componentWillReact,當(dāng)組件計(jì)劃re-render 時會觸發(fā).
Provider 和 Inject
Provider 是一個組件,可以使用react上下文機(jī)制將store(其他東西)傳遞給子組件。如果你不希望顯示傳遞多層組件 使用provider
inject 可以獲得store 它是一個更高階的組件,它接受一個字符串列表并使這些存儲可用于被包裝的組件。
@inject("color") @observer
class Button extends React.Component {
render() {
return (
<button style={{background: this.props.color}}>
{this.props.children}
</button>
);
}
}
class Message extends React.Component {
render() {
return (
<div>
{this.props.text} <Button>Delete</Button>
</div>
);
}
}
class MessageList extends React.Component {
render() {
const children = this.props.messages.map((message) =>
<Message text={message.text} />
);
return <Provider color="red">
<div>
{children}
</div>
</Provider>;
}
}
componentWillReact 不帶參數(shù)
? componentWillReact 在初始渲染之前不會觸發(fā)(改用 componentWillMount)