I have two input form divs. After clicking register button I want to show the second div where the user can confirm registration. Before the code in RegisterFormInputs function was in the sign-up div and I was able to type in the input fields. Then I moved it into a sepratate function in order to be able to show and hide the div. Now I cannot write anything in the inputs. Why is this happening? How can I solve this?
function RegisterForm() {
const [registerInputValues, setRegisterInputValues] = useState({
email: '', password: ''
});
const [showRegisterForm, setShowRegisterForm] = useState(true);
const [showRegisterVerificationForm, setShowRegisterVerificationForm] = useState(false);
const handleRegisterOnChange = event => {
const { name, value } = event.target;
setRegisterInputValues({ ...registerInputValues, [name]: value });
};
const register = () => {
studentsService.registerStudent(registerInputValues)
.then(response => {
console.log(response);
})
.catch(e => {
console.log(e);
});
setShowRegisterForm(false);
setShowRegisterVerificationForm(true);
}
const confirmRegistration = () => {
studentsService.confirmRegistration(confirmationToken)
.then(response => {console.log(confirmationToken, response)
})
.catch(e => {console.log(e); alert(e.response.data);});
}
const RegisterFormInputs = () => {
return <div>
<h2 className="loginElement">Create profile</h2>
<label className="loginElement">
<span className="loginElement">Email</span>
<input type="email" name="email" className="loginElement" onChange={handleRegisterOnChange} />
</label>
<label className="loginElement">
<span className="loginElement">Password</span>
<input type="password" name="password" className="loginElement" onChange={handleRegisterOnChange} />
</label>
<button type="button" className="submit" onClick={register}>Register</button>
</div>
}
const RegisterVerificationForm = () => {
return <div className="verify-registration">
<h2 className="loginElement text-center">Activate your profile</h2>
<div className="d-flex justify-content-center align-items-center">
<TextField id="outlined-basic" label="Verification token" variant="outlined" onChange={handleTokenOnChange} />
<Timer initialMinutes={10}/>
</div>
<div className="mt-3 text-center">
<Button variant="contained" onClick={confirmRegistration}>Submit</Button>
</div>
</div>;
}
return (
<>
<div className="cont mt-5">
<div className="sub-cont">
<div className="form sign-up">
{showRegisterForm ? <RegisterFormInputs /> : null}
{showRegisterVerificationForm ? <RegisterVerificationForm /> : null}
</div>
</div>
</div>
</>
)
}
export default RegisterForm;
CodePudding user response:
I guess you should try to control values of inputs, like this:
<input value={registerInputValues.email} type="email" name="email" className="loginElement" onChange={handleRegisterOnChange} />
CodePudding user response:
I would use useRef() in the handler function and set the state on the register/submit to ref.current. Currently every input change is causing a re-render which is why it's so jumpy.
const formRef = useRef("")
const handleRegisterOnChange = (event) => {
formRef.current = event;
//You can see the ref updates when typing, but without a re-render
console.log(formRef.current);
};
Drilled in to the event.target.value in the input
<input
type="email"
name="email"
className="loginElement"
onChange={(event) => handleRegisterOnChange(event.target.value)}
/>
I don't have all of the context for everything but in your register function it may be something like this:
const register = () => {
studentsService
.registerStudent(formRef.current)
etc.....