Controlled Elements & String to Number Conversion
Tags: javascript, tutorial, react, frontend
Published: 2023-07-31 08:23:00

Keeping UI in sync with data is one of the primary goals of React library.

React achieve this by re-rendering the UI whenever there is a change in data.

In React we allow users to give their input data by using form elements whether it's an input text field, a select dropdown list with multiple options, or checkboxes and radio buttons.

By itself, HTML form elements have a way of storing data (state) in DOM (Document Object Model) temporarily. But it's quite limited and what we can do with it. 

For example, let's say you want to make changes to certain UI components as soon as the user types a specific word in the input field. We can't do that because there is no way for React to know what's being typed by the user.

Similarly, as soon as the user submits the form if we want to reset the inputs without refreshing the page, we can't do that since React isn't in control of data (state).

That's why we take the control of data (state) from DOM to React which also allow us to keep all the data (state) centralized in our React application.

The user input data is dynamic and it changes over time. In React we store dynamic data using the useState() hook. This hook makes sure the UI is re-render whenever there is a change in data.

Let's take an example:

``` jsx
function Form() {
  const [input, setInput] = useState(""); // string datatype
  const [select, setSelect] = useState(1); // number datatype

  function handleSubmit(e) {
    e.preventDefault(); // prevent page refresh

    if (!input) return; // prevent empty input submission

    // capture user data
    const data = {
      name: input, quantity: select
    }

    console.log(data); // log the data in console

    // Reset the form input
    setInput("");
    setSelect(1);
  }
  return (
    <form onSubmit={handleSubmit}>
      <h1>How many cookies do you want?</h1> 
      <input type="text" value={input} placeholder="Type your name..." onChange={(e) => setInput(e.target.value)} />
      
      {/* converting string to number using + prefix or Number() function */}
      <select onChange={(e) => setSelect(+e.target.value)} value={select}>

        {/* {} forces the value to be set as a number instead of string */}
        <option value={1}>1</option>
        <option value={2}>2</option>
        <option value={2}>2</option>
      </select>
      <button>Give Me</button>      
    </form>
  );
}
```
We create two pieces of state to store two pieces of data.

2 ways to convert a string to a number value.

1. Adding a `+` prefix: `setSelect(+e.target.value)`

2. Wrap it with `Number` function: `setSelect(Number(e.target.value))`

Also enclosing data in quotation marks `""` make it a string while wrapping it in curly braces `{}` force the string to be converted into a JavaScript number.
``` jsx
<option value="1">1</option> // string datatype
<option value={1}>1</option> // number datatype
```

You might be asking why we have to make `e.target.value` number conversion if we already set the number as a value in the option.

This is because when we receive an event object `(e)` the value we receive is always a string.

Thanks for reading!

Follow me: @wasimapinjari 

Links: [wasimapinjari.bio.link](https://wasimapinjari.bio.link)