Here's my code so far (just the relevant parts, and I'm also using availity-reactstrap-validation just FYI):
export default class CustomModal extends Component {
constructor(props) {
super(props);
this.state = {
data: [],
toolPlatform: [],
workstream: [],
opsarea: [],
campus: [],
riskcat: [],
activeItem: this.props.activeItem,
validate: {
textState: '',
},
};
}
validateText(e) {
const textRex = /^(?!\s*$).+/;
const { validate } = this.state
if (textRex.test(e.target.value)) {
validate.textState = 'has-success'
} else {
validate.textState = 'has-danger'
}
this.setState( {validate})
};
render() {
const { toggle, onSave } = this.props;
return (
<Modal isOpen={true} toggle={toggle}>
<ModalHeader toggle={toggle}> Tool Details </ModalHeader>
<ModalBody>
<AvForm onValidSubmit = {() => onSave(this.state.activeItem)}>
<FormGroup>
<Label for="title">Title</Label>
<AvInput valid
type="text"
name="title"
value={this.state.activeItem.title}
//onChange={this.handleChange}
placeholder="Tool Name"
valid={ this.state.validate.textState === 'has-success' }
invalid={ this.state.validate.textState === 'has-danger' }
onChange={ (e) => {
this.validateText(e)
this.handleChange(e)
}}
required
/>
</FormGroup>
<AvGroup>
<Label for="description">Description</Label>
<AvInput valid
type="text"
name="description"
value={this.state.activeItem.description}
valid={ this.state.validate.textState === 'has-success' }
invalid={ this.state.validate.textState === 'has-danger' }
placeholder="Tool description"
onChange={ (e) => {
this.validateText(e)
this.handleChange(e)
}}
required
/>
The validation works, however when I start typing in one of the fields, both fields are validated at the same time. This makes sense, and I get why it's doing it, but I'm not 100% sure how to change the syntax to only validate the fields I'm typing in.
Hope that makes sense! I'm sure it's fairly basic to change, I'm just new, and learning, so I can't quite get the right syntax.
Thanks a lot!
First, you need two different fields for your textState, otherwise they share the same:
this.state = {
data: [],
toolPlatform: [],
workstream: [],
opsarea: [],
campus: [],
riskcat: [],
activeItem: this.props.activeItem,
validate: {
textState: {
title: '',
description: '',
},
},
};
Then check e.target.name to determine which field of textState to update (you could also pass it as an argument in this function)
validateText ( e ) {
const textRex = /^(?!\s*$).+/;
// If test is true / false
const fieldTextState = textRex.test( e.target.value ) ? 'has-success' : 'has-danger'
// Create textState object with all the fields
const textState = Object.assign( {}, this.state.validate.textState, { [ e.target.name ]: fieldTextState})
this.setState( { validate : { textState } } )
};
Also, set specific valid and invalid for each input
<AvInput valid
type="text"
name="title"
value={ this.state.activeItem.title }
//onChange={this.handleChange}
placeholder="Tool Name"
valid={ this.state.validate.textState.title === 'has-success' }
invalid={ this.state.validate.textState.title === 'has-danger' }
onChange={ ( e ) => {
this.validateText( e )
this.handleChange( e )
} }
required
/>
and
<AvInput valid
type="text"
name="description"
value={ this.state.activeItem.description }
valid={ this.state.validate.textState.description === 'has-success' }
invalid={ this.state.validate.textState.description === 'has-danger' }
placeholder="Tool description"
onChange={ ( e ) => {
this.validateText( e )
this.handleChange( e )
} }
required
/>