react组件通讯的三种方式

89 阅读3分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

一 父组件 → 子组件

父组件传递数据给子组件

import React from "react";
import ReactDOM from "react-dom";

//父组件
class Parent extends React.Component {

 
    state = {
        lastName: "洛"
    }

    render() {
        return (
            <h1>
                父组件:  
                <Child name={this.state.lastName}></Child>
            </h1>
        )
    }
}

//子组件
class Child extends React.Component {
    render() {
        return 
        (<p>
            子组件:          
            <span>{this.props.name}</span>
        </p>)
    }
}


ReactDOM.render(<Parent/>, document.getElementById("root"));

分析

1

子组件模板里有占位符props.name

2

父组件使用了子组件,子组件的属性name的值 就是要替代子组件模板里的占位符props.name的值

但这里子组件的属性name的值不是一个直接的值

而是使用了父组件里的state里的lastName属性的值

3

最后渲染父组件到页面

效果

二 子组件 → 父组件

子组件传递数据给父组件

思路

利用回调函数: 父组件提供回调函数,子组件调用,将要传递的数据作为回调函数的参数

回调函数是什么?

是一个作为参数传递的函数

为什么要使用回调函数?

一个函数的参数如果是函数,这个参数可以传A函数、B函数、C函数

只要改变参数的函数,就可以实现不同的功能,且不需要修改原函数,变的很灵活

代码

import React from "react";
import ReactDOM from "react-dom";

//父组件
class Parent extends React.Component {

    state = {
        parentMsg: ''
    }

    //回调函数.用来接收数据
    //4 执行回调函数,在页面alert
    getChildMsg = (data) => {
        alert("接收到子组件传递过来的数据:" + data)
        this.setState({
                parentMsg: data
            }
        )
    }

    render() {
        return (
            <h1>
                父组件:{this.state.parentMsg}
                {/*子组件的属性是回调函数*/}
                {/*3 回调函数getMsg(msg) → getChildMsg(data)*/}
                <Child getMsg={this.getChildMsg}></Child>
            </h1>
        )
    }
}

//子组件
class Child extends React.Component {

    //组件要传递给父组件的数据
    state = {
        msg: "我的帅爸爸"
    }
    handleClick = () => {
        //2 子组件调用父组件中传递过来的回调函数getMsg(msg),回调函数的参数是 子组件要传递给父组件的数据
        this.props.getMsg(this.state.msg)
    }

    render() {
        return (<p>
            子组件:
            <div>
                {/*1 点击按钮,走handleClick函数*/}
                <button onClick={this.handleClick}>点我</button>
            </div>
        </p>)
    }
}

ReactDOM.render(<Parent/>, document.getElementById("root"));

分析

→ 点击子组件的按钮 → 执行handleClick函数

→ handleClick函数又引发执行另一个函数: 父组件传递过来的回调函数getMsg() 

→ getMsg() 就是 getChildMsg(), 该函数的参数就是子组件要传递给父组件的数据, 这个数据在子组件的state的msg属性里 → alert

效果

 

 总结:

三 兄弟组件通讯

思路

将共享状态提示到最近的公共父组件中,由公共父组件来管理这个状态

核心思想

状态提升

公共父组件职责

1 提供共享状态

2 提供操作共享状态的方法  

代码

import React from "react";
import ReactDOM from "react-dom";

//父组件
class Parent extends React.Component {

    //提供共享状态
    state = {
        score: 0
    }

    //提供操作共享状态的方法
    addScore = () => {
        this.setState({
            score:this.state.score+1
            }
        )
    }

    render() {
        return (
            <h1>
                <Child1 score={this.state.score}/>
                <Child2 addScore={this.addScore}/>
            </h1>
        )
    }
}

//子组件1
class Child1 extends React.Component {
    render() {
        return (<h1>分数:{this.props.score}</h1>)
    }
}

//子组件2
class Child2 extends React.Component {

    render() {
        return (<button onClick={this.props.addScore}>点我加分</button>)
    }
}

ReactDOM.render(<Parent/>, document.getElementById("root"));

分析

有两个子组件child1 、child2

child1里有占位符score

child2里有一个按钮,按钮上有一个动作addScore

父组件使用了这两个子组件child1、child2

child1里的占位符score来源于父组件的state里的score属性的值

child2按钮上的动作addScore来源于父组件的addScore函数,该方法会操作父组件的state里的score属性的值,进而影响child1的score的值

通过共同的父组件,达到兄弟组件child1、child2之间的通讯

效果

点击按钮, 增加分数