A difference between state
and props
is that while the data stored by props
are fixed throughout their lifetime, state
store data that can be changed over time. This change can be in response to user actions, network responses, or anything. Also, while props
are set by the parent component, state
is changed internally by the component itself.
A component’s state should be considered private data. This data is not exposed to the component that makes use of it. It is private and fully controlled by the component. It is only seen on the inside of component definitions. You can think of state it as an internal data-set that affects the rendering of components. Components that have a state are referred to as stateful components while those that do not have states are referred to as stateless components.
You can set a component’s default state, access the current state, and update this state. Let us consider how we can do each of these. We are going to make reference to the <Greeting />
component that was created in my article on React Components. Here’s the component that was created.
class Greeting extends React.Component {
render() {
return (
<div className = "box">
<h2> Hello Human Friend!!!</h2>
<p> We are so glad to have you here. </p>
</div>
);
}
}
ReactDOM.render(<Greeting />, document.getElementById("app"));
Setting a Component’s Initial State
“`js class Greeting extends React.Component { constructor(props) { super(props); this.state = { name : “Human Friend”, message : “You are welcome to our World” } }… “`
The above is the syntax for doing setting a component’s default state. The constructor
method is a special method for creating and initializing an object created with a class. In any class, there can only be one constructor
method. super
allows you to call the constructor method of the parent class. You need to include props
to have access to this.props
inside of your constructor. In React, super
should be present in a constructor
method.
You set the initial state of the component by using this.state
. this.state
should be equal to an object just like in the example above. So in our example, the initial state of the component has been set to
this.state = {
name : "Human Friend",
message : "You are welcome to our World"
}
So that’s how the initial state of a component is set. How can we access a component’s state then?
Accessing a Component’s State
To access a component’s state we use this.state.name-of-property
. For instance, if we want to access the state of the name
we simply use this.state.name
. Now let’s change what is displayed to be the initial state of the component.
render() {
return (
<div className = "box">
<h2> Hello {this.state.name}!!!</h2>
<p> {this.state.message}</p>
</div>
);
}
If you understand state
up to this point, you are doing great. Next, let’s see how to change the state of a component.
Changing a Component’s State
To change a component’s state, we call a function this.setState()
. this.setState()
takes two arguments, an object, and a callback. So, in our greeting component, if we are to call this.setState({name : “TeachDeveloper”}), the state of the name
property will be changed to “TeachDeveloper”. Cool!!!
So back to our <Greeting />
component. Let’s see this.setState
it in action. What we are going to do is to create a button that toggles between the initial state of this.state.name
and the new this.state.name
.
First, we add the button.
render() {
return (
<div className = "box">
<h2> Hello {this.state.name}!!!</h2>
<p> {this.state.message}</p>
<button onClick = {this.handleClick}> Click Me </button>
</div>
);
}
Next, we add a method that handles the click.
handleClick() {
const newName = this.state.name == "TeachDeveloper" ? "Human Friend" : "TeachDeveloper";
this.setState({name : newName});
}
...
So what the above code does is check if the value of this.state.name
is “TeachDeveloper”. If it is, the value of newName is “Human Friend” and vice versa. Then we set this.state.name the value of newName
.
One last thing, In JavaScript, class methods are not bound by default. If you forget to bind this.handleClick
and pass it to onClick
, this
will be undefined when the function is actually called. So we have to bind our method to this
in the constructor method.
class Greeting extends React.Component {
constructor(props) {
super(props);
this.state = {
name : "Human Friend",
message : "You are welcome to our World"
}
this.handleClick = this.handleClick.bind(this);
}
It’s nice that you have read up to this point. Here is the total code we’ve written for the <Greeting/>
component.
class Greeting extends React.Component {
constructor(props) {
super(props);
this.state = {
name : "Human Friend",
message : "You are welcome to our World"
}
this.handleClick = this.handleClick.bind(this);
}
handleClick() {
const newName = this.state.name == "TeachDeveloper" ? "Human Friend" : "TeachDeveloper";
this.setState({name : newName});
}
render() {
return (
<div className = "box">
<h2> Hello {this.state.name}</h2>
<p> {this.state.message} </p>
<button onClick = {this.handleClick}>Click Me </button>
</div>
);
}
}
ReactDOM.render(<Greeting />, document.getElementById("app"));
To see how this works, try it on Codepen.
So, we’ve been able to understand states and learn how we can initialize, access, and update a component’s state. Awesome!!!
Got any questions? Any addition? Feel free to leave a comment.