Day 11: Mastering useRef React Hook – Accessing DOM & Persisting Values
4 mins read

Day 11: Mastering useRef React Hook – Accessing DOM & Persisting Values

In today’s React learning series, we will deep dive into useRef React Hook. When working with React, you’ve probably noticed that most things revolve around state and props. We’ve used useState to store and update values, and we’ve seen how React automatically re-renders components when state changes.

But what if we want to store a value that doesn’t cause re-renders every time it changes? Or what if we want to directly interact with a DOM element (like focusing an input box)?

That’s where the useRef hook comes in.


What is useRef?

In simple words:

  • useRef is a React hook that lets you create a mutable reference object.
  • This object has a .current property where you can store values.
  • Unlike state (useState), updating .current does not trigger a re-render.

Think of it like a hidden box in your component—React remembers what’s inside the box, but won’t bother re-rendering the UI when you change its contents.

Syntax

const refContainer = useRef(initialValue);
  • refContainer is the object returned by useRef.
  • refContainer.current will hold the actual value.

When to Use useRef?

  1. Accessing DOM elements directly (like document.querySelector in plain JS).
  2. Storing values between renders that don’t need to trigger UI updates.
  3. Persisting previous values for comparison or debugging.

Example 1: Focusing an Input Field

Let’s say we want a button that automatically focuses on an input field. Normally, we would have to manually grab the element in vanilla JS using document.getElementById. In React, we can do this cleanly with useRef.

import React, { useRef } from "react";

function InputFocusExample() {
  const inputRef = useRef(null);

  const handleFocus = () => {
    inputRef.current.focus();
  };

  return (
    <div className="p-4">
      <h2 className="text-lg font-bold mb-2">useRef Example: Focus Input</h2>
      <input
        ref={inputRef}
        type="text"
        placeholder="Type something..."
        className="border p-2 rounded"
      />
      <button
        onClick={handleFocus}
        className="ml-2 px-4 py-2 bg-blue-500 text-white rounded"
      >
        Focus Input
      </button>
    </div>
  );
}

export default InputFocusExample;

How it works:

  • We create inputRef with useRef(null).
  • Assign it to the input element via the ref prop.
  • On button click, we access inputRef.current (the actual input element) and call .focus().

Example 2: Tracking a Value Without Re-renders

Sometimes you need to store a value but don’t want it to trigger a re-render like useState would. For example, let’s build a counter that keeps track of clicks but doesn’t re-render the UI every time.

import React, { useRef, useState } from "react";

function CounterWithRef() {
  const [renderCount, setRenderCount] = useState(0);
  const clickCount = useRef(0);

  const handleClick = () => {
    clickCount.current += 1;
    console.log("Clicked:", clickCount.current);
    setRenderCount((prev) => prev + 1);
  };

  return (
    <div className="p-4">
      <h2 className="text-lg font-bold mb-2">useRef Example: Counter</h2>
      <p>Button clicked: {clickCount.current} times</p>
      <button
        onClick={handleClick}
        className="px-4 py-2 bg-green-500 text-white rounded"
      >
        Click Me
      </button>
      <p>Component re-rendered: {renderCount} times</p>
    </div>
  );
}

export default CounterWithRef;

What’s happening here?

  • clickCount is managed by useRef, so React doesn’t re-render when it changes.
  • To see UI changes, we manually update a dummy state renderCount.
  • This shows how useRef can store values across renders without causing re-renders.

Difference Between useState and useRef

FeatureuseStateuseRef
Causes re-render?✅ Yes❌ No
Stores data across renders?✅ Yes✅ Yes
Typical use caseUI updates, dynamic renderingDOM access, storing values silently

Why useRef is Important

  • It bridges the gap between React world (declarative) and DOM world (imperative).
  • It gives you a way to store values that don’t belong to the UI state.
  • Without useRef, we’d often need hacks or external variables, which break React’s flow.

Wrapping Up

Today we learned:

  • useRef is like a box that stores values without triggering re-renders.
  • You can use it to directly access DOM elements.
  • It helps in scenarios where you need to persist values silently between renders.

By now, we’ve covered useState, useEffect, and useRef—three of the most commonly used React hooks.


👉 In the next blog (Day 12), we’ll dive into useReducer, a hook that helps manage complex state logic in a cleaner way than multiple useState calls.

Leave a Reply

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