Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

React useState – setting initial state to prefilled value

I have a form with an input component that may be empty or it may be prefilled with some data. It’s also a controlled component so I keep track of the value of the input field using React’s useState.

Something like this:

export const MyComponent = props => {
    const [value, setValue] = useState(props.value || null)

    return <input value={value} type="text" />
}

In reality, however, prefilling the initial state of the input field is a bit more complex as there is a bit more drilling I have to do in the props argument and some checks that I have to do before initializing the default value.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

Now, I can do this:

export const MyComponent = props => {
    const [value, setValue] = useState(null)

    useEffect(() => {
        if (props.one?.two?.[0].value !== 0) {
            const option = props.someList.find(x => x.id === props.one.two[0].value)
            if (option)
                setValue(option)
        }
    }, [])

    return <input value={value} type="text" />
}

But I get warnings saying that useEffect has missing dependencies and I should add the props drilldown to my dependencies array. But I don’t want to have the useEffect run every single time that is updated. I just want to have it run once upon component mount / initialization and that’s it.

Is there a way to do my complicated initialization without having to use useEffect?

>Solution :

The initial value to useState can be a function. You can put the logic there instead of in a useEffect.

const [value, setValue] = useState(getInitialValue)

const getInitialValue = () => {
  if (props.one?.two?.[0].value !== 0) {
    const option = props.someList.find(x => x.id === props.one.two[0].value)
    if (option) {
      return option;
    }
  }
  return null;
}

Notice that it was not useState(getInitialValue()). Passing the function for React to call means it will only be called once. Calling it yourself will cause it to happen every render.

Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading