Khóa học reactjs

Tìm hiểu Refs và useRef trong React

0 phút đọc

Trong data flow của React, props là cách để các parent component tương tác với các child component. Để updated child componnent, bạn cần re-render nó với các props mới. Nhưng sẽ có một số trường hợp cần bắt buộc phải cập nhật các child component bên ngoài data flow của React. Cho những trường hợp này, chúng ta có thể sử dụng react Refs.

React ref là gì?

React Ref (React reference) hiểu đơn giản là một đối tượng tham chiếu đến một biến, một component giữ cho giá trị của nó không thay đổi giữa các lần render và truy xuất các giá trị đó thông qua key current.

Tìm hiểu Refs và useRef trong React

Cách thêm một Ref vào component

Bạn có thể thêm một Ref vào component của bạn bằng cách import Hook useRef từ React:

javascript Copy
import { useRef } from "react";

Trong component của bạn, gọi Hook useRef và truyền giá trị ban đầu mà bạn muốn , ví dụ đây là một Ref đến giá trị 0:

javascript Copy
const ref = useRef(0);

useRef trả về một đối tượng như sau:

javascript Copy
{
  current: 0; // Giá trị bạn đã truyền cho useRef
}

Bạn có thể truy cập giá trị hiện tại của Ref đó thông qua thuộc tính ref.current. Giá trị này có ý nghĩa được thay đổi, có nghĩa bạn có thể đọc và ghi vào nó.

Truy xuất giá trị và cập nhật giá trị cho ref

Sau khi khởi tạo, bạn chỉ việc truy xuất key current để lấy giá trị hoặc gán cho ref một giá trị mà cần giữ cho nó không thay đổi giữa các lần render

jsx Copy
import { useRef } from "react";

function MyComponent() {
  const myRef = useRef(null);
  useEffect(() => {
    myRef.current = "Hello world";
  }, []);

  console.log(myRef.current);

  return <div>Demo</div>;
}

// Result 1: null
// Result 2: Hello world

Nhưng có một lưu ý mà đã được nhắc từ đầu về ref nó sẽ không trigger render lại component. Vì thế, nếu không sử dụng state hoặc một số kỹ thuật khác để trigger render lại component. Bạn sẽ không thấy được giá trị của ref thay đổi trên giao diện.

Ví dụ sử dụng Ref trong React

Dưới đây là một ví dụ về việc sử dụng Ref trong một ứng dụng React:

javascript Copy
import { useRef } from "react";

export default function Counter() {
  let ref = useRef(0);

  function handleClick() {
    ref.current = ref.current + 1;
    alert("Bạn đã nhấp chuột " + ref.current + " lần!");
  }

  return <button onClick={handleClick}>Nhấp vào tôi!</button>;
}

Ref này trỏ đến một số, nhưng giống như state, bạn có thể trỏ đến bất cứ thứ gì: một chuỗi, một đối tượng, hoặc thậm chí một hàm. Khác với state, Ref là một đối tượng JavaScript thuần túy có thuộc tính hiện tại (current) mà bạn có thể đọc và sửa đổi.

Sự khác biệt giữa Refs và State

Dưới đây là một so sánh giữa Refs và state:

Refs State
useRef(initialValue) trả về { current: initialValue } useState(initialValue) trả về giá trị hiện tại của biến state và một hàm setter state ( [value, setValue])
Không gây ra việc render lại khi bạn thay đổi nó Gây ra việc render lại khi bạn thay đổi nó
Có thể thay đổi - bạn có thể sửa đổi và cập nhật giá trị current bên ngoài quá trình render "Bất biến" - bạn phải sử dụng hàm setter state để sửa đổi biến state và gây ra việc render lại.
Bạn không nên đọc (hoặc viết) giá trị current trong quá trình render Bạn có thể đọc state bất kỳ lúc nào. Tuy nhiên, mỗi lần render có một bản sao riêng biệt của state và nó không thay đổi.

Khi nào nên sử dụng Refs trong React

Có rất nhiều trường hợp ở đây, xem qua thử nhé.

Tham chiếu đến real DOM Elements - trong trường hợp này, bạn có thể đặt ref cho các thể jsx như sau

jsx Copy
function MyComp() {
  const inputRef = useRef(null);

  return <input type="text" ref={inputRef} />;
}

Sau đó, bạn có thể thử truy cập DOM element bằng inputRef.current

Cho một ví dụ như sau

jsx Copy
function MyComp() {
  const inputRef = useRef(null);

  const onSubmitForm = (e) => {
    e.preventDefault();
    console.log(inputRef.current.value);
  };

  return (
    <form onSubmit={onSubmitForm}>
      <input type="text" ref={inputRef} />
      <button htmlType="submit">Submit</button>
    </form>
  );
}

Việc này sẽ giảm thiểu được lượng lớn lần re-render lại component nếu chúng ta sử dụng các thông thường bằng cách đặt và thay đổi state của input.

Lưu ý

Nếu phần tử được hiển thị có điều kiện, bạn có thể thích sử dụng callback kết hợp với ref

jsx Copy
function MyComp() {
  const [isShowingForm, setShowingForm] = useState(false);
  const inputRef = useRef(null);

  const refCallback = useCallback((node) => {
    console.log(node);
  }, []);

  const onSubmitForm = (e) => {
    e.preventDefault();

    console.log(inputRef.current.value);
  };

  return (
    <>
      <button htmlType="button" onClick={() => setShowingForm(!isShowingForm)}>
        {isShowingForm ? "To Off" : "To On"}
      </button>

      {isShowingForm && (
        <form onSubmit={onSubmitForm}>
          <input type="text" ref={refCallback} />
          <button htmlType="submit">Submit</button>
        </form>
      )}
    </>
  );
}

Lưu ý rằng

Bạn có thể thấy sử dụng phải sử dụng useCallback bên trong ref. Nếu không useCallback sẽ được gọi lại ở mỗi lần hiển thị, điều này sẽ ảnh hưởng không tốt đến tính nhất quán.

Avatar
Được viết bởi

Admin Team

Gợi ý câu hỏi phỏng vấn

Không có dữ liệu

Không có dữ liệu

Gợi ý bài viết
Không có dữ liệu

Không có dữ liệu

Bình luận

Chưa có bình luận nào

Chưa có bình luận nào