目录:

  1. 简介
  2. useRef
  3. forwardRef
  4. useImperativeHandle
  5. 回调Ref

简介

大家都知道React中的ref属性可以帮助我们获取子组件的实例或者Dom对象,进而对子组件进行修改,是一个很方便的特性。在传统类组件中,我们通过使用 React.createRef() 创建的,并通过 ref 属性附加到 React 元素来使用。而随着hooks的越来越广泛的使用,我们有必要了解一下在函数式组件中,如何使用Ref.

想要在函数式组件中使用Ref,我们必须先了解两个Api,useRefforwardRef

useRef

const refContainer = useRef(initialValue);

useRef返回一个可变的ref对象,其.current属性被初始化为传入的参数(initialValue)。返回的ref对象在整个生命周期内保持不变。

下面看一个例子

function TextInputWithFocusButton() {
// 关键代码
const inputEl = useRef(null);
const onButtonClick = () => {
// 关键代码,`current` 指向已挂载到 DOM 上的文本输入元素
inputEl.current.focus();
};
return (
<>
// 关键代码
<input ref={inputEl} type="text" /> <button onClick={onButtonClick}>Focus the input</button>
</>
);
}

效果如下

可以看到我们点击button,先通过useRef创建一个ref对象inputEl,然后再将inputEl赋值给inputref,最后,通过inputEl.current.focus()就可以让input聚焦。

然后,我们再想下,如果input不是个普通的dom元素,而是个组件,该怎么办呢?

这就牵扯到另外一个api,forwardRef

forwardRef

我们修改一下上面的例子,将input单独封装成一个组件TextInput

const TextInput =  forwardRef((props,ref) => {
return <input ref={ref}></input>
})

然后用TextInputWithFocusButton调用它

function TextInputWithFocusButton() {
// 关键代码
const inputEl = useRef(null);
const onButtonClick = () => {
// 关键代码,`current` 指向已挂载到 DOM 上的文本输入元素
inputEl.current.focus();
};
return (
<>
// 关键代码
<TextInput ref={inputEl}></TextInput>
<button onClick={onButtonClick}>Focus the input</button>
</>
);
}

可以看到React.forwardRef 接受一个渲染函数,其接收 props 和 ref 参数并返回一个 React 节点。

这样我们就将父组件中创建的ref转发进子组件,并赋值给子组件的input元素,进而可以调用它的focus方法。

至此为止,通过useRef+forwardRef,我们就可以在函数式组件中使用ref了。当然,这篇文章还远不止如此,下面还要介绍两个重要的知识点useImperativeHandle回调Ref,结合上面两个api,让你的代码更加完美。

useImperativeHandle

有时候,我们可能不想将整个子组件暴露给父组件,而只是暴露出父组件需要的值或者方法,这样可以让代码更加明确。而useImperativeHandleApi就是帮助我们做这件事的。

语法:

useImperativeHandle(ref, createHandle, [deps])

useImperativeHandle 可以让你在使用 ref 时自定义暴露给父组件的实例值。

一个例子

React函数式组件使用Ref的更多相关文章

  1. React 函数式组件的 Ref 和子组件访问(useImperativeHandle)

    引入:如何调用函数式组件内部的方法 对于 React 中需要强制修改子组件的情况,React 提供了 Refs 这种解决办法,使得我们可以操作底层 DOM 元素或者自定的 class 组件实例.除此之 ...

  2. 如何对 React 函数式组件进行优化

    文章首发个人博客 前言 目的 本文只介绍函数式组件特有的性能优化方式,类组件和函数式组件都有的不介绍,比如 key 的使用.另外本文不详细的介绍 API 的使用,后面也许会写,其实想用好 hooks ...

  3. React函数式组件和类组件[Dan]

    一篇对Dan的 How Are Function Components Different from Classes? 一文的个人阅读总结,内容来自于此.强烈推荐阅读 Dan Abramov.的博客. ...

  4. React函数式组件的性能优化

    优化思路 主要优化的方向有2个: 减少重新 render 的次数.因为在 React 里最重(花时间最长)的一块就是 reconction(简单的可以理解为 diff),如果不 render,就不会 ...

  5. 函数式组件中实现Antd打开Modal后其Input框自动聚焦(focus)到文字的最后

    目前React使用函数式组件已经成为趋势, 如何把React函数式组件用好, 提高性能, 从而实现业务需求也成为了一种能力的体现......咳咳咳, 进入正题: 现实场景需求 我想实现这一个需求, 父 ...

  6. react 中的无状态函数式组件

    无状态函数式组件,顾名思义,无状态,也就是你无法使用State,也无法使用组件的生命周期方法,这就决定了函数组件都是展示性组件,接收Props,渲染DOM,而不关注其他逻辑. 其实无状态函数式组件也是 ...

  7. React Native中ref的用法(通过组件的ref属性,来获取真实的组件)

    ref是什么? ref是组件的特殊属性,组件被渲染后,指向组件的一个引用.可以通过组件的ref属性,来获取真实的组件.因为,组件并不是真正的DOM节点,而是存在于内存中的一种数据结构,称为虚拟的DOM ...

  8. react创建组件的几种方式及其区别

    react创建组件有如下几种方式 ①.函数式定义的无状态组件 ②.es5原生方式React.createClass定义的组件   ③.es6形式的extends React.Component定义的组 ...

  9. React创建组件的三种方式及其区别

    内容转载于http://www.cnblogs.com/wonyun/p/5930333.html React推出后,出于不同的原因先后出现三种定义react组件的方式,殊途同归; 具体的三种方式: ...

随机推荐

  1. Mutual Information

    Mutal Information, MI, 中文名称:互信息. 用于描述两个概率分布的相似/相关程度. 常用于衡量两个不同聚类算法在同一个数据集的聚类结果的相似性/共享的信息量. 给定两种聚类结果\ ...

  2. HDU_1495_模拟

    http://acm.split.hdu.edu.cn/showproblem.php?pid=1495 自己用模拟写的,先除以三个数的最大公约数,弱可乐为奇数,则无解,然后开始模拟. 利用大杯子和小 ...

  3. Linux系统资料

    Linux的心得: 1)Linux由众多微内核组成,其源代码完全开源: 2)Linux继承了Unix的特性,具有非常强大的网络功能,其支持所有的因特网协议,包括TCP/IPv4. TCP/IPv6和链 ...

  4. Docker容器到底是什么?

    Docker是一个开源的应用容器引擎,是近些年最火的技术之一,Docker公司从Docker项目开源之后发家致富把公司商标改为了Docker,收购了fit项目,整合为了docker-compose,前 ...

  5. 【基础】CodeBlocks调试器基本使用方法

     CodeBlocks是一个开放源码的全功能的跨平台C/C++集成开发环境. 下载地址:http://www.codeblocks.org/downloads/26 其中,Windows环境下可以使用 ...

  6. Wannafly挑战赛5 A珂朵莉与宇宙 前缀和+枚举平方数

    Wannafly挑战赛5 A珂朵莉与宇宙 前缀和+枚举平方数 题目描述 给你一个长为n的序列a,有n*(n+1)/2个子区间,问这些子区间里面和为完全平方数的子区间个数 输入描述: 第一行一个数n 第 ...

  7. MySql在Windows下自动备份的几种方法

    以下几种全部是批处理命令中对于备份文件 1.复制date文件夹备份============================假想环境:MySQL   安装位置:C:\MySQL论坛数据库名称为:bbs数 ...

  8. sql 忘记密码 解决方法(window cmd命令解决)

    cd wamp\bin\mysql\mysql5.6.17\bin mysqld --skip-grant-tables

  9. pytorch --Rnn语言模型(LSTM,BiLSTM) -- 《Recurrent neural network based language model》

    论文通过实现RNN来完成了文本分类. 论文地址:88888888 模型结构图: 原理自行参考论文,code and comment: # -*- coding: utf-8 -*- # @time : ...

  10. rm -f 后如何恢复

    前言 每当我们在生产环境服务器上执行rm命令时,总是提心吊胆的,因为一不小心执行了误删,然后就要准备跑路了,毕竟人不是机器,更何况机器也有bug,呵呵. 那么如果真的删除了不该删除的文件,比如数据库. ...