iT邦幫忙

2022 iThome 鐵人賽

DAY 15
0
自我挑戰組

我與 React 的 30天系列 第 15

Day 15 useRef 就是不讓你 re-render

  • 分享至 

  • xImage
  •  

之前我們曾說到,我們可以 useState 配合 on.. 系列的事件去綁定 DOM,讓我們可以達成我們要的事件,但是若是發生以下狀況我們該如何去解決呢?

不要在 re-render 了

現在讓我們做出一個 input 標籤,並且取得他的值,印在畫面上,現在我們可能會這樣做

import { useState } from "react";

const Text = () => {
  const [text, setText] = useState("");

  const CountText = (e) => {
    setText(e)
    console.log("re-render"); 
  }
  
  return (
    <div>
      <input type="text" onChange={(e)=>{CountText(e.target.value)}}/>
      <div>
        目前文字: {text}
      </div>
    </div>
  )
}

export { Text }

雖然我們可以抓到他每次改變的值
但是對 React 已經有一些清楚的你應該知道會發生什麼事吧
那就是每當 input 的值改變時,畫面就會重新 re-render 了
若是小專案的話,勉強可以接受,但是我們可能會遇到大型的專案,每次的 re-render 都是很大的消耗,而且 React 有提供更方便的 Hook 讓我們不會發生這種問題,現在讓我們來隆重介紹今日的主角 useRef

什麼是 useRef

useRef 是一個函式

useState 的相同之處接收一個參數,作為初始值

而不同的地方是 useState 會回傳一個包含兩個值的陣列,第一個值是 state、第二個值setState 是用來更新 state 的函式。
而且每當 renderCount 值改變,就會觸發 re-render

差別是useRef回傳的是一個物件,裡面只有一個屬性current
重點是,請大家拿起筆記,這邊是重點
就是 當更新 current 值並不會觸發 re-render
看到不會 re-render 大家應該都很興奮吧!
接下來讓我們用簡單的範例來說明 useRef

const count = useRef(0);
count = { current: 0 }

import { useState, useRef } from "react";

const Text = () => {
  const [text, setText] = useState("");
  const textRef = useRef("")

  const textHandler = () => {
    console.log(textRef.current);  
    setText(textRef.current.value)
  }

  const inputFocus = () => {
    textRef.current.focus()
  }
  
  return (
    <div>
      <input type="text" ref={textRef} />
      <div>
        目前文字: {text}
      </div>
      <button onClick={inputFocus}>按此可以進行輸入</button>
      <button onClick={textHandler}>送出文字</button>
    </div>
  )
}

export { Text }

我們只要在 input 標籤上加上 ref 屬性並且給他你定義的 useRef 變數,就可以了,是不是很簡單

注意! 我們可以加上下面這句來確認 textRef.current 到底是什麼!

console.log(textRef.current);

印出來的結果是這樣
所以我們就可以取得 input 的值也就是textRef.current.value,來達到我們的目的~

小結

今天介紹了 useRef 的基本用法,明天會再繼續下去,讓我們看看 useRef 還有什麼黑魔法,謝謝大家


上一篇
Day 14 props 我不要你了? 讓我們來試試 useContext
下一篇
Day 16 useRef 還有什麼作用
系列文
我與 React 的 30天30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言