Nearby lessons
18 of 44🪝 ReactJS – useRef Hook & Uncontrolled Components
📌 What is useRef?
What is useRef Hook in React?
The useRef Hook allows you to persist values between renders without causing re-renders.
It can also be used to directly access DOM elements in functional components.
An uncontrolled component uses refs instead of state to manage form inputs.
📌 Why use useRef?
- Access DOM elements directly using
refattribute - Store a mutable value that does not cause re-render
- Persist values across component renders
- Helpful for uncontrolled components (like forms without state)
⚙️ Accessing DOM Elements with useRef
We can attach a ref to any element to access it directly in the DOM.
Here, we use useRef with <h1> and change its style dynamically.
import React, { useEffect, useRef } from 'react'; const UseRefHook = () => { const newRef = useRef(); useEffect(() => { console.log(newRef); console.log(newRef.current); }); const handleHeading = () => { newRef.current.style.color = "red"; newRef.current.style.fontFamily = "cooper"; } return ( <div> <h1 ref={newRef}>Learning Never Ends</h1> <button onClick={handleHeading}>Click</button> </div> ) } export default UseRefHook;
📝 Uncontrolled Component with useRef
Instead of storing form values in useState,
we can use useRef to directly read values from input fields.
import React, { useEffect, useRef } from 'react'; const UseRefHook = () => { const firstRef = useRef(); const lastRef = useRef(); useEffect(() => { firstRef.current.focus(); firstRef.current.style.color = "red"; firstRef.current.style.backgroundColor = "green"; }); const handleSubmit = (e) => { e.preventDefault(); console.log('Full Name = ', firstRef.current.value, lastRef.current.value); } return ( <form onSubmit={handleSubmit}> <label>First Name</label> <input type="text" ref={firstRef} placeholder="Enter First Name" /> <br /><br /> <label>Last Name</label> <input type="text" ref={lastRef} placeholder="Enter Last Name" /> <br /><br /> <input type="submit" value="Submit" /> </form> ) } export default UseRefHook;
❌ Problem: Using useState for Render Count
If we try to use useState inside useEffect
to count renders, it causes an infinite loop.
import React, { useEffect, useState } from 'react'; const UseRefHook2 = () => { const [inputValue, setInputValue] = useState(""); const [count, setCount] = useState(0); useEffect(() => { setCount(count + 1); // ❌ Causes re-render loop }, []); return ( <div> <label>Enter Name: </label> <input type="text" value={inputValue} onChange={(e) => setInputValue(e.target.value)} /> <h2>Render count: {count}</h2> </div> ) } export default UseRefHook2;
✅ Solution: Using useRef for Render Count
We can fix this issue by using useRef instead of useState
since updating ref.current does not trigger re-renders.
import React, { useEffect, useRef, useState } from 'react'; const UseRefHook2 = () => { const [inputValue, setInputValue] = useState(""); const count = useRef(0); useEffect(() => { count.current = count.current + 1; }); return ( <div> <label>Enter Name: </label> <input type="text" value={inputValue} onChange={(e) => setInputValue(e.target.value)} /> <h2>Render count: {count.current}</h2> <h3>Name: {inputValue}</h3> </div> ) } export default UseRefHook2;