DEV Community

K-Sato
K-Sato

Posted on • Updated on

React hooks for noobs

Introduction

Hooks are a new feature introduced in React16.8.
I'll try to explain what they are in the following order.

What are Hooks?

According to the official React documentation,

Hooks let you use state and other React features without writing a class.

Yup. That's exactly it!.
Now you can use some React features such as state in functional components thanks to hooks!!

I'll introduce 3 following hooks in this post.

  • (1)State Hook: It lets you use state and setState in functional components.
  • (2)Effect Hook: It lets you perform side effects such as data fetching in functional components.
  • (3)Custom Hooks: Building your custom hooks lets you extract component logic into reusable functions.

Rules of Hooks

There are 2 ground rules you have to follow to use hooks safely.

(1) Only Call Hooks at the Top Level!!
Don’t call Hooks inside loops, conditions, or nested functions.

(2) Only Call Hooks from React Functions!!
Don’t call Hooks from regular JavaScript functions.

State Hook

You can use state and setState in functional components by using a hook called useState.

Let's see how to use useState through comparing a functional componentusing useState to the equivalent class component.

Equivalent Class Component

It does the following 2 things.

  • (1) Define the count state and its initialState 0.
  • (2) Add 1 to count each time setState is called.
class Example extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      count: 0
    };
  }

  render() {
    return (
      <div>
        <p>You clicked{this.state.count} times</p>
        <button onClick={() => this.setState({ count: this.state.count + 1 })}>
          Click Me
        </button>
      </div>
    );
  }
}
Enter fullscreen mode Exit fullscreen mode

Functional Component with State Hook

Now it's time to create a functional component using useState which does the same thing as the class component above.

The basic syntax of useState looks like this!

const [state, setState] = useState(initialState);
Enter fullscreen mode Exit fullscreen mode

It's like you define the state, setState and initialState all together.

If you want to define the same state as the one in the class component above, it would look like this.

import React, { useState } from  'react';

function Counter() {
  const [count, setCount] = useState(0)
}
Enter fullscreen mode Exit fullscreen mode

Notice 3 things in the code above!

  • (1) count is the equivalent ofthis.state={count:0} in the class component.
  • (2) setCount is the equivalent of setState part in the class component.
  • (3) 0 is the initial state of count.

While you are writing up the rest of the code, keep these 2 things in mind.

  • (1) You can use count directory!(no need to do this.count.)
  • (2) You can update the state by using setCount.
import React, { useState } from  'react';

function Counter() {
  const [count, setCount] = useState(0)

  return(
    <div>
      // (1) You can use count directory!
      <p>You clicked {count} times</p>

      // (2) You can update the state by using setCount.
      <button onClick={() => setCount(count + 1)}> Click me</button> 
    </div>
  )
}

export default Counter;
Enter fullscreen mode Exit fullscreen mode

As a side note, you can define multiple states like the code below.

import React, { useState } from  'react';

function Counter() {
  const [count, setCount] = useState(0)
  const [name, setName] = useState('')

  return(
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}> Click me</button>
      <p>My name is {name}.</p>
      <button onClick={() => setName('テスト太郎')}>Show my name</button>
    </div>
  )
}

export default Counter;
Enter fullscreen mode Exit fullscreen mode

Effect Hook

You can perform side effects in functional components by using a hook called useEffect!

Let's see how to use useEffec through comparing a functional componentusing useEffect to the equivalent class component.

Example Class Component

In class components, we perform side effects such as fetching data and changing the DOM in componentDidMount componentDidUpdate.

Here, it outputs It did mount in the console after a component is mounted and outputs It did get updated after updating occurs.

import React from  'react';

class Effect extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      count: 0
    };
  }

  componentDidMount() {
    console.log('It did mount.')
  }

  componentDidUpdate() {
    console.log('It did get updated.')
  }

  render() {
    return (
      <div>
        <h1>You clicked {this.state.count} times</h1>
        <button onClick={() => this.setState({ count: this.state.count + 1 })}>
          Click me
        </button>
      </div>
    );
  }
}
Enter fullscreen mode Exit fullscreen mode

Example Functional Component using useEffect

The useEffect hook is like a combination of componentDidMount, componentDidUpdate and componentWillUnmount.
It runs after every render including the first render.
When you are building react applications with hooks this is where you perform side effects.

import React, { useState, useEffect } from 'react'

function Effect() {
  const [count, setCount] = useState(0)

  useEffect(() => {
    console.log('It got rendered')
  })

  return(
    <div>
      <h1>You clicked {count} times</h1>
      <button onClick={() => setCount(count + 1)}> Click me</button>
    </div>
  );
}
Enter fullscreen mode Exit fullscreen mode

Custom Hooks

As I mentioned above, building your custom hooks lets you extract component logic into reusable functions.

Let's suppose there are two components like below.

  • (1) A component called Status which returns Logged in if it receives id = 1.
  • (2) A component called Message which returns Welocme Back if it receives id = 1.
export default function Status(props){
  const [isLoggedIn, setIsLoggedIn] = useState(false);

  const handleStateChange = (id) => {
    if(id === 1){
      setIsLoggedIn(true)
    }
    else{
      setIsLoggedIn(false)
    }
  }

  useEffect(() => {
    handleStateChange(props.user.id)
  })

 const status = isLoggedIn ? 'Logged in' : 'Sign up'

  return (
    <>
      <h1>Status: {status}</h1>
    </>
  )
}
Enter fullscreen mode Exit fullscreen mode
export default function Message(props){
  const [isLoggedIn, setIsLoggedIn] = useState(false);

  const handleStateChange = (id) => {
    if(id === 1){
      setIsLoggedIn(true)
    }
    else{
      setIsLoggedIn(false)
    }
  }

  useEffect(() => {
    handleStateChange(props.user.id)
  })

 const message = isLoggedIn ? 'Welcome Back' : 'Who are you??'

  return (
    <>
      <h1>Message: {message}</h1>
    </>
  )
}
Enter fullscreen mode Exit fullscreen mode

As you probably noticed, it's very redundant.
You can build a custom hook to extract the same logic exists in both components into one reusable function.

※It is very important that you name your custom hook starting with use.
In this case, I named my custom hook useLogIn.

import { useState, useEffect } from 'react';

export default function useLogIn(userId){
  const [isLoggedIn, setIsLoggedIn] = useState(false);

  // The login you want to reuse.
  const handleStateChange = (id) => {
    if(id === 1){
      setIsLoggedIn(true)
    }
    else{
      setIsLoggedIn(false)
    }
  }

  // Perform side effects in useEffect.
  useEffect(() => {
    handleStateChange(userId)
  })

  return isLoggedIn;
}
Enter fullscreen mode Exit fullscreen mode

Using useLogIn, we can simplify Status and Message components.

import React from 'react';
import useLogIn from './useLogIn';

export default function Status(props){
  const status = useLogIn(props.user.id) ? 'Logged in' : 'Sign up'
  return (
    <>
      <h1>Status: {status}</h1>
    </>
  )
}
Enter fullscreen mode Exit fullscreen mode
import React from 'react';
import useLogIn from './useLogIn';

export default function Message(props){
  const message = useLogIn(props.user.id) ? 'Welcome Back' : 'Who are you??'
  return (
    <>
      <h1>Message: {message}</h1>
    </>
  )
}
Enter fullscreen mode Exit fullscreen mode

The custom hooks can be used for other cool stuff, check out the official document about Building Your Own Hooks.

Resources

Top comments (11)

Collapse
 
samparker4123 profile image
samparker4123

To run the code in Java, you must first create a class. I'm not sure what this Hook technique is all about. I'm working on an application for my Malaysian customer of Transfer Factor Malaysia. I'm completely baffled as to how to do this approach. I attempted it without first establishing a class. Errors were still present.

Collapse
 
cryptoexchangesoftware profile image
Shah Iritza

The new feature in the react 16.8 version, it is used to allow and use state and other features of React with out writing or giving a class. I have experienced this when I used this to my site perfectcvmaker.ae last month and it is great and easy to make.

Collapse
 
itsliamwilliam profile image
itsliamwilliam

These are extraordinary in light of the fact that going out as a family can be very costly, particularly at the motion pictures where food and beverages are difficult to bear on an ordinary financial plan. By : UK Essay Writing Service.

Collapse
 
scriptkavi profile image
ScriptKavi

Many early birds have already started using this custom hooks library
in their ReactJs/NextJs project.

Have you started using it?

scriptkavi/hooks

PS: Don't be a late bloomer :P

Collapse
 
elmadavis profile image
elmadavis • Edited

Java always requires a class to run the code. I didn’t get a clear concept of this Hook method. I am developing an application for my client cv help uk - cvwritings.co.uk. I am totally getting confused about how to run this method. I’ve tried it without creating a class. It was still showing errors.

Collapse
 
samtim2050 profile image
samtim2050

It's a new feature in React that allows you to leverage state and other React capabilities without having to write or give a class. Last month, I utilised this on my best travel company site, and it worked excellent and was simple to set up.

Collapse
 
sergiogomesva profile image
Sérgio Gomes

Simple and succinct. Well done!

Collapse
 
asuka_miyuk profile image
明日香-みゆき

Solary Electricals is a leading auto body collision repair welding products company committed to deliver innovation as well as powerful, durable and reliable products. Browse Solary's spot welder, dent puller, infrared curing lamp, hot stapler, battery charger and more for all your auto body repair needs.

Collapse
 
markbuttler profile image
markbuttler7164

The best thing is that the custom hooks can be used for other cool stuff. Thanks for sharing this guide. This will be helpful for me to serve the animation production service all over the region.

Collapse
 
john_kelvin_8aa1bb7ed0ed1 profile image
John Kelvin • Edited

Thank's for sharing. I didn't understand the hook method clearly. I am currently developing an application for my my friend wikiwriters.co.uk | Wikipedia agency in UK. Your info helped me solve some major technical issues. Thank you!