Tự học ReactJS: Sử dụng useRef và useEffect với DOM

Thông thường khi làm việc với React, chúng ta cần phải tích hợp vào thao tác với UI library. Và đôi khi một số thư viện cần thao tác trực tiếp với DOM. Trong React, khi bạn sử dụng <div>Some content</div> đây chỉ là cú pháp từ React.createElement. Cho nên bạn sẽ không truy cập được DOM trực tiếp trong render function. Và thực sự các nút DOM cũng ko được render cho tới khi hàm render của component được chạy xong. Hàm render trong component chỉ có nhiệm vụ là khai báo và trả về React elements. Tới đây bạn chưa có quyền truy xuất vào DOM.

Và có một cách khác đó là sau khi component render các elements xong, chúng ta khai báo một ref để truy cập vào một nút DOM cụ thể nào đó.

Sau đây là một ví dụ đơn giản khi sử dụng ref

function MyDiv() {
  const myDivRef = React.useRef()

  React.useEffect(() => {
    const myDiv = myDivRef.current
    // myDiv là một DOM node!
    console.log(myDiv)
  }, [])

  return <div ref={myDivRef}>hi</div>
}

Sau khi component được render xong, hay còn gọi là "mounted". React.useEffect được khởi chạy và ref sẽ có current với DOM node. Sau đó, bạn có thể sử dụng ref.current và thao tác trên DOM đó.

Bạn có thể sử dụng ref.current để truyền DOM vào cho các third-party như highcharts, vanilla-tilt.

Vi dụ về cách sử dụng với VanillaTilt như sau:

import * as React from 'react'
import VanillaTilt from 'vanilla-tilt'

function Tilt({children}) {
  const tiltRef = React.useRef()

  React.useEffect(() => {
    const {current: tiltNode} = tiltRef
    const vanillaTiltOptions = {
      max: 25,
      speed: 400,
      glare: true,
      'max-glare': 0.5,
    }
    VanillaTilt.init(tiltNode, vanillaTiltOptions)
    return () => tiltNode.vanillaTilt.destroy()
  }, [])

  return (
    <div ref={tiltRef} className="tilt-root">
      <div className="tilt-child">{children}</div>
    </div>
  )
}

function App() {
  return (
    <Tilt>
      <div className="totally-centered">vanilla-tilt.js</div>
    </Tilt>
  )
}

export default App

thaunguyen.com via Epic React by Kent C.Dodds

2 Comments

Leave a Reply

Your email address will not be published. Required fields are marked *