vue element-ui vant-ui vue vee-validate 组件库 纯原生 Input formik
import React, { useState } from 'react'
// import Icon from '@/components/Icon'
import styles from './index.module.scss'
import NavBar from '@/components/NavBar'
import Input from '@/components/Input'
import { useFormik } from 'formik'
// 表单验证的包
import * as Yup from 'yup'
import classNames from 'classnames'
import { useDispatch } from 'react-redux'
import { sendCode, login } from '@/store/action/login'
import { Toast } from 'antd-mobile'
import { useHistory } from 'react-router'
export default function Login() {
const history = useHistory()
const dispatch = useDispatch()
// 发送验证码之后倒计时点击按钮
const [time, setTime] = useState(0)
// 点击发送验证码请求
const onExtraClick = async () => {
if (time > 0) return
if (!/^1[3-9]\d{9}$/.test(mobile)) {
formik.setTouched({
mobile: true,
})
return
}
await dispatch(sendCode(mobile))
Toast.success('获取验证码成功', 1)
// 开启倒计时
setTime(60)
let timeId = setInterval(() => {
setTime((time) => {
if (time === 1) {
clearInterval(timeId)
}
return time - 1
})
}, 1000)
}
const formik = useFormik({
initialValues: {
mobile: '',
code: '',
},
// 当表单提交时会触发
async onSubmit(values) {
await dispatch(login(values))
Toast.success('登陆成功')
history.push('/home')
},
validationSchema: Yup.object({
mobile: Yup.string()
.required('手机号不能为空')
.matches(/^1[3-9]\d{9}$/, '手机号格式错误'),
code: Yup.string()
.required('验证码不能为空')
.matches(/^\d{6}$/, '手机号格式错误'),
}),
//原生书写很麻烦
// validate(values) {
// const errors = {}
// if (!values.mobile) {
// errors.mobile = '手机号不能为空'
// }
// if (!values.code) {
// errors.code = '验证码不能为空'
// }
// return errors
// },
})
const {
values: { mobile, code },
handleChange,
handleSubmit,
handleBlur,
touched,
errors,
isValid,
} = formik
return (
<div className={styles.root}>
<NavBar>登录</NavBar>
<div className="content">
{/* 标题 */}
<h3>短信登录</h3>
<form onSubmit={handleSubmit}>
{/* 手机号输入框 */}
<div className="input-item">
<Input
maxLength={11}
className="input"
name="mobile"
placeholder="请输入手机号"
onChange={handleChange}
onBlur={handleBlur}
value={mobile}
autoComplete="off"
/>
{touched.mobile && errors.mobile ? (
<div className="validate">{errors.mobile}</div>
) : null}
</div>
{/* 短信验证码输入框 */}
<div className="input-item">
<Input
placeholder="请输入验证码"
extra={time === 0 ? '获取验证码' : time + 's后获取'}
maxLength={6}
onExtraClick={onExtraClick}
onChange={handleChange}
name="code"
value={code}
onBlur={handleBlur}
autoComplete="off"
></Input>
{touched.code && errors.code ? (
<div className="validate">{errors.code}</div>
) : null}
</div>
{/* 登录按钮 */}
<button
type="submit"
className={classNames('login-btn', { disabled: !isValid })}
disabled={!isValid}
>
登录
</button>
</form>
</div>
</div>
)
}