Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

React - setting input value with JavaScript does not trigger 'onChange'

In my React app (version 15.4.2), I am updating the value of a text input field with JavaScript - however, I have an onChange event listener associated with the input field, and changing the value of the input field does not trigger the handler (good old fashioned typing in the input field does, of course), though the content of the field is correctly updated.

constructor(props) {
    super(props);
    this.onChange = this.onChange.bind(this);
}

onChange(event){
    let attribute = event.target.name;
    let updatedGroup = this.state.group;
    updatedGroup[attribute] = event.target.value;
    this.setState({group: updatedGroup});
}

addMember(memberId) {
    let inputField = document.getElementById("members");
    let inputValues = inputField.value.split(",");
    inputField.value = [...inputValues, memberId];
}

render(){
    <input type="text" id="members" name="members" value={this.state.group.members} onChange={this.onChange} />
}

So when addMember() is called (via button click in a child component), then content of the input field itself is correctly updated, but onChange is not called and thus the state is not updated, etc...

Is there a way that I can programatically set the value of the input field and trigger onChange?

like image 795
skwidbreth Avatar asked Feb 17 '17 03:02

skwidbreth


2 Answers

What I always do in this situation is have your onChange event handler be a function that passes the event data (the character that was entered or the aggregate string) into another function. I put all of the business logic in that function. That way, if I want to invoke the business logic, I just call that method.

Since you are asking "Is there a way that I can programatically set the value of the input field and trigger onChange?" Why not skip onChange and call the business logic function from your function that is programmatically setting the value?

like image 162
joe_coolish Avatar answered Oct 11 '22 05:10

joe_coolish


Onchange method will get triggered only when you type something, if you use document.getElementById and replace its values, it will directly replace the value in DOM, onChange will not get triggered in that case. Since you are using the react, I think you should avoid the direct DOM manipulation.

You are using controlled input, so in addMember method instead of updating the value in DOM, update the state value.

Try this addmember method:

addMember(memberId) {
    //let inputField = document.getElementById("members");
    //let inputValues = inputField.value.split(",");
    //inputField.value = [...inputValues, memberId];

    let group = this.state.group.slice();
    group[members] = group[members] + ',' + memberId;
    this.setState({
        group
    });
}
like image 1
Mayank Shukla Avatar answered Oct 11 '22 04:10

Mayank Shukla