Skip to main content

Command Palette

Search for a command to run...

React Controlled Components and Forms

Published
3 min readView as Markdown

Controlling Form Values from State

  • A controlled form is a form that derives its input values from state

  • Consider the following form code

import React, { useState } from "react";

function Form() {
  const [firstName, setFirstName] = useState("John");
  const [lastName, setLastName] = useState("Henry");

  return (
    <form>
      <input type="text" value={firstName} />
      <input type="text" value={lastName} />
      <button type="submit">Submit</button>
    </form>
  );
}

export default Form;
  • Currently, the input values of the form will display what the state of firstName and lastName is set to

    • But there is no way to update the state yet.
  • We can update the state by adding the onChange event listener as follows

<input type="text" onChange={handleFirstNameChange} value={firstName}/>
<input type="text" onChange={handleLastNameChange} value={lastName} />
  • With this, the onChange will execute every time the value of an input changes

  • Below, find the functions to handle the changes, you will notice the functions take in an event as an argument, which is passed down from the onChange event listener

function handleFirstNameChange(event) {
  setFirstName(event.target.value);
}
function handleLastNameChange(event) {
  setLastName(event.target.value);
}

Form Element Types

  • Form Elements:

    • <input>, <textarea>, <select>, and <form>

    • For these, the prop we use is value

    • For a checkbox <input type="checkbox">, we used checked, which is a true or false value that can be set by the state through an onChange event listener

**A major benefit of controlled forms is how it allows us to use the form values in other components

  • You could have all the form states, logic, and functions stored in a parent component while passing down this logic as props to the Form component.

  • As the state updates in the form, you can pass down the state to a different child component for other uses, such as displaying form inputs live as they're being typed.

    • This is very useful to capture user input and utilize it throughout your application, even if a server isn't involved.

Form Validation with Controlled Forms

  • Having controlled forms allows us the functionality to validate the input before setting the State for the input.

  • For example, if you want the form to allow only numbers between 0 - 5, you can set up an if statement inside the call-back function for the onChange event listener as follows

function handleNumberChange(event) {
    const newNumber = parseInt(event.target.value);
    if (newNumber >= 0 && newNumber <= 5) {
      setNumber(newNumber);
    }
  }
  • If the input is invalid, we avoid setting the state and thus preventing the input from updating.

  • As well, this allows us to set another state variable as an error that can be displayed if the input is not valid

Submitting a Controlled Form

  • When submitting the form, add an onSubmit event listener to the form element

      return (
        <form onSubmit={handleSubmit}> //right here
          <input type="text" onChange={handleFirstNameChange} value={firstName} />
          <input type="text" onChange={handleLastNameChange} value={lastName} />
          <button type="submit">Submit</button>
        </form>
      );
    

Then create the callback function for handleSubmit as follows

function handleSubmit(event) {
  event.preventDefault(); // need to do this like Javascript
  const formData = {    //Here we are adding the current State data at the
    firstName: firstName, //time of submit to an object variable
    lastName: lastName,
  };
  props.sendFormDataSomewhere(formData); //When submitted, this data should go somewhere
  setFirstName(""); //This is to clear the current input fields and reset the states
  setLastName("");
}

As well, in the handleSubmit call-back function, we can also validate the inputs for submission and send out error messages.

citations:

-Flatiron School