在模糊和单击按钮时反应验证
React validation on blur and on button click
我有多步表单,我想进行必要的输入。验证应处于模糊状态并单击“下一步”按钮。 On blur 按预期工作,但我在验证按钮单击时遇到问题。像下面这样,不管填不填,我都不进行下一步,不知道怎么解决。
在一个文件中我有:
import React, { Component } from 'react';
import PersonalDetails from './PersonalDetails';
import CourseDetails from './CourseDetails';
class Form extends Component {
state = {
step: 1,
firstname: '',
lastname: '',
isError: {
firstName: true,
lastName: true
},
errorMessage: {
firstName: '',
lastName: ''
}
};
nextStep = () => {
const { step } = this.state;
this.setState({
step: step + 1
})
}
handleChange = input => e => {
this.setState({
[input]: e.target.value
})
if (input === 'firstname') {
if (this.state.firstname.length >= 1) {
this.setState({
isError: {...this.state.isError, firstName: false}
})
}
}
else if (input === 'lastname') {
if (this.state.lastname.length >= 1) {
this.setState({
isError: {...this.state.isError, lastName: false}
})
}
}
}
validateFirstName = () => {
if (this.state.firstname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, firstName: 'Type your first name (at least 2 characters)'},
isError: {...this.state.isError, firstName: true}
});
}
}
validateLastName = () => {
if (this.state.lastname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, lastName: 'Type your last name (at least 2 characters)'},
isError: {...this.state.isError, lastName: true}
});
}
}
render() {
const {
step,
firstname,
lastname,
errorMessage,
isError
} = this.state;
switch(step) {
case 1:
return (
<PersonalDetails
nextStep={this.nextStep}
handleChange={this.handleChange}
firstname={firstname}
lastname={lastname}
validateFirstName={this.validateFirstName}
validateLastName={this.validateLastName}
errorMessage={errorMessage}
isError={isError}
/>
)
case 2:
return (
<CourseDetails />
)
default: return null
}
}
}
export default Form;
在其他文件中:
class PersonalDetails extends Component {
continue = e => {
e.preventDefault();
this.props.validateFirstName();
this.props.validateLastName();
if (!this.props.isError.firstName && !this.props.isError.lastName) {
this.props.nextStep();
}
}
render() {
const {
firstname,
lastname,
handleChange,
validateFirstName,
validateLastName,
errorMessage,
isError
} = this.props;
return (
<div>
<form>
<div>
<div>
<label htmlFor='first name'>
First name
</label>
<input type='text' value={firstname} name='first name' onChange={handleChange('firstname')} onBlur={validateFirstName} />
<p>{isError.firstName && errorMessage.firstName}</p>
</div>
<div>
<label htmlFor='last name'>
Last name
</label>
<input type='text' value={lastname} name='last name' onChange={handleChange('lastname')} onBlur={validateLastName} />
<p>{isError.lastName && errorMessage.lastName}</p>
</div>
<div>
<button onClick={this.continue}>Next</button>
</div>
</form>
</div>
)
}
}
export default PersonalDetails;
CourseDetails 让我们假设它现在是空白页面:
class CourseDetails extends Component {
render() {
return (
<div>
</div>
)
}
}
export default CourseDetails;
由于 React 状态更新是异步的(它们不会立即应用),因此道具不会在您执行验证后立即更改。最简单的方法是 return 验证器的验证结果,如下所示:
validateFirstName = () => {
if (this.state.firstname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, firstName: 'Type your first name (at least 2 characters)'},
isError: {...this.state.isError, firstName: true}
});
return false;
}
return true;
}
validateLastName = () => {
if (this.state.lastname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, lastName: 'Type your last name (at least 2 characters)'},
isError: {...this.state.isError, lastName: true}
});
return false;
}
return true;
}
然后你可以用它来决定你是否应该继续下一步:
continue = e => {
e.preventDefault();
const isFirstNameValid = this.props.validateFirstName();
const isLastNameValid = this.props.validateLastName();
if (isFirstNameValid && isLastNameValid) {
this.props.nextStep();
}
}
我会尝试不同的方法。我不会调用验证函数,然后立即尝试检查错误,而是提取验证本身,并将其用于单一职责。查看您当前的代码:
continue = e => {
e.preventDefault();
this.props.validateFirstName(); // You set / clear the errors in Form state
this.props.validateLastName(); // You set / clear the errors in Form state
if (!this.props.isError.firstName && !this.props.isError.lastName) { // You expect to have that exact state which you've just updated in 2 lines above
this.props.nextStep();
}
}
this.props.isError
不会立即在您的函数中更新,您刚刚在其中调用了另外 2 个更新它的函数。在第二次调用该函数时会很明显。
让我们尝试这样切换:
continue = e => {
e.preventDefault();
if (firstname.length < 2 || lastname.length < 2) {
this.props.validateFirstName();
this.props.validateLastName();
} else {
this.props.nextStep();
}
}
这种方法还需要您添加 firstname
和 lastname
道具。
我有多步表单,我想进行必要的输入。验证应处于模糊状态并单击“下一步”按钮。 On blur 按预期工作,但我在验证按钮单击时遇到问题。像下面这样,不管填不填,我都不进行下一步,不知道怎么解决。
在一个文件中我有:
import React, { Component } from 'react';
import PersonalDetails from './PersonalDetails';
import CourseDetails from './CourseDetails';
class Form extends Component {
state = {
step: 1,
firstname: '',
lastname: '',
isError: {
firstName: true,
lastName: true
},
errorMessage: {
firstName: '',
lastName: ''
}
};
nextStep = () => {
const { step } = this.state;
this.setState({
step: step + 1
})
}
handleChange = input => e => {
this.setState({
[input]: e.target.value
})
if (input === 'firstname') {
if (this.state.firstname.length >= 1) {
this.setState({
isError: {...this.state.isError, firstName: false}
})
}
}
else if (input === 'lastname') {
if (this.state.lastname.length >= 1) {
this.setState({
isError: {...this.state.isError, lastName: false}
})
}
}
}
validateFirstName = () => {
if (this.state.firstname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, firstName: 'Type your first name (at least 2 characters)'},
isError: {...this.state.isError, firstName: true}
});
}
}
validateLastName = () => {
if (this.state.lastname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, lastName: 'Type your last name (at least 2 characters)'},
isError: {...this.state.isError, lastName: true}
});
}
}
render() {
const {
step,
firstname,
lastname,
errorMessage,
isError
} = this.state;
switch(step) {
case 1:
return (
<PersonalDetails
nextStep={this.nextStep}
handleChange={this.handleChange}
firstname={firstname}
lastname={lastname}
validateFirstName={this.validateFirstName}
validateLastName={this.validateLastName}
errorMessage={errorMessage}
isError={isError}
/>
)
case 2:
return (
<CourseDetails />
)
default: return null
}
}
}
export default Form;
在其他文件中:
class PersonalDetails extends Component {
continue = e => {
e.preventDefault();
this.props.validateFirstName();
this.props.validateLastName();
if (!this.props.isError.firstName && !this.props.isError.lastName) {
this.props.nextStep();
}
}
render() {
const {
firstname,
lastname,
handleChange,
validateFirstName,
validateLastName,
errorMessage,
isError
} = this.props;
return (
<div>
<form>
<div>
<div>
<label htmlFor='first name'>
First name
</label>
<input type='text' value={firstname} name='first name' onChange={handleChange('firstname')} onBlur={validateFirstName} />
<p>{isError.firstName && errorMessage.firstName}</p>
</div>
<div>
<label htmlFor='last name'>
Last name
</label>
<input type='text' value={lastname} name='last name' onChange={handleChange('lastname')} onBlur={validateLastName} />
<p>{isError.lastName && errorMessage.lastName}</p>
</div>
<div>
<button onClick={this.continue}>Next</button>
</div>
</form>
</div>
)
}
}
export default PersonalDetails;
CourseDetails 让我们假设它现在是空白页面:
class CourseDetails extends Component {
render() {
return (
<div>
</div>
)
}
}
export default CourseDetails;
由于 React 状态更新是异步的(它们不会立即应用),因此道具不会在您执行验证后立即更改。最简单的方法是 return 验证器的验证结果,如下所示:
validateFirstName = () => {
if (this.state.firstname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, firstName: 'Type your first name (at least 2 characters)'},
isError: {...this.state.isError, firstName: true}
});
return false;
}
return true;
}
validateLastName = () => {
if (this.state.lastname.length < 2) {
this.setState({
errorMessage: {...this.state.errorMessage, lastName: 'Type your last name (at least 2 characters)'},
isError: {...this.state.isError, lastName: true}
});
return false;
}
return true;
}
然后你可以用它来决定你是否应该继续下一步:
continue = e => {
e.preventDefault();
const isFirstNameValid = this.props.validateFirstName();
const isLastNameValid = this.props.validateLastName();
if (isFirstNameValid && isLastNameValid) {
this.props.nextStep();
}
}
我会尝试不同的方法。我不会调用验证函数,然后立即尝试检查错误,而是提取验证本身,并将其用于单一职责。查看您当前的代码:
continue = e => {
e.preventDefault();
this.props.validateFirstName(); // You set / clear the errors in Form state
this.props.validateLastName(); // You set / clear the errors in Form state
if (!this.props.isError.firstName && !this.props.isError.lastName) { // You expect to have that exact state which you've just updated in 2 lines above
this.props.nextStep();
}
}
this.props.isError
不会立即在您的函数中更新,您刚刚在其中调用了另外 2 个更新它的函数。在第二次调用该函数时会很明显。
让我们尝试这样切换:
continue = e => {
e.preventDefault();
if (firstname.length < 2 || lastname.length < 2) {
this.props.validateFirstName();
this.props.validateLastName();
} else {
this.props.nextStep();
}
}
这种方法还需要您添加 firstname
和 lastname
道具。