When changing an option of my material select I get: Use the `defaultValue` or `value` props on <select> Instead of Setting `Selected` on <option>

Asked

Viewed 288 times

0

I have the following material-ui-React select component:

<FormControl fullWidth variant="outlined" className={classes.formControl}>
  <InputLabel ref={inputLabel} htmlFor="outlined-age-native-simple">
    Filial
  </InputLabel>
  <Select
    onChange={handleChange}
    onBlur={handleBlur}
    error={touched.filial && Boolean(errors.filial)}
    value={values.filial}
    defaultValue={'DEFAULT'}
    inputProps={{
      name: 'filial',
      id: 'outlined-filial-native-simple',
    }}
  >
    <option value="DEFAULT" disabled>Choose a salutation ...</option>
    <option value={10}>Ten</option>
    <option value={20}>Twenty</option>
    <option value={30}>Thirty</option>
  </Select>
</FormControl>

When I change the select I get:

index.js:1 Warning: Use the defaultValue or value props on Instead of Setting selected on

I’m using the formik to process the form:

const enhanceWithFormik = withFormik({
  mapPropsToValues: () => ({ email: '', password: '', filial: '' }),
  handleSubmit: values => {
    console.log(values)
  },
  isInitialValid: false,
  validateOnChange: true,
  validateOnBlur: true,
  displayName: 'MyForm',
  validationSchema: schema
})

When I fill all the fields and click on the Ubmit button, it is correctly shown the value I selected in select, however I am getting this error.

  • You can send the Function code handleChange?

1 answer

1


To the facts

To clarify, let’s understand why you’re receiving this message before we go into why.

This message is given by React and not by Material-UI. What we need to understand is that React always works with controlled or uncontrolled components. Controlled components are recommended. Here follows a little straw of documentation.

When the component is controlled the state that defines the selection is by the property value. Thus React does not expect an element <option>, where its element father is controlled, is marked with the attribute Selected. In other words, codes like this will fall on this message and the attribute Selected will be ignored:

    <select onChange={handleChange} value={values.filial}>
      <option value="DEFAULT" disabled>Choose a salutation ...</option>
      <option selected value={10}>Ten</option>
      <option value={20}>Twenty</option>
      <option value={30}>Thirty</option>
    </select>

    <ul onChange={handleChange} value={values.filial}>
      <option value="DEFAULT" disabled>Choose a salutation ...</option>
      <option selected value={10}>Ten</option>
      <option value={20}>Twenty</option>
      <option value={30}>Thirty</option>
    </ul>       

But then why am I getting this message on <Select> of Material-UI if I’m not putting Selected in the element <option>?

What is happening is that the Select of Material-UI (reinforcing, not native element <select>), when controlled by a property value and not marked with the property Native, expects your options to be elements <MenuItem> and not <option>.

Material-UI Select will render the options in a drop-down menu by forwarding to the property select for the element <MenuItem> who is selected(only indicating to apply selected element CSS styles).

<MenuItem selected value={10}>Ten</MenuItem>

Rendering then in:

<li value={10}>Ten</li>

Note that when rendering the property Selected will not be present. The final rendering with Material-UI will look like this:

  <ul onChange={handleChange} value={values.filial}>
    <li value="DEFAULT" disabled>Choose a salutation ...</li>
    <li value={10}>Ten</li> //Renderiza com os estilos de CSS de um elemento selecionado
    <li value={20}>Twenty</li>
    <li value={30}>Thirty</li>
  </ul> 

Note that the component <MenuItem> is transformed into an element <li> child of an element <ul>.

When using the element <option> Material-UI will do the same process, but when identifying the item that is selected, it will forward the same property select to the element we place, in this case <option>.

<option selected value={10}>Ten</option>

In the process of rendering React, it will detect a controlled element marked with Selected, falling so into the scenario where we have an element option with the attribute Selected, generating the aforementioned message.

So:

When using the Select of the Material-UI, always not being marked with the property Native, use <MenuItem> for your options. Otherwise you can normally use the widget <option>.

Another tip regarding the use of React components, if you use a controlled component, avoid using the property defaultValue, use the value to control, instantiating your component with the default option in the value of value.

const [filial, setFilial] = React.useState("DEFAULT")

This helps to avoid some warnings.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.