DEV Community

David Clark
David Clark

Posted on • Edited on

[React] How to manipulate input values before storing to state.

While working on a project, I decided it was important to do some manipulating of input values before storing it to state. Namely, capitalizing the first letter of each word the user types into that field.

I wasn't sure how to do this in JavaScript, and I wasn't 100% sure how to implement that capitalization behavior into my React component before it was stored to state (this might seem obvious to most, but I've spent a few weeks away from this project).

After all was said and done, I realized there wasn't a lot out there on this that I'd seen, so I'm sharing it here with you all.

Where Do We Do It?

If we look at our components, we probably have one for each form, or even each field. Inside there, we have what are called handlers. These little buddies take our inputs and do something with them. Chances are, storing it to our state.

This handler might look something like this:

  handleInput(event, key) {
    this.setState({
      [key]: event.target.value
    });
  }

What this does, is stores the value of the input field (so, whatever the user types or selects) and plunks it into this component's state object, at the key that is passed from our onChange event.

Our input with onChange might look like this (usually more going on here, but let's keep it simple for this):

    <input
      required
      type="text"
      onChange={event => this.handleInput(event, 'firstName')}
    />

Our onChange is saying to run the handleInput handler, passing the event values and the firstName key.

Our state, then, might look like this:

this.state = {
  firstName: '',
  lastName: '',
  age: ''
}

If what we pass in our onChange doesn't match a key in our state object, this will not work.

All that said – still, where do we do it?

Our handler is the perfect place to do this. We're going to pass the data on from our input's onChange, up to our handleInput. Before we setState, we'll perform our logic.

How do we do it?

I wasn't entirely sure how to do this myself, so I had to do some hunting. I knew we'd have to split and join and toUpperCase some things, but wasn't entirely sure beyond that.

Turns out, it's quite easy.

First of all, let's understand what we are doing it to. Simply put, we need to manipulate our event.target.value, which is whatever the user inputs into that field.

Here are all the things we need to perform on our event.target.value input to capitalize the first letter of each word:

      .toLowerCase()
      .split(' ')
      .map(s => s.charAt(0).toUpperCase() + s.substr(1))
      .join(' ');
  • toLowerCase() is first making every character lower case.
  • split(' ') takes each character in our original string (event.target.value) and splits them into an array equal to each character in that string. So if our user provided John, we would get [j,o,h,n]. This allows us to map over each character.
  • map(s ...) - Here, we're using s to represent each iteration, so each character, which is a single-character string.
  • map(s => s.charAt(0) ...) - if our iteration is the character at the 0 place in our array...
  • map(s => s.charAt(0).toUpperCase() then capitalize it...
  • map(s => s.charAt(0).topupperCase() + s.substr(1)) - this one is tougher to explain. substr (short for substring) returns the part of the string at the index value you define, and anything after it. In this case, everything but the first index value. Alternatively, we could use it to return maybe just the first two indexes (0, 1) or Jo. We use the + to combine (concatenate) all of the array items together.

So here's what our code should look like:

    let capsText = event.target.value
      .toLowerCase()
      .split(' ')
      .map(s => s.charAt(0).toUpperCase() + s.substr(1))
      .join(' ');

Now, if we console.log(capsText), you'll see we get exactly what we want. How do we store that in state?

Simple!

    this.setState({
      [key]: capsText
    });

Let's put it all together!

  handleInput(event, key) {
    let capsText = event.target.value
      .toLowerCase()
      .split(' ')
      .map(s => s.charAt(0).toUpperCase() + s.substr(1))
      .join(' ');

    this.setState({
      [key]: capsText
    });
  }

That's it! Not so bad, eh?

Thanks for reading.

Top comments (0)