Introduction - What is a React Hook?
A React Hook is a special function that lets you "hook into" React features like state and lifecycle methods, enabling functional components to manage state and side effects.
Now, you've decided to build a React app, leveraging the power of React hooks. With numerous hooks available, it can be challenging to know which ones to use.
Let's explore the essential hooks, understand their functions, and see some concise examples to get you started:
State Management Hooks
  
  
  useState
The useState hook is fundamental for managing state and rendering components upon state changes.
import React, { useState } from 'react';
function Counter() {
  const [count, setCount] = useState(0);
  return (
    <div>
      <p>{count}</p>
      <button onClick={() => setCount(count + 1)}>Increment</button>
    </div>
  );
}
  
  
  useReducer
The useReducer hook is ideal for handling more complex state logic.
import React, { useReducer } from 'react';
const initialState = { count: 0 };
function reducer(state, action) {
  switch (action.type) {
    case 'increment': return { count: state.count + 1 };
    case 'decrement': return { count: state.count - 1 };
    default: return state;
  }
}
function Counter() {
  const [state, dispatch] = useReducer(reducer, initialState);
  return (
    <div>
      <p>{state.count}</p>
      <button onClick={() => dispatch({ type: 'increment' })}>Increment</button>
      <button onClick={() => dispatch({ type: 'decrement' })}>Decrement</button>
    </div>
  );
}
Effect Hooks
  
  
  useEffect
Effect hooks allow you to perform side effects, such as data fetching or DOM manipulation.
import React, { useState, useEffect } from 'react';
function Example() {
  const [count, setCount] = useState(0);
  useEffect(() => {
    document.title = `Count: ${count}`;
  }, [count]);
  return (
    <div>
      <p>{count}</p>
      <button onClick={() => setCount(count + 1)}>Increment</button>
    </div>
  );
}
  
  
  useLayoutEffect
useLayoutEffect runs synchronously after all DOM mutations, useful for operations that need to occur before the browser repaints.
import React, { useLayoutEffect, useRef } from 'react';
function LayoutEffectExample() {
  const ref = useRef();
  useLayoutEffect(() => {
    console.log(ref.current.getBoundingClientRect());
  }, []);
  return <div ref={ref}>Measure my dimensions</div>;
}
Ref Hooks
  
  
  useRef
The useRef hook allows you to persist values across renders without causing a re-render.
import React, { useRef } from 'react';
function TextInputWithFocusButton() {
  const inputEl = useRef(null);
  const onButtonClick = () => {
    inputEl.current.focus();
  };
  return (
    <div>
      <input ref={inputEl} type="text" />
      <button onClick={onButtonClick}>Focus the input</button>
    </div>
  );
}
  
  
  useImperativeHandle
useImperativeHandle customizes the instance value that is exposed when using ref in parent components.
import React, { useImperativeHandle, useRef, forwardRef } from 'react';
const FancyInput = forwardRef((props, ref) => {
  const inputRef = useRef();
  useImperativeHandle(ref, () => ({
    focus: () => {
      inputRef.current.focus();
    }
  }));
  return <input ref={inputRef} />;
});
function Parent() {
  const inputRef = useRef();
  return (
    <div>
      <FancyInput ref={inputRef} />
      <button onClick={() => inputRef.current.focus()}>Focus the input</button>
    </div>
  );
}
Performance Hooks
  
  
  useMemo
useMemo memoizes expensive calculations, recomputing the cached value only when its dependencies change.
import React, { useMemo } from 'react';
function ExpensiveCalculationComponent({ num }) {
  const result = useMemo(() => num * 2, [num]);
  return <div>Result: {result}</div>;
}
  
  
  useCallback
useCallback memoizes callback functions, preventing unnecessary re-creations on each render.
import React, { useState, useCallback } from 'react';
function Button({ onClick }) {
  return <button onClick={onClick}>Click me</button>;
}
function App() {
  const [count, setCount] = useState(0);
  const handleClick = useCallback(() => setCount(count + 1), [count]);
  return (
    <div>
      <p>{count}</p>
      <Button onClick={handleClick} />
    </div>
  );
}
Context Hooks
  
  
  useContext
useContext accesses values from a context provider.
import React, { useContext } from 'react';
const MyContext = React.createContext();
function Display() {
  const value = useContext(MyContext);
  return <div>{value}</div>;
}
function App() {
  return (
    <MyContext.Provider value="Hello, World!">
      <Display />
    </MyContext.Provider>
  );
}
Transition Hooks
  
  
  useTransition
useTransition marks state updates as non-urgent, improving user experience by deferring heavy computations.
import React, { useState, useTransition } from 'react';
function FilterList({ items }) {
  const [filter, setFilter] = useState('');
  const [isPending, startTransition] = useTransition();
  const filteredItems = items.filter((item) =>
    item.toLowerCase().includes(filter.toLowerCase())
  );
  return (
    <div>
      <input
        type="text"
        value={filter}
        onChange={(e) => {
          startTransition(() => setFilter(e.target.value));
        }}
      />
      {isPending ? <p>Loading...</p> : filteredItems.map((item) => <p key={item}>{item}</p>)}
    </div>
  );
}
  
  
  useDeferredValue
useDeferredValue defers a value update to maintain responsiveness.
import React, { useState, useDeferredValue } from 'react';
function DeferredList({ items }) {
  const [filter, setFilter] = useState('');
  const deferredFilter = useDeferredValue(filter);
  const filteredItems = items.filter((item) =>
    item.toLowerCase().includes(deferredFilter.toLowerCase())
  );
  return (
    <div>
      <input type="text" value={filter} onChange={(e) => setFilter(e.target.value)} />
      {filteredItems.map((item) => (
        <p key={item}>{item}</p>
      ))}
    </div>
  );
}
Conclusion
React hooks provide a powerful and flexible way to manage state, handle side effects, and optimize performance in your React applications. By understanding and utilizing these essential hooks, you can build more efficient and maintainable React apps. For a deeper dive into all things React, consider exploring comprehensive resources and bootcamps that offer interactive challenges, videos, and cheat sheets.
              
    
Top comments (0)