react (组件通信,生命周期和非受控组件)

组件通信

父传子

案例:父组件发送数据,子组件接收并渲染
父组件 App.js

import React, { Component } from 'react'
import FriendList from './FriendList'

class App extends Component {
  state = {
    name: '张三'
  }
  render() {
    return (<div>
      <FriendList
        name={this.state.name}
      />
    </div>)
  }
}
export default App

子组件 FriendList.js

import {Component} from 'react'
export default class FriendList extends Component{
    render(){
        console.log(this.props);
        return (
            <div>
                {this.props.name}
          </div>
      );
    }
}

子传父

案例:子组件通过props属性获取父组件的change方法,并将this.state值传递过去
子组件 FriendList.js

import {Component} from 'react'
export default class FriendList extends Component{
    childeChange=(newName)=>{
        this.props.change(newName)
    }
    render(){
        return (
            <div>
                {<button onClick={()=>{this.childeChange('子组件数据')}}>
                点击
                </button>}
          </div>
      );
    }
}

父组件 App.js

import React, { Component } from 'react'
import FriendList from './FriendList'

class App extends Component {
  state = {
    name: '张三'
  }
  change = (newName) => {
    this.setState({ name: newName })
  }
  render() {

    return (<div>
      <p>{this.state.name}</p>
      <FriendList
        name={this.state.name}
        change={this.change}
      />
    </div>)
  }
}
export default App

兄弟传值

兄弟组件之间的传值,是通过父组件做的中转 ,流程为:
组件A – 传值 --> 父组件 – 传值 --> 组件B
案例:

发送数据 子组件 FriendList.js

import { Component } from 'react'

export default class FriendList extends Component {
    childeChange = () => {
        this.props.data('friendList数据')
    }
    render() {
        console.log(this.props);
        return (
            <div>
                {<button onClick={() => { this.childeChange() }}>
                    点击
                </button>}

            </div>
        );
    }
}

父组件 App.js

import React, { Component } from 'react'
import FriendList from './FriendList'
import Friend from './Friend'
class App extends Component {
  state = {
    mess: ''
  }
  change = (data) => {
    this.setState({ mess: data })
  }
  render() {
    return (<div>
      <FriendList
        data={this.change}
      />
      <Friend mess={this.state.mess} />
    </div>)
  }
}
export default App

接收数据 子组件 Friend.js

import {Component} from 'react'

export default class Friend extends Component{
    render(){
        return (
            <div>
                <p>{this.props.mess}</p>
          </div>
      );
    }
}

跨级传值

在单纯的父子传参中this.props就可以了。子传父也是通过调用父组件的方法去改变参数变化,但是有时不只是父子传参,还可能爷爷组件和孙子组件或者重孙等等都有可能,所以 react 提供了组件跨级传参
案例:父级组件B 给 子组件A 传参
在这里插入图片描述
1.创建context对象并导出

父组件B

import {createContext} from 'react'
let context=createContext()
let {Consumer,Provider}=context
export default context
export {Consumer,Provider}

2.引入父组件A,父组件B,在父组件B标签中通过value属性指定需要传递的值
通过Provider标签把希望接收的组件的父组件包裹
根组件

import React, { Component } from 'react'
import Friend from './friend'
import { Provider } from './content'
class App extends Component {
    render() {
        return (
            <Provider value={{ info: 'context组件数据' }}>
                <div>
                    <Friend />
                </div>
            </Provider>
        )
    }
}
export default App

3.引入子组件B并在父组件A里书写子组件B
父组件A

import { Component } from 'react'
import DataList from './dataList'
export default class Friend extends Component {
    render() {
        return (
            <div>
                <DataList />
                )
            </div>
        )
    }
}

4.引入父组件B,子组件A通过Consumer包裹进行数据的展示
子组件A

import React,{Component} from 'react'
import {Consumer} from './content'
export default class Data extends Component{
    render (){
        return(
            <div >
                    <p>
                        <Consumer>{
                            (value)=>{console.log(value)}
                                }</Consumer>
                    </p>
            </div>
        )
    }
}

组件的生命周期

组件从创建到销毁的过程

生命周期(旧)

1.挂载阶段

constructor
componentWillMount
render
componentDidMount

2.更新阶段

componentWillReceiveProps(nextProps)
shouldComponentUpdate(nextProps, nextState)
componentWillUpdate(nextProps, nextState)
render
componentDidUpdate(prevProps, prevState)

3.卸载阶段

componentWillUnmount

生命周期(新)

使用getDerivedStateFromProps代替了旧的componentWillReceiveProps及componentWillMount。
使用getSnapshotBeforeUpdate代替了旧的componentWillUpdate。
1.挂载阶段

constructor
static getDerivedStateFromProps(props, state)
render
componentDidMount

2.更新阶段

static getDerivedStateFromProps(props, state)
shouldComponentUpdate()
componentWillUpdate()
render()
getSnapshotBeforeUpdate()
componentDidUpdate()

3.卸载阶段

componentWillUnmount

与错误相关的生命周期

static getDerivedStateFromError()
componentDidCatch(error, info)

生命周期函数详解

constructor(props)

组件初始化函数
初始化 state
处理事件绑定函数的 this

render()

render 方法是 Class 组件必须实现的方法
它会返回一个虚拟DOM,会被挂载到虚拟DOM树中,最终渲染到页面的真实DOM中
不能使用setState

static getDerivedStateFromProps(props, state)

该方法会在 render 方法之前调用,让组件在 props 变化时更新 state

  • 通过参数可以获取新的属性和状态
  • 该函数是静态的
  • 该函数的返回值会覆盖掉组件状态

componentDidMount()

在组件挂载后调用
它只会执行一次,可以使用setState

shouldComponentUpdate(nextProps, nextState)

发生在更新阶段,getDerivedStateFromProps 之后,render 之前
指示React是否要重新渲染该组件,通过返回true和false来指定
默认情况下,会直接返回true

getSnapshotBeforeUpdate(prevProps, prevState)

该方法在 render() 之后执行

  • 真实的DOM构建完成,但还未实际渲染到页面中。
  • 在该函数中,通常用于实现一些附加的dom操作
  • 该函数的返回值,会作为componentDidUpdate的第三个参数

componentDidUpdate

往往在该函数中使用dom操作,改变元素

componentDidUpdate()

DOM重新渲染触发,首次渲染不触发

componentWillUnmount()

该方法会在组件卸载及销毁前调用
可以使用setState

错误处理
当渲染过程,生命周期,或子组件的构造函数中抛出错误时,会调用如下方法

static getDerivedStateFromError()
componentDidCatch()

受控组件

在 HTML 中,表单元素(如、 和 )通常自己维护 state,并根据用户输入进行更新。而在 React 中,可变状态(mutable state)通常保存在组件的 state 属性中,并且只能通过使用 setState()来更新。
我们可以把两者结合起来,使 React 的 state 成为“唯一数据源”。渲染表单的 React 组件还控制着用户输入过程中表单发生的操作。被 React 以这种方式控制取值的表单输入元素就叫做“受控组件”。

简单来说:就是组件的状态,受react的控制

import React,{Component} from 'react'
export default class Count extends Component{
    state={
        info:'原数据'
    }
    render(){
        let {info}=this.state
        return (
            <div>
                {/* 受控组件  类似于单向数据流  只可以数据改变视图 */}
                <input type='text' value={info} onChange={({target})=>{
                    this.setState({
                        info:target.value
                    })
                }}/>
                
                <button onClick={
                    ()=>{
                        console.log(info);
                    }
                }>点击</button>
            </div>
        )
    }
}

代码分析:
info通过事件改变了,打印的不是原来的数据,而是更新后的数据

非受控组件

就是不受state的状态值改变而改变,只是具有一个类似于defaultValue这样的初始值来设置状态,或者说只接受props的改变而改变的组件,自身不会去改变state的值

简单来说:就是组件的状态,不受react的控制

import React,{Component} from 'react'
export default class Friend extends Component{
    state={
        info:'原数据'
    }
    render(){
        let {info}=this.state
        return (
            <div>
            	<input />
                <button onClick={
                    ()=>{
                        console.log(info);
                    }
                }>点击</button>
            </div>
        )
    }
}

代码分析:
这里打印的一直都是上面state里面的info的值不会根据你上面input框中值变化而发生变化

总结:

React 有两种不同的方式来处理表单输入。
如果一个 input 表单元素的值是由 React 控制,就其称为受控组件。当用户将数据输入到受控组件时,会触发修改状态的事件处理器,这时由你的代码来决定此输入是否有效(如果有效就使用更新后的值重新渲染)。如果不重新渲染,则表单元素将保持不变。
一个非受控组件,就像是运行在 React 体系之外的表单元素。当用户将数据输入到表单字段(例如 input,dropdown 等)时,React 不需要做任何事情就可以映射更新后的信息。然而,这也意味着,你无法强制给这个表单字段设置一个特定值。
在大多数情况下,你应该使用受控组件。

简单来说:
非受控组件就是一个组件的状态更新不依赖于react
受控组件就是组件的状态,受react的控制
本文只是简单介绍了一下生命周期,想要更详细的了解可以访问官网

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值