Reactjs material ui textfield number max and min

Viewed 7391

Registrazione schermo 2020-11-20 alle 17 21 03

I have an input field which should only take values between min and max.

I did as shown below, but entering the number manually as seen in the image bypasses the control.

How can I do?

Link: codesandbox

<TextField
          id="outlined-number"
          label="Number max number 10"
          type="number"
          InputProps={{ inputProps: { min: "0", max: "10", step: "1" } }}
          variant="outlined"
          handleChange('number')
        />

My handleChange:

const handleChange = field => ({ target: { value } }) => {
        setState(prev => {
            const _item = prev.item;
            _item[field] = value;
            return { ...prev, item: _item };
        });
    };

handleChange('nameAttr')
4 Answers

Maybe a little late but it worked for me

const minValue = 0  //Or whichever number you want
const maxValue = 10
const [value, setValue] = useState(minValue)

//Executes when the value changes
const handle = (e) => {
    const newValue = Math.min(Math.max(e.target.value, minValue), maxValue)
    setValue(previousValue => newValue)
}

Then in yout TextField you do...

    <TextField
      id="outlined-number"
      label="Number max number 10"
      type="number"
      variant="outlined"
      handleChange(e => handle(e))
      value={value}
    />

set a function to onChange of the text input

set a state of the number

const [number, setNumber] = useState('');

set the value of the text input to the number and then add the onChange event

<TextField
    ....
    onChange={validateNumber}
    value={number}
/>

const validateNumber = (event) => {
  const value = event.target.value;
  const setValue = value <= 10 ? value : number; //if the input value is greater than 10, then don't change the input value
  setNumber(setValue);
};

Updated Example

https://codesandbox.io/s/material-demo-forked-hxflw?file=/demo.js

Use onBlur or onChange to adjust your value to your max.

Using your onChange:

const handleChange = field => ({ target: { value } }) => {
    setState(prev => {
        const _item = prev.item;
        _item[field] = parseInt(value) > 10 ? "10" : value;
        return { ...prev, item: _item };
    });
};

You can use the TextField as a controlled component to prevent the input to be more than 10. You should also use an additional state variable for that.

The code is as follows (Replace the component with the component given below and import useEffect additionally)

export default function FormPropsTextFields() {
  const classes = useStyles();
  
  const [value, setValue] = useState();

  function handler(e) {
    if (Number(e.target.value) > 10) {
      setValue(10);
    }else{
      setValue(e.target.value);
    }
  }

  return (
    <form className={classes.root} noValidate autoComplete="off">
      <div>
        <TextField
          id="outlined-number"
          label="Number max number 10"
          type="number"
          InputProps={{ inputProps: { min: "0", max: "10", step: "1" } }}
          variant="outlined"
          onChange={handler}
          value={value}
        />
      </div>
    </form>
  );
}

So if the input value is more than 10, it prevents updating the state variable value thanks to our logic in the handler function. This is not the best solution and you may want to build upon you logic based on this example.

Related