前言
注意: 从
React v15.5
开始 ,React.PropTypes 助手函数
已被弃用,我们建议使用prop-types 库
来定义contextTypes
。
首先你需要通过在终端npm install prop-types
安装一个叫prop-types的第三方包
context分为新版后旧版,这里都介绍下
一 context旧版使用步骤
1.1 根组件childContextTypes属性
定义静态属性
getChildContext 指定的传递给子组件的属性需要先通过 childContextTypes 来指定,不然会产生错误
// 声明Context对象属性
static childContextTypes = {
propA: PropTypes.string,
visibleA:PropTypes.string,
methodA: PropTypes.func
}
1.2 根组件getChildContext方法
返回context对象, 指定子组件可以使用的信息
// 返回Context对象,方法名是约定好的
getChildContext () {
return {
propA: this.state.propA,
methodA: this.changeStateByChildren
}
}
注意:如果context的值是动态的采用state管理,更改某个context值时,改变根组件的state
1.3 子组件contextTypes静态属性
调用context先定义静态属性,根据约定好的参数类型,否则会出现未定义
子组件需要通过 contextTypes
指定需要访问的元素。 contextTypes 没有定义, context 将是一个空对象。
static contextTypes = {
propA: PropTypes.string,
methodA:PropTypes.func
}
1.4 下文改变context的值,通过context的函数去改变根组件的状态即可
新版context的使用步骤和方法:更好的解释了生产者和消费者模式
1.5 例子
父组件Greeter
class Greeter extends Component {
constructor(props) {
super(props);
this.state = {
add: 87,
remove: 88,
};
}
static childContextTypes = {
add: PropTypes.number,
remove: PropTypes.number,
}
getChildContext() {
const { add, remove } = this.state;
return {
add,
remove,
};
}
render() {
return (
<div>
<ComponetReflux />
</div>
);
}
}
子组件ComponetReflux
class ComponetReflux extends Component {
constructor(props) {
super(props);
this.state = {
};
}
static contextTypes = {
add: PropTypes.number,
remove: PropTypes.number,
}
render() {
console.log(this.context); // 打印{add:87,remove:88}
const { name, age } = this.state;
return (
<div>测试context</div>
);
}
}
二 新版context的使用步骤和方法
更好的解释了生产者和消费者模式
2.1 先定义全局context对象
import React from 'react'
const GlobalContext = React.createContext()
export default GlobalContext
2.2 根组件引入GlobalContext,并使用GlobalContext.Provider(生产者)
<GlobalContext.Provider
value={{
background: 'green',
color: 'white',
content:this.state.content,
methodA:this.changeStateByChildren
}}
/>
注意:传入的value为根context对象的值,如果是动态的,使用状态管理
2.3 子组件引入GlobalContext并调用context,使用GlobalContext.Consumer(消费者)
<GlobalContext.Consumer>
{
context => {
return (
<div>
<h1 style={{background: context.background, color: context.color}}>
{context.content}
</h1>
<Input methodA = {context.methodA} value={context.content}></Input>
</div>
)
}
}
</GlobalContext.Consumer>
注意:GlobalContext.Consumer内必须是回调函数
,改变context,通过context方法改变根组件状态
三 context优缺点:
优点:跨组件访问数据
缺点:react组件树种某个上级组件shouldComponetUpdate 返回false,当context更新时,不会引起下级组件更新