Is saying event handler the same as saying state-changing method?

Question

Is saying event handler the same as saying state-changing method?

Answer

Not quite. They can be related but they are not the same. When we talk about event handlers, it sometimes involves an HTML element that directly interacts with the user, like a button or an input form, but it can also be a JavaScript function that checks for a specific interaction with or from the page, like a keyboard key press, a page load, page scroll, or leaving a page. For Example:
let’s say we have a button:

...
render(){
  return(
    <div>
      <button> click me! </button>
    </div>
  )
}

Now, because we want something to happen we attach an event handler, which is a method that will track every time the button is clicked:

...
checkClick(e){ // because in React an onClick attribute 
  //provides us with an event object, we will console.log it
  console.log( " button has been click, and this is the event object:", e);
}

render(){
  return(
    <div>
      <button onClick= { this.checkClick }> click me! </button> 
    </div>
  )
}

With the addition of the method in the onClick attribute, we have created an event listener, that method is now connected to the button and it will be trigger every time the button is clicked thus console logging the message and the event object.

Talking about a state-changing method can only involve a change of state from within the app and it could also be a response to another method being called. It relates to event handlers because React is user center, being a front-end library, it is meant to relate to the interaction with the window and the components. For example:

...
class App extends Component {
  constructor(){
    super()
    this.state = {
      counter: 0
    };
    this.updateCounter = this.updateCounter.bind(this);
    this.counterCaller = this.counterCaller.bind(this);
  }
  
  updateCounter(){  //we are creating a method that will update our state
   let newNum = this.state.counter+1; //we will increase the number by one
    this.setState({
      counter: newNum
    });
    console.log("counter is: ", this.state.counter);
  }

  counterCaller(id){
    if(this.state.counter !== 30){ // we want to make sure counter is less than 30
     this.updateCounter();
    } else{
       console.log( "Counter ended at 30. counter reset!" ); 
     clearInterval(id); //once it is 30 we will finish the count
      this.setState({
        counter: 0  //and reset it
      });
    }
  }
  
  componentDidMount(){ //calling a method from React that checks if the component 
  //was rendered. 
  //we will take advantage of it and use it to call our method:
     let intervalId = setInterval( () => {this.counterCaller(intervalId)}, 2000); //set interval will call the function passed in intervals of the amount of time passed as the second parameter
//note: we need to pass the setInterval id to our function to be able to stop the counter,
// and we need to do it inside the set interval function for them to be connected and for our if statement check to remain relevant
  }

  render(){
    return <p> {this.state.counter} </p>;
  }
...

In the last example we created some state that we decided to update (change), based on time and an amount condition, the state-changing methods only interact with one another and they are called by another method. We are not handling any events with the exception of the rendering of the component itself. With this, we can conclude that event handlers and state-changing methods are not the same but can be related, since one can trigger the other.

5 Likes

There are bugs in the snippets given.

1- an if statement should be used instead of a while, otherwise, the time cannot pass by in setTimeOut
// while (this.state.counter <= 30) {
if (this.state.counter <= 30) {

consequently, at the end of updateCounter, a call to this.counterCaller() should be made

2- These lines are wrong

newNum = counter++; //we will increase the number by one
    this.setState({
      counter: newNum
    });

it should be replaced by
let newNum = this.state.counter+1; //we will increase the number by one
this.setState({
counter: newNum
});

there is both a problem of scope: this.state.counter instead of counter
and a problem of syntax
counter++ is equivalent to counter=counter+1
thus assigning newNum to counter++ doesnt make any sense

3- the first argument to setTimeout should be a function, not a value. Thus
setTimeout( this.updateCounter(), 2000);
should be replaced by
setTimeout( this.updateCounter, 2000);

Please test out your code before posting it here,
Anthony

6 Likes

Thank you for bringing this up, I am sorry I even posted something so buggy. I had adjusted and actually opted to what it was supposed to be from the beginning: setInterval, not setTimeout which we can also opt in to set the id on state if desired which might make it cleaner, yet it would depend on how much state we are storing if the use of it were to be implemented.

3 Likes