17.React获取DOM的方式

3. 获取DOM方式refs

3.1. 如何使用Ref
    1. 在React的开发模式中,通常情况下不需要、也不建议直接操作原生DOM,但是某些特殊的情况,确实需要获取到DOM进行某些操作;
    • 1.1. 管理焦点,文本选择或媒体播放;
    • 1.2. 触发强制动画;
    • 1.3. 集成第三方DOM库;
    • 1.4. 我们可以通过refs获取DOM;
    1. 如何创建refs来获取对应的DOM呢?目前有三种方式:
    • 2.1. 方式一: 在React元素上绑定一个ref字符串(这种方式获取ref元素会被废弃,不推荐使用)

    • 2.2. 方式二: 提前创建好ref对象createRef(), 将创建出来的对戏那个绑定到元素上(推荐使用这种方式)

    • 2.3. 方式三: 传入一个回调函数,在对应的元素被渲染之后,回调函数被执行,并且将元素传入

    • 2.4. 示例代码如下:

      js 复制代码
        import React, { PureComponent, createRef } from 'react'
      
        export class App extends PureComponent {
          constructor() {
            super()
            this.state = {
        
            }
            // 1. 创建的ref不涉及页面更新的东西,不涉及到渲染的东西
            this.titleRef = createRef()
            this.titleEl = null
      
      
          }
          getNativeDom () {
            // 不建议这样拿原生dom
            // const h2El = document.querySelector('h2')
      
            // 1. 方式一: 在React元素上绑定一个ref字符串(这种方式获取ref元素会被废弃,不推荐使用)
            // console.log(this.refs.why)
            // 2. 方式二: 提前创建好ref对象,createRef(), 将创建出来的对戏那个绑定到元素上(推荐使用这种方式)
            // console.log(this.titleRef.current)
            // 3. 方式三: 传入一个回调函数,在对应的元素被渲染之后,回调函数被执行,并且将元素传入
            console.log(this.titleEl)
          }
          render() {
            return (
              <div>
                <h2 ref='why'>Hello World</h2>
                <div ref={this.titleRef}>你好啊,李银河</div>
                {/* 传入一个函数,当元素渲染出来之后自动回调这个函数,回调函数时并把元素作为参数传递给这个函数 */}
                <div ref={el => this.titleEl = el }>你好啊,世界</div>
                <button onClick={(e) => this.getNativeDom()}>获取ref元素</button>
              </div>
            )
          }
        }
      
        export default App
3.2. ref获取类组件实例
    1. 类组件的ref获取方式和绑定元素类似,通过ref属性绑定组件实例
    1. 示例代码如下:
    jsx 复制代码
      import React, { PureComponent, createRef } from 'react'
    
      export class HelloWorld extends PureComponent {
        test () {
          console.log('------')
        }
        render() {
          return (
            <div>
              <h2>Hello World!</h2>
            </div>
          )
        }
      }
    
    
      export class App extends PureComponent {
        constructor() {
          super()
          this.state = {
      
          }
          // 1. 创建的ref不涉及页面更新的东西,不涉及到渲染的东西
          this.hwRef = createRef()
        }
        getComponent () {
          console.log(this.hwRef.current)
          this.hwRef.current.test()
        }
        render() {
          return (
            <div>
              <HelloWorld ref={this.hwRef} />
              <button onClick={(e) => this.getComponent()}>获取组件实例</button>
            </div>
          )
        }
      }
    
      export default App
3.3. ref获取函数组件(ref的转发)
    1. 在前面我们学习ref时讲过,ref不能应用于函数式组件;
    • 1.1. 因为函数式组件没有实例,所以不能获取对应的组件对象
    1. 但是,在开发中我们可能想要获取函数式组件中某个元素的DOM,这个时候我们应该如何操作呢?
    • 方式一: 直接传入ref属性(错误的做法)
    • 方式二: 通过forwardRef()高阶函数
    1. 示例代码如下:
    jsx 复制代码
      import React, { PureComponent, createRef, forwardRef } from 'react'
    
      const HelloWorld = forwardRef (function (props, ref) {
        // 1. 在前面学习的ref,ref不能应用于函数式组件
        //  - 1.1. 函数式组件没有实例,所以不能获取对应的组件对象;
        // 2. 通过forwardRef高阶函数;
        return (
          <div>
            <h2  ref={ref}>Hello World!</h2>
            <p>哈哈哈</p>
          </div>
        )
      })
    
    
      export class App extends PureComponent {
        constructor() {
          super()
          this.state = {
      
          }
          // 1. 创建的ref不涉及页面更新的东西,不涉及到渲染的东西
          this.hwRef = createRef()
        }
        getComponent () {
          console.log(this.hwRef.current)
        }
        render() {
          return (
            <div>
              <HelloWorld ref={this.hwRef} />
              <button onClick={(e) => this.getComponent()}>获取函数组件实例</button>
            </div>
          )
        }
      }
    
      export default App
3.4. ref的类型
    1. ref的值根据节点的类型而有所不同
    • 1.1. 当ref属性用于HTML元素时,构造函数中使用React.createRef()创建的ref接受底层DOM元素作为其current属性
    • 1.2. 当ref属性用于自定义class组件时,ref对象接收组件的实例作为其current属性
    • 1.3. 不能在函数组件上使用ref属性,因为他们没有实例
    1. 函数组件是没有实例的,所以无法通过ref获取他们的实例:
    • 2.1. 但是某些时候,我们可能想要获取函数式组件中的某个DOM元素;
    • 2.2. 这个时候我们可以通过React.forwardRef(), 当ref属性用于通过forwardRef转发的函数式组件时,ref对象接收组件内部转发的具体元素或组件实例作为其current属性。
    • 2.3. 后面还会记录到hooks中如何使用ref;
相关推荐
代码搬运媛8 小时前
Jest 测试框架详解与实现指南
前端
counterxing9 小时前
我把 Codex 里的 Skills 做成了一个 MCP,还支持分享
前端·agent·ai编程
wangqiaowq9 小时前
windows下nginx的安装
linux·服务器·前端
之歆9 小时前
DAY_12JavaScript DOM 完全指南(二):实战与性能篇
开发语言·前端·javascript·ecmascript
发现一只大呆瓜9 小时前
Vite凭什么这么快?3分钟带你彻底搞懂 Vite 热更新的幕后黑手
前端·面试·vite
Maimai1080810 小时前
React如何用 @microsoft/fetch-event-source 落地 SSE:比原生 EventSource 更灵活的实时推送方案
前端·javascript·react.js·microsoft·前端框架·reactjs·webassembly
candyTong10 小时前
Claude Code 的 Edit 工具是怎么工作的
javascript·后端·架构
kyriewen11 小时前
产品经理把PRD写成“天书”,我用AI半小时重写了一遍,他当场愣住
前端·ai编程·cursor
humcomm12 小时前
元框架的工作原理详解
前端·前端框架
canonical_entropy12 小时前
Attractor Before Harness: AI 大规模开发的方法论
前端·aigc·ai编程