Introduction To State And Lifecycle (React) - Zero To Hero Series - Part Four

This is the fourth article in ReactJS – Zero to Hero Series. I will recommend reading the first three articles (link given below), before going through this article.

In this article, we will see what State and Lifecycle are in React.

  • React support a feature state that is similar to props, but it is private and fully controlled by the component.
  • This feature is typically available to components defined as classes since they can support a local state which is completely controlled by the component.

So far, we have only learned one way to update the UI. We call ReactDOM.render() to change the rendered output.

Now, we will create a Clock component and we will learn how to make the Clock component truly reusable and encapsulated. It will set up its own timer and update itself every second.

We can write a Clock component which will be called from the function tick(), as shown below,

  1. function Clock(props) {  
  2.   return (  
  3.     <div>  
  4.       <h1>Hello, world!</h1>  
  5.       <h2>It is {props.date.toLocaleTimeString()}.</h2>  
  6.     </div>  
  7.   );  
  8. }  
  9.   
  10. function tick() {  
  11.   ReactDOM.render(  
  12.     <Clock date={new Date()} />,  
  13.     document.getElementById('root')  
  14.   );  
  15. }  
  16.   
  17. setInterval(tick, 1000);  

However, the above code misses a very crucial part. In the above code, the setting up of Timer and updating the UI should be the implementation detail of the Clock, however, the implementation is getting executed from the tick() function. Ideally, we want to write this once and have the Clock update itself, as shown below:-

  1. ReactDOM.render(  
  2.   <Clock />,  
  3.   document.getElementById('root')  
  4. );  

To implement this, we need to add "state" to the Clock component.

How to convert a function to a Class

We can convert a functional component like Clock to a class in five steps,

  1. Create an ES6 class with the same name that extends React.Component.
  2. Add a single empty method to it called render().
  3. Move the body of the function into the render() method.
  4. Replace props with this.props in the render() body.
  5. Delete the remaining empty function declaration.
  1. class Clock extends React.Component {  
  2.     render() {  
  3.        return (  
  4.           <div>  
  5.               <h1>Hello, world!</h1>  
  6.               <h2>It is {this.props.date.toLocaleTimeString()}.</h2>  
  7.          </div>  
  8.      );  
  9.   }  

Clock is now defined as a class rather than a function.

How to Add Local State to a Class

We can add local state to a class in three steps,

  1. Replace this.props.date with this.state.date in the render() method.
  2. Add a class constructor that assigns the initial this.state
  3. Remove the prop from the element

Adding Lifecycle Methods to a Class

In applications with many components, it is very important to free up resources taken by the components when they are destroyed.

For E.g. - We want to set up a timer whenever the Clock is rendered to the DOM for the first time. This is called "mounting" in React.

We also want to clear that timer whenever the DOM produced by the Clock is removed. This is called "unmounting" in React.

We can declare special methods on the component class to run some code when a component mounts and unmounts:

These methods are called "Lifecycle Hooks". The componentDidMount() hook runs after the component output has been rendered to the DOM.

So, the complete looks like below,

  1. class Clock extends React.Component {  
  2.   constructor(props) {  
  3.     super(props);  
  4.     this.state = {date: new Date()};  
  5.   }  
  6.   
  7.   componentDidMount() {  
  8.     this.timerID = setInterval(  
  9.       () => this.tick(),  
  10.       1000  
  11.     );  
  12.   }  
  13.   
  14.   componentWillUnmount() {  
  15.     clearInterval(this.timerID);  
  16.   }  
  17.   
  18.   tick() {  
  19.     this.setState({  
  20.       date: new Date()  
  21.     });  
  22.   }  
  23.   
  24.   render() {  
  25.     return (  
  26.       <div>  
  27.         <h1>Hello, world!</h1>  
  28.         <h2>It is {this.state.date.toLocaleTimeString()}.</h2>  
  29.       </div>  
  30.     );  
  31.   }  
  32. }  
  33.   
  34. ReactDOM.render(  
  35.   <Clock />,  
  36.   document.getElementById('root')  
  37. ); 

Points to Remember for State

  • Do not modify State Directly
  • State Updates May Be Asynchronous
  • State Updates are Merged

Summary

In this article, we saw how we could implement State and Lifecycle methods in React code.