context

定义: Context提供了一种方式,能够让数据在组件树中传递,而不必一级一级手动传递。

API : createContext(defaultValue?)。

使用方法:

首先要引入createContext

import React, { Component, createContext } from 'react';

然后创建一个Context

const BatteryContext = createContext();

然后用BatteryContext.Provider包裹组件并且传递属性值。

<BatteryContext.Provider value={60}>
<Middle />  //子组件
</BatteryContext.Provider>

为了方便看出效果,将定义一个子组件和一个孙组件。然后不通过子组件,孙组件直接取值。

import React, { Component, createContext } from 'react';

const BatteryContext = createContext();

//声明一个孙组件
class Leaf extends Component {
render() {
return ( )
}
} //声明一个子组件
class Middle extends Component {
render() {
return <Leaf />
}
} class App extends Component {
render(){
return (
<BatteryContext.Provider value={60}>
<Middle />
</BatteryContext.Provider>
);
}
} export default App;

孙组件需要BatteryContext.Consumer来接收值,Consumer里面不能直接渲染其他组件,而是要声明一个函数。函数的参数就是context的值。

class Leaf extends Component {
render() {
return (
<BatteryContext.Consumer>
{
battery => <h1>Battery : {battery}</h1>
}
</BatteryContext.Consumer>
)
}
}

效果图;

这样没通过Middle组件来传递值,但是Leaf组件能通过context来获得属性。这就是context的基本用法。

context不但能跨层级来传递属性值,还能在属性值发生变化的时候重渲染Consumer下面的元素,举个例子:
 
在state中定义battery并赋值
state = {
battery: 60
}
然后做一个按钮,每次点击的时候都要battery减一。  代码:
render() {
const { battery } = this.state;
return (
<BatteryContext.Provider value={battery}>
<button
type="button"
onClick={() => this.setState({ battery: battery - 1 })}
>
减减
</button>
<Middle />
</BatteryContext.Provider>
);
}
全部代码:
import React, { Component, createContext } from 'react';

const BatteryContext = createContext();

//声明一个孙组件
class Leaf extends Component {
render() {
return (
<BatteryContext.Consumer>
{
battery => <h1>Battery : {battery}</h1>
}
</BatteryContext.Consumer>
)
}
} //声明一个子组件
class Middle extends Component {
render() {
return <Leaf />
}
} class App extends Component {
state = {
battery: 60
}
render() {
const { battery } = this.state;
return (
<BatteryContext.Provider value={battery}>
<button
type="button"
onClick={() => this.setState({ battery: battery - 1 })}
>
减减
</button>
<Middle />
</BatteryContext.Provider>
);
} } export default App;

效果图:

这样每次点击都会使battery得数值发生变化,从而重渲染Consumer下面的元素。

如果有多个Context该怎么做呢?我们在创建一个 Context
const OnLineContext = createContext();
如果有多个context变量的话,只需要把Privider嵌套进来即可,顺序不重要。接下来声明online的Provider了。
class App extends Component {
state = {
battery: 60,
online: false
}
render() {
const { battery, online } = this.state;
return (
<BatteryContext.Provider value={battery}>
<OnLineContext.Provider value={online} >
<button
type="button"
onClick={() => this.setState({ battery: battery - 1 })}
>
减减
</button>
<button
type="button"
onClick={() => this.setState({ online: !online })}
>
Switch
</button>
<Middle />
</OnLineContext.Provider>
</BatteryContext.Provider>
);
}
与Provider类似。Consumer也需要嵌套,顺序不重要。只要Consumer需要声明函数,所以要注意语法。
class Leaf extends Component {
render() {
return (
<BatteryContext.Consumer>
{
battery => (
<OnLineContext.Consumer>
{
online => <h1>Battery : {battery} , Online : {online.toString()}</h1>
}
</OnLineContext.Consumer>
)
}
</BatteryContext.Consumer>
)
}
}

全部代码:

import React, { Component, createContext } from 'react';

const BatteryContext = createContext();
const OnLineContext = createContext(); //声明一个孙组件
class Leaf extends Component {
render() {
return (
//与Provider类似。Consumer也需要嵌套,顺序不重要。只要Consumer需要声明函数,所以要注意语法。
<BatteryContext.Consumer>
{
battery => (
<OnLineContext.Consumer>
{
online => <h1>Battery : {battery} , Online : {online.toString()}</h1>
}
</OnLineContext.Consumer>
)
}
</BatteryContext.Consumer>
)
}
} //声明一个子组件
class Middle extends Component {
render() {
return <Leaf />
}
} class App extends Component {
state = {
battery: 60,
online: false
}
render() {
const { battery, online } = this.state;
//接下来声明online的Provider了。如果有多个context变量的话,只需要把Privider嵌套进来即可,顺序不重要。
return (
<BatteryContext.Provider value={battery}>
<OnLineContext.Provider value={online} >
<button
type="button"
onClick={() => this.setState({ battery: battery - 1 })}
>
减减
</button>
<button
type="button"
onClick={() => this.setState({ online: !online })}
>
Switch
</button>
<Middle />
</OnLineContext.Provider>
</BatteryContext.Provider>
);
} } export default App;

效果图:

还有一个问题 , 如果Consumer向上找不到对应的Provider怎么办?
 
其实即使找不到也不会报错,而是显示为空。那怎么设置默认值呢?
 
那上面的demo举例 ,刚才我们设置的battery为60。如果Consumer向上找不到BatteryContext.Provider的值,我们可以这样设置默认值:
const BatteryContext = createContext(30);
这样BatteryContext.Consumer向上找不到值,就会取默认值30。
context不仅仅只是可以传数值,也可以传函数。大家可以试试看。
最后再提示一下大家,不要滥用context,不然会影响组件的独立性。 如果一个组件中只使用一个Context的话,就可以使用contextType代替Consumer。详见https://www.cnblogs.com/littleSpill/p/11221817.html
 
 
 

React的Context的使用方法简介的更多相关文章

  1. React的contextType的使用方法简介

    上一篇介绍了Context的使用方法.但是Context会让组件变得不纯粹,因为依赖了全局变量.所以这决定了Context一般不会大规模的使用.所以一般在一个组件中使用一个Context就好. 由于C ...

  2. iOS中常用的四种数据持久化方法简介

    iOS中常用的四种数据持久化方法简介 iOS中的数据持久化方式,基本上有以下四种:属性列表.对象归档.SQLite3和Core Data 1.属性列表涉及到的主要类:NSUserDefaults,一般 ...

  3. 手写一个React-Redux,玩转React的Context API

    上一篇文章我们手写了一个Redux,但是单纯的Redux只是一个状态机,是没有UI呈现的,所以一般我们使用的时候都会配合一个UI库,比如在React中使用Redux就会用到React-Redux这个库 ...

  4. 网络神器Greasemonkey(油猴子)使用方法简介+脚本分享【转载】

    推荐下,觉得这个方法有用, 今天艾薇百科来介绍一下功能强大的Greasemonkey,俗称"油猴子",Greasemonkey可以自由定制网页,实现你想要的各种功能.堪称" ...

  5. Redis Cluster搭建方法简介22211111

    Redis Cluster搭建方法简介 (2013-05-29 17:08:57) 转载▼       Redis Cluster即Redis的分布式版本,将是Redis继支持Lua脚本之后的又一重磅 ...

  6. Monte Carlo方法简介(转载)

    Monte Carlo方法简介(转载)       今天向大家介绍一下我现在主要做的这个东东. Monte Carlo方法又称为随机抽样技巧或统计实验方法,属于计算数学的一个分支,它是在上世纪四十年代 ...

  7. C#——Marshal.StructureToPtr方法简介

    目录 MarshalStructureToPtr方法简介 功能及位置 语法 参数说明 异常 备注 举例 本博客(http://blog.csdn.net/livelylittlefish)贴出作者(三 ...

  8. Fatal error: Using $this when not in object context in 解决方法

    Fatal error: Using $this when not in object context in 解决方法 粗心造成的错误 $this 只存在于下面情况 $obj = new object ...

  9. TabBarController创建及使用方法简介

    TabBarController创建及使用方法简介 大致讲解一下TabBarController的创建过程: 首先,我们需要一些视图,如创建UIControllerView类型的view1,view2 ...

随机推荐

  1. MySQLNonTransientConnectionException: Data source rejected establishment of connection, message from server: "Too many connections"

    com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException: Data source rejected establish ...

  2. html5创建的sqlite存放为止以及在手机中的位置

    C:\Users\xiaoai\AppData\Local\Google\Chrome\User Data\Default\databases\http_127.0.0.1_8020 如图:这是用bh ...

  3. Qt 不规则窗体 – 鼠标点击穿透(Linux也可以,有对x11的配置的方法)

    之前写过如何用 Qt 现成的方法写出无边框半透明的不规则窗体:<Qt 不规则窗体 – 无边框半透明> 其实有一个很特殊的窗体属性一直以来都伴随着不规则窗体出现,这就是本文要介绍的鼠标点击穿 ...

  4. Zookeeper详解-工作流和leader选举(三)

    一.工作流 一旦ZooKeeper集合启动,它将等待客户端连接.客户端将连接到ZooKeeper集合中的一个节点.它可以是leader或follower节点.一旦客户端被连接,节点将向特定客户端分配会 ...

  5. kafka 名词概念

    ProducerConsumerBrokerTopicPartitionConsumer Group分布式 Broker     Kafka集群包含一个或多个服务器,这种服务器被称为brokerTop ...

  6. shell脚本开发基本规范

    当你的才华还撑不起你的野心的时候,你就应该静下心来学习.当你的能力还驾驭不了你的目标的时候,你就应该沉下心来历练.问问自己,想要怎样的人生. 欢迎加入 基础架构自动化运维:598432640,大数据S ...

  7. 浅谈Linq查询

    一.Var关键字 在学习Linq查询之前,我们先来学习var关键字的用法,看看微软官方的定义:从Visual C#3.0开始,在方法范围声明的变量可以具有隐式“类型” var.隐式类型的局部变量是强类 ...

  8. 第一个SpringBoot

    Spring Boot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配置.用我 ...

  9. Flink中的状态与容错

    1.概述 Flink支持有状态计算,根据支持得不同状态类型,分别有Keyed State和Operator State.针对状态数据得持久化,Flink提供了Checkpoint机制处理:针对状态数据 ...

  10. Flutter学习笔记(3)--Dart变量与基本数据类型

    一.变量 在Dart里面,变量的声明使用var.Object或Dynamic关键字,如下所示: var name = ‘张三’: 在Dart语言里一切皆为对象,所以如果没有将变量初始化,那么它的默认值 ...