How to set the formik field value with the useState hook? - reactjs

I have a simple form which has only two fields,name and wallet_address, I want the user's to type wallet_address or simply scan the address, once the scan is successful the address will be stored in the state variable, I want to update the wallet_address field with the new state value. Currently this is not working, only manually typing the address is working but not the scanning feature.
import { ErrorMessage, Field, Form, Formik } from "formik";
import ScanQrPopUp from "../components/wallet/popup/ScanQrPopup";
const [walletAddress, setWalletAddress] = useState<any>("");
const handleScanAddress = (wallet: string) => {
console.log("wallet address---", wallet);
setWalletAddress(wallet);
};
const validationSchema = Yup.object().shape({
name: Yup.string()
.min(3, "Name should be atleast 3 characters")
.required("Name is required"),
wallet_address: Yup.string()
.required("Wallet Address is required")
});
<Formik
initialValues={{
name: "",
wallet_address: "",
}}
onSubmit={async (values, { resetForm }) => {
setIsLoading(true);
console.log(values.name);
console.log(values.wallet_address);
setIsLoading(false);
resetForm();
}}
validationSchema={validationSchema}
validateOnChange
>
{({ values, resetForm }) => (
<Form>
<div className="w-[80%]">
<label
className="text-left"
htmlFor="input"
>
Name
</label>
<Field
name="name"
type="text"
spellCheck={false}
className="block"
placeholder="Enter the Name"
/>
<p className="text-red-600">
<ErrorMessage name="name" />
</p>
</div>
<div className="w-[80%] mt-4">
<label
className="text-left"
htmlFor="wallet_address"
>
wallet address
</label>
<Field
name="wallet_address"
type="text"
spellCheck={false}
className="block "
placeholder="Enter wallet address"
/>
<p className="text-red-600 ">
<ErrorMessage name="wallet_address" />
</p>
</div>
</Form>
)}
</Formik>
<ScanQrPopUp
handlePopUp={handleQrPopup}
walletAddress={handleScanAddress}
/>

Related

Form data filled does not show on console using react hooks

I have a form built with formik and yup, but after filling the form, the data did not show on the console and when i clicked the next button, it does not take to the next page.
The validations are working.
.
.
.
const navigate = useNavigate()
const initialValues = {
phone: "",
email: ""
}
const validationSchema = Yup.object({
phone: Yup.string().required('Required'),
email: Yup.string().required('Required').email('Invalid email format'),
})
const onSubmit = values => {
console.log('Form data', values)
navigate("/NextPage")
}
<Formik
initialValues={initialValues}
validationSchema={validationSchema}
onSubmit={onSubmit}>
<Form>
<div className="mb-3">
<label className='form-label'>Phone Number</label><br/>
<Field type='tel' name='phone' className='place-holder white-bg' id='phone'/>
<ErrorMessage name='phone'>
{ (errorMsg) => <div className='error'>{errorMsg}</div> }
</ErrorMessage>
</div>
<div className="mb-3">
<label className='form-label'>Email address(optional)</label><br/>
<Field type='email' name='email' className='place-holder white-bg' id='email'/>
<ErrorMessage name='email'>
{ (errorMsg) => <div className='error'>{errorMsg}</div> }
</ErrorMessage>
</div>
<Button variant="primary" type="submit" className="buy-token-next-btn">
Next
</Button>
</Form>
</Formik>

Yup Was Not Working With Formik and also not provide any type of error

Yup Validation Not Working I Also tried Like This import Yup from 'yup' But Still Not Working.., when I create a simple validate Function without YUP it was worked fine. but when I use YUP that time Validation Not Work.
Added Form Component
import React from 'react';
import { useFormik } from 'formik';
import * as Yup from 'yup';
const initialValues = {
name : "",
surname : "",
address : ""
}
const validateSchema = Yup.object({
name: Yup.string().required('This Field is Required'),
surname: Yup.string().required('This Field is Required'),
address: Yup.string().required('This Field is Required')
});
const onSubmit = values =>{
console.log('FormData->',values);
}
function Form() {
const formik = useFormik({
initialValues ,
onSubmit ,
validateSchema
})
return (
<div className="container x col-md-4 col-md-offset-4" >
<form onSubmit={formik.handleSubmit} >
<div className="form-group">
<input autoComplete="off" onBlur={formik.handleBlur} onChange={formik.handleChange}
value={formik.values.name} name="name" className="name form-control-lg" placeholder="Enter A Name" />
<small>
{formik.touched.name && formik.errors.name ? <div className="error"> {formik.errors.name} </div> : null}
</small>
</div>
<div className="form-group">
<input autoComplete="off" onBlur={formik.handleBlur} onChange={formik.handleChange}
value={formik.values.surname} name="surname" className="surname form-control-lg" placeholder="Enter A Surname" />
<small> { formik.touched.surname && formik.errors.surname ? <div className="error"> {formik.errors.surname} </div> : null} </small>
</div>
<div className="form-group">
<input autoComplete="off" onBlur={formik.handleBlur} onChange={formik.handleChange} value={formik.values.address}
name="address" className="address form-control-lg" placeholder="Enter A Address" />
<small> {formik.touched.address && formik.errors.address ? <div className="error"> {formik.errors.address} </div> : null} </small>
</div>
<button className="btn btn-danger" >Submit</button>
</form>
</div>
)
}
export default Form;
The valid option here is validationSchema not validateSchema. Just set the right one:
const validationSchema = Yup.object({
// ...
});
useFormik({
// ...
validationSchema
})
To use formik and yup, first you have you do npm install yup and npm install formik. if your yarn user then do yarn add formik and yarn add yup.
after that follow this code.
import {Formik} from 'formik';
import * as yup from 'yup';
//functional component am using
export const Auth = () => {
const initialFormValue ={
email: '',password: '',};
const SignInSchema = yup.object().shape({
email: yup.string().email('Invalid Email').required('Email is Required'),
password: yup.string().min(5, 'Too Short').required('Password is Required'),
})
<Formik initialValues={initialFormValue} validationSchema={SignInSchema}
onSubmit={values => console.log(values)}>
{({values, errors, touched, handleChange, handleBlur,
handleSubmit,isSubmitting,
isValid}) => (
<>
<input name='email' type='email' handleChange={handleChange} value=
{values.email} onBlur={handleBlur} label='Email' />
{errors.email && touched.email ? (<Error>{errors.email}</Error>): null}
<input name='password' type='password' handleChange={handleChange} value=
{values.password} onBlur={handleBlur} label='Password' />
{errors.password && touched.password ? (<Error>{errors.password}</Error>):
null}
<button onClick={handleSubmit} type="submit">Send</button>
</>
) }
</Formik>
)}
its not necessary for you to define initial value outside you can do inside formik too <Formik initialValues={email: '', password: ''}> </Formik>
i hope this will help you thank you.

formik rendering an element when input field is clicked in react?

I am trying to make a simple login form i want to render an element when an input field is clicked . I have done this in normal react form by rendering an element by changing the value of a boolean variable to true and when the input is written if the user touch somewhere else then the element disapears . kind of toggle thing . but i don't know hoe to do this in formik. my code looks like this.
import React from "react";
import { Formik } from "formik";
import * as EmailValidator from "email-validator";
import * as Yup from "yup";
const ValidatedLoginForm = () => (
<Formik
initialValues={{ email: "", password: "" }}
onSubmit={(values, { setSubmitting }) => {
console.log(values);
console.log("hello there ");
}}
validationSchema={Yup.object().shape({
email: Yup.string()
.email()
.required("Required"),
password: Yup.string()
.required("No password provided.")
.min(8, "Password is too short - should be 8 chars minimum.")
.matches(/(?=.*[0-9])/, "Password must contain a number.")
})}>
{props => {
const {
values,
touched,
errors,
isSubmitting,
handleChange,
handleBlur,
handleSubmit
} = props;
return (
<div className="container">
<div className="row">
<form onSubmit={handleSubmit}>
<br />
<input
name="email"
type="text"
placeholder="Enter your email"
value={values.email}
onChange={handleChange}
onBlur={handleBlur}
className={errors.email && touched.email && "error"}
/>
<br />
<br />
{errors.email && touched.email && (
<div className="input-feedback">{errors.email}</div>
)}
<br />
<input
name="password"
type="password"
placeholder="Enter your password"
value={values.password}
onChange={handleChange}
onBlur={handleBlur}
className={errors.password && touched.password && "error"}
/> <br />
<br />
{errors.password && touched.password && (
<div className="input-feedback">{errors.password}</div>
)}
<button type="submit" disabled={isSubmitting}>
Login
</button>
</form>
</div>
<div className="row">
<button className="btn btn-default">Value</button>
</div>
</div>
);
}}
Maybe this will help you. Try to add function to onBlur prop then handle handleBlur function.
onBlur={(e) => {
handleBlur(e);
// here handle component showing
}}

onchange in a form using formik the value of the field is not updated

I'm new to react, and I'm trying to apply validations to a form.
For some reason when adding the property:
onChange={onChange}
I want to send the values to the parent component. That's why I'm using the onchange.
Nothing I write is shown in my text fields, why does this happen?
export const Son = props => {
const { onChange } = props;
return (
<Formik
initialValues={{
fullname: "",
email: ""
}}
validationSchema={Yup.object().shape({
fullname: Yup.string()
.min(2, "Your name is too short")
.required("Please enter your full name"),
email: Yup.string()
.email("The email is incorrect")
.required("Please enter your email")
})}
onSubmit={(values, { setSubmitting }) => {
const timeOut = setTimeout(() => {
console.log(values);
setSubmitting(false);
clearTimeout(timeOut);
}, 1000);
}}
>
{({
values,
errors,
touched,
handleSubmit,
isSubmitting,
validating,
valid
}) => {
return (
<Form name="contact" method="post" onSubmit={handleSubmit}>
<label htmlFor="fullname">
Fullname
<Field
type="text"
name="fullname"
autoComplete="name"
placeholder="your fullname"
onChange={onChange}
/>
</label>
{<ErrorMessage name="fullname">{msg => <p>{msg}</p>}</ErrorMessage>}
{/*errors.fullname && touched.fullname && <p>{errors.fullname}</p>*/}
<br />
<label htmlFor="email">
Email
<Field
type="email"
name="email"
autoComplete="email"
placeholder="your email"
onChange={onChange}
/>
</label>
<ErrorMessage name="email">{msg => <p>{msg}</p>}</ErrorMessage>
<br />
<button type="submit" disabled={!valid || isSubmitting}>
{isSubmitting ? `Submiting...` : `Submit`}
</button>
</Form>
);
}}
</Formik>
);
};
this is my live code:
https://stackblitz.com/edit/react-qotvwb?file=components/son_component.js
you're not using the formik handleChange at all.
I highlighted the changes that I made in https://stackblitz.com/
and you can test this working here

Submitting Formik form data to firebase database in react

I am trying to figure out how to send form data form a Formik form to a Firebase database in my react app.
I have a form as follows:
import React from 'react'
import { Link } from 'react-router-dom'
// import { Formik } from 'formik'
import { Formik, Form, Field, ErrorMessage, withFormik } from 'formik';
import * as Yup from 'yup';
import { Badge, Button, Col, Feedback, FormControl, FormGroup, FormLabel, InputGroup } from 'react-bootstrap';
import Select from 'react-select';
import firebase from '../../../firebase';
const style1 = {
width: '60%',
margin: 'auto'
}
const style2 = {
paddingTop: '2em',
}
const style3 = {
marginRight: '2em'
}
const style4 = {
display: 'inline-block'
}
const options = [
{ value: 'author', label: 'Author' },
{ value: 'reviewer', label: 'Reviewer' },
];
class Basic extends React.Component {
state = {
selectedOption: null,
}
handleChange = (selectedOption) => {
this.setState({ selectedOption });
console.log(`Option selected:`, selectedOption);
}
render() {
const { selectedOption } = this.state;
return (
<Formik
initialValues={{
firstName: '',
lastName: '',
email: '',
password: '',
confirmPassword: '',
selectedOption: null
}}
validationSchema={Yup.object().shape({
firstName: Yup.string()
.required('First Name is required'),
lastName: Yup.string()
.required('Last Name is required'),
email: Yup.string()
.email('Email is invalid')
.required('Email is required'),
selectedOption: Yup.string()
.required('It will help us get started if we know a little about your background'),
password: Yup.string()
.min(6, 'Password must be at least 6 characters')
.required('Password is required'),
confirmPassword: Yup.string()
.oneOf([Yup.ref('password'), null], 'Passwords must match')
.required('Confirm Password is required')
})}
// onSubmit={fields => {
// alert('SUCCESS!! :-)\n\n' + JSON.stringify(fields, null, 5))
// }}
// onSubmit={handleSubmit}
render={({ errors, status, touched }) => (
<Form style={style1}>
<h1 style={style2}>Get Started</h1>
<div className="form-group">
<label htmlFor="firstName">First Name</label>
<Field name="firstName" type="text" className={'form-control' + (errors.firstName && touched.firstName ? ' is-invalid' : '')} />
<ErrorMessage name="firstName" component="div" className="invalid-feedback" />
</div>
<div className="form-group">
<label htmlFor="lastName">Last Name</label>
<Field name="lastName" type="text" className={'form-control' + (errors.lastName && touched.lastName ? ' is-invalid' : '')} />
<ErrorMessage name="lastName" component="div" className="invalid-feedback" />
</div>
<div className="form-group">
<label htmlFor="email">Email</label>
<Field name="email" type="text" placeholder="Please use your work email address" className={'form-control' + (errors.email && touched.email ? ' is-invalid' : '')} />
<ErrorMessage name="email" component="div" className="invalid-feedback" />
</div>
<div className="form-group">
<label htmlFor="password">Password</label>
<Field name="password" type="password" className={'form-control' + (errors.password && touched.password ? ' is-invalid' : '')} />
<ErrorMessage name="password" component="div" className="invalid-feedback" />
</div>
<div className="form-group">
<label htmlFor="confirmPassword">Confirm Password</label>
<Field name="confirmPassword" type="password" className={'form-control' + (errors.confirmPassword && touched.confirmPassword ? ' is-invalid' : '')} />
<ErrorMessage name="confirmPassword" component="div" className="invalid-feedback" />
</div>
<div className="form-group">
<label htmlFor="selectedOption">Which role best describes yours?</label>
<Select
value={selectedOption}
onChange={this.handleChange}
options={options}
/>
</div>
<div className="form-group" >
<label htmlFor="consent">By registering you accept the <Link to={'/Terms'}>Terms of Use</Link> and <Link to={'/Privacy'}>Privacy Policy</Link> </label>
</div>
<div className="form-group">
<Button variant="outline-primary" type="submit" style={style3} id="submitRegistration">Register</Button>
</div>
</Form>
)}
/>
);
}
}
export default Basic;
I have a database in firebase (cloud firestore) with a collection called Registrations that has fields named the same as each of these form fields.
I have spent the day following tutorials that seem to be made for react before Formik. There's not much point to showing all the things I've tried and failed at for the day - they're clearly not written with Formik in mind. I can't find a way to write the onSubmit so that Formik can give the data to Firebase.
Has anyone found a current tutorial or know how to do this?
I've used Formik and Firebase in this Open-Source React project. Maybe this is what you're looking for :)
Expertizo React Native Kit

Resources