Search code examples
reactjsinputuser-inputreact-bootstraperase

Unable to delete value character from input reactjs


I cannot seem to delete the last character of the value I input.

For example: I will type in the input field: "syEmail@mail.com" and want to delete it all to rewrite it. I can backspace all of them without a problem, untill I get to the last character. So the input field now has: "s".

p.s. I am using react-bootstrap validation on top of the validation I wrote myself. This problem started when I wrote the conditional of the value field beïng empty in handleChange.

I have deleted all of the other code to hopefully help get a clear picture of what is going on. If I'm missing something please let me know.

The const below have more than just these objects, but for this problem its not relevant. :

const [validation, setValidation] = useState({email: "notActive"}); 
const [messages, setMessages] = useState({ errormessageEmail: '' });
const [account, setAccount] = useState({ createEmail: ""});

useEffect to validate if the email has the right characters

    useEffect(() => {
        if (validation.email === "active") {
            let err = '';
            const emailRegex = new RegExp("[^\\.\\s@:](?:[^\\s@:]*[^\\s@:\\.])?@[^\\.\\s@]+(?:\\.[^\\.\\s@]+)+(?:\\.[^\\.\\s@]+)*");
            if (emailRegex.test(account.createEmail)) {
                err = false;
                setMessages(prevState => ({ ...prevState, errormessageEmail: err }))
                setValidation(prevState => ({ ...prevState, email: true }));
            } else {
                err = <div className="text-start">{translated.errorMail}</div>
                setMessages(prevState => ({ ...prevState, errormessageEmail: err }))
                setValidation(prevState => ({ ...prevState, email: false }));
            }
        }
    }, [account.createEmail, validation.email, translated.errorMail]);

handleChange:

        const handleChange = (e, i) => {
            const { name, value, type } = e.target;
                if (name === 'createEmail') {
                    if (value === '') {
                        setValidation(prevState => ({ ...prevState, email: false }));
                    } else {
                        setAccount(prevState => ({ ...prevState, [name]: value }));
                        setValidation(prevState => ({ ...prevState, email: "active" }));
                    }
                }
        }

inputfield:

                                        <Form.Group as={Row}>
                                            <Form.Control
                                                name="createEmail"
                                                type="email"
                                                className={validation.email === true ? "form-control is-valid" : validation.email === false || validation.email === "active" ? "form-control is-invalid" : null}
                                                placeholder={props.t('login:CreateEmail')}
                                                value={account.createEmail}
                                                onChange={(e) => handleChange(e)}
                                                required />
                                            {messages.errormessageEmail ?
                                                < Alert className="no-margin-bttm nav-button-full" variant="danger">{messages.errormessageEmail}</Alert>
                                                : null}
                                        </Form.Group>

Can anyone please tell me why it's working like this? Thanks in advance!


Solution

  • Your input field has the value account.createEmail. This value was initialized by useState with an empty string. It can later on be changed with the method setAccount.

    However, this method is not called in handleChange listener in case that value === ''.

    That explains why internal state is not updated and the input field cannot reflect any changes.