资讯专栏INFORMATION COLUMN

React父组件调用子组件中的方法实例详解

3403771864 / 2113人阅读

  本文主要讲述ref 的应用仅为父组件调用子组件场景下的应用方式1

  Class组件

  1. 自定义事件

   Parent.js

  import React, { Component } from 'react';
  import Child from './Child';
  class Parent extends Component {
  componentDidMount () {
  console.log(this.childRef)
  }
  handleChildEvent = (ref) => {
  // 将子组件的实例存到 this.childRef 中, 这样整个父组件就能拿到
  this.childRef = ref
  }
  //按钮事件处理
  handleClick = () => {
  // 通过子组件的实例调用组组件中的方法
  this.childRef.sendMessage()
  }
  render () {
  return (
  <>
  <Child
  onChildEvent={this.handleChildEvent}
  />
  <button onClick={this.handleClick}>Trigger Child Event</button>
  </>
  );
  }
  }
  export default Parent;

  Child.js

  import React, { Component } from 'react';
  class Child extends Component {
  //子组件完成挂载时, 将子组件的方法 this 作为参数传到父组件的函数中
  componentDidMount () {
  // 在子组件中调用父组件的方法,并把当前的实例传进去
  this.props.onChildEvent(this)
  }
  // 子组件的方法, 在父组件中触发
  sendMessage = () => {
  console.log('sending message')
  }
  render () {
  return ( <div>Child</div> );
  }
  }
  export default Child;
  2. 使用 React.createRef()

  ParentCmp.js

  import React, { Component } from 'react';
  import ChildCmp from './ChildCmp';
  export default class ParentCmp extends Component {
  constructor(props) {
  super(props)
  // 创建Ref
  this.childRef = React.createRef()
  }
  // 按钮事件
  handleClick = () => {
  // 直接通过 this.childRef.current 拿到子组件实例
  this.childRef.current.sendMessage()
  }
  render () {
  return (
  <>
  <ChildCmp ref={this.childRef} />
  <button onClick={this.handleClick}>Trigger Child Event</button>
  </>
  );
  }
  }

  而子组件就是一个普通的组件

  ChildCmp.js

  import React, { Component } from 'react';
  export default class ChildCmp extends Component {
  sendMessage = () => {
  console.log('sending message')
  }
  render () {
  return 'Child';
  }
  }

  3. 使用回调Refs

  回调 Refs 是另一种设置 Ref 的方式,可以控制 refs 被设置和解除的时间。

  此时,需要传递一个函数,不同于传递 createRef() 创建的 ref 属性。

   current也不是访问 Ref 必需。

  ParentCmp.js

  import React, { Component } from 'react';
  import ChildCmp from './ChildCmp';
  export default class ParentCmp extends Component {
  constructor(props) {
  super(props)
  // 创建 Ref,不通过 React.createRef()
  this.childRef = null
  }
  // 设置 Ref
  setChildRef = (ref) => {
  this.childRef = ref
  }
  // 按钮事件
  handleClick = () => {
  // 直接通过 this.childRef 拿到子组件实例
  this.childRef.sendMessage(`Trigger Child Event from Parent`)
  }
  render () {
  return (
  <>
  <ChildCmp ref={this.setChildRef} />
  <button onClick={this.handleClick}>Trigger Child Event</button>
  </>
  );
  }
  }

  而子组件还是一个普通的组件

  ChildCmp.js

  import { Component } from 'react';
  export default class ChildCmp extends Component {
  sendMessage = (message) => {
  console.log('sending message:', message)
  }
  render () {
  return 'Child';
  }
  }

  【注】对比自定义事件方式,回调 Refs 更像是精简的自定义事件方式:

  在自定义事件名称变成了 ref之后,子组件内无需手动绑定。

  Function组件

  在普通默认情况下,无法在函数组件上使用 ref 属性,主要是没有实例。上述两种方式都行不通。

  解决办法就是使用 forwardRef 和 useImperativeHandle。

  不过在函数的内部是可以使用 useRef 钩子来获取组件内的 DOM 元素。

  Parent.js

  import React, { useRef } from 'react';
  import Child from './Child';
  const Parent = () => {
  // 通过 Hooks 创建 Ref
  const childRef = useRef(null)
  const handleClick = () => {
  childRef.current.sendMessage()
  }
  return (
  <>
  <Child
  ref={childRef}
  />
  <button onClick={handleClick}>Trigger Child Event</button>
  </>
  );
  }
  export default Parent;

  Child.js

  import React, { forwardRef, useImperativeHandle } from 'react';
  const Child = forwardRef((props, ref) => {
  //将子组件的方法 暴露给父组件
  useImperativeHandle(ref, () => ({
  sendMessage
  }))
  const sendMessage = () => {
  console.log('sending message')
  }
  return ( <div>Child</div> );
  })
  export default Child;

  注:

  上面的例子中只是简单地演示了父子组件之间的方法调用,当然实际情况中子组件中可以也会有自己的 ref 指向自己内部的 DOM 元素,不过这些原理都是一样的。

  补充:子组件调用父组件方法

  子组件中调用父组件的setId方法

  父组件

  <NavBarX
  item={item}
  current={current}
  getBatchDetails={(id) => this.getBatchDetails(0, id)}
  setId={(id, callback) => this.setState({ id }, callback)}
  onRef={this.onNavBarXRef}
  />

  子组件

  this.props.setId(prePageId, () => {
  getBatchDetails(prePageId)
  })

       上述就是全部内容,后续请大家多多关注!

文章版权归作者所有,未经允许请勿转载,若此文章存在违规行为,您可以联系管理员删除。

转载请注明本文地址:https://www.ucloud.cn/yun/127716.html

相关文章

  • 5、React组件事件详解

    摘要:组件事件响应在构建虚拟的同时,还构建了自己的事件系统且所有事件对象和规范保持一致。的事件系统和浏览器事件系统相比,主要增加了两个特性事件代理和事件自动绑定。 React组件事件响应 React在构建虚拟DOM的同时,还构建了自己的事件系统;且所有事件对象和W3C规范保持一致。 React的事件系统和浏览器事件系统相比,主要增加了两个特性:事件代理、和事件自动绑定。 1、事件代理 ...

    Ververica 评论0 收藏0
  • 简述 React 组件生命周期

    摘要:这个阶段只有一个方法,该方法在整个生命周期内调用且仅调用一次。在这里进行一些相关的销毁操作,比如撤销定时器,事件监听等等。 详解 React 生命周期 整个 React 生命周期有3个阶段:创建、更新、卸载,每个阶段有对应的工作和方法,我们可以看下面这个经典的图研究一下: showImg(https://segmentfault.com/img/remote/1460000016330...

    qpal 评论0 收藏0
  • React入门看这篇就够了

    摘要:背景介绍入门实例教程起源于的内部项目,因为该公司对市场上所有框架,都不满意,就决定自己写一套,用来架设的网站。做出来以后,发现这套东西很好用,就在年月开源了。也就是说,通过钩子函 react - JSX React 背景介绍 React 入门实例教程 React 起源于 Facebook 的内部项目,因为该公司对市场上所有 JavaScript MVC 框架,都不满意,就决定自己写一套...

    luckyw 评论0 收藏0
  • React的Refs方法获取DOM实例 和 访问组件方法及属性

    摘要:绑定属性调用的时候使用调用子组件方法这是一个很神奇的方法,它可以调用子组件的方法以及属性。建立组件建立子组件,并在子组件实现一个方法,如,这个方法实现变更当前组件上面的文本,提供这样一个测试用例。输入框获取焦点完整实例点我输入框获取焦点 React 支持一种非常特殊的属性 Ref ,你可以用来绑定到 render() 输出的任何组件上。 ref : 绑定属性 refs : 调用的时候...

    geekzhou 评论0 收藏0
  • React

    摘要:基础创建虚拟参数元素名称,例如参数属性集合,例如,,,从参数开始,表示该元素的子元素,通常这些元素通过创建,文本文件可以直接插入嘻嘻哈哈这是渲染器,将元素渲染到页面中。 React简介 FeceBook开源的一套框架,专注于MVC的视图V模块。实质是对V视图的一种实现。 React框架的设计没有过分依赖于某个环境,它自建一套环境,就是virtual DOM(虚拟DOM)。 提供基础AP...

    hlcc 评论0 收藏0

发表评论

0条评论

最新活动
阅读需要支付1元查看
<