How to Implement Controlled Components in React

This article provides a straightforward guide on how to implement controlled components in React. You will learn the core concepts behind controlled inputs, the step-by-step process of setting them up using React state, and see a practical code example to help you manage form data effectively.

In React, a controlled component is an input element whose value is completely controlled by the React state. Instead of the DOM maintaining its own internal state, React acts as the “single source of truth.” When a user types into an input, an event handler updates the React state, which then updates the displayed value of the input.

To implement a controlled component in a functional React component, follow these three steps:

  1. Initialize State: Use the useState hook to create a state variable that will hold the input’s value.
  2. Bind the Value: Assign the state variable to the value attribute of the HTML input element.
  3. Handle Changes: Create an onChange event handler function. This function will trigger whenever the user types, updating the state variable with the new input value (e.target.value).

Code Example

Here is a practical implementation of a controlled text input:

import React, { useState } from 'react';

function ControlledForm() {
  // 1. Initialize state with an empty string
  const [inputValue, setInputValue] = useState('');

  // 3. Handle change event and update state
  const handleChange = (event) => {
    setInputValue(event.target.value);
  };

  const handleSubmit = (event) => {
    event.preventDefault();
    alert(`Submitted Value: ${inputValue}`);
  };

  return (
    <form onSubmit={handleSubmit}>
      <label htmlFor="username">Username:</label>
      <input
        type="text"
        id="username"
        value={inputValue} // 2. Bind the input value to state
        onChange={handleChange} // Bind the change handler
      />
      <button type="submit">Submit</button>
    </form>
  );
}

export default ControlledForm;

Key Benefits

By using controlled components, you gain direct access to the input value at any time without querying the DOM. This makes it easy to perform real-time field validation, conditionally disable submit buttons, and dynamically format user input (such as forcing uppercase or formatting phone numbers) as they type.