Context in React.js

Context provides a way to pass data through the component tree without having to pass props down manually at every level.

In a typical React application, data is passed top-down (parent to child) via props, but such usage can be cumbersome for certain types of props (e.g. locale preference, UI theme) that are required by many components within an application.

Context provides a way to share values like these between components without having to explicitly pass a prop through every level of the tree.

Meetup WebSite

context api in react js

We want to store and update the meetup list on different pages. When the content of the list changes, all pages that use it can be updated immediately. To achieve this, we use the React Context mechanism.

import React from "react";
import ReactDOM from "react-dom";
import { BrowserRouter } from "react-router-dom/cjs/react-router-dom";

import "./index.css";
import App from "./App";
import { FavoritesContextProvider } from "./store/favorites-context";

ReactDOM.render(
  <FavoritesContextProvider>
    <BrowserRouter>
      <App />
    </BrowserRouter>
  </FavoritesContextProvider>,
  document.getElementById("root")
);

We need to implement a React Context Provider and place it on the parent node of the React Component that will be used in the Meetup list.

import { createContext, useState } from "react";

const FavoritesContext = createContext({
  favorites: [],
  totalFavorites: 0,
  addFavorite: (favoriteMeetup) => {},
  removeFavorite: (meetupId) => {},
  itemIsFavorite: (meetupId) => {},
});

export function FavoritesContextProvider(props) {
  const [userFavorites, setUserFavorites] = useState([]);

  function addFavoriteHandler(favoriteMeetup) {
    setUserFavorites((preUserFavorites) => {
      return preUserFavorites.concat(favoriteMeetup);
    });
  }

  function removeFavoriteHandler(meetupId) {
    setUserFavorites((preUserFavorites) => {
      return preUserFavorites.filter(meetup => meetup.id !== meetupId);
    });
  }

  function itemIsFavoriteHandler(meetupId) {
    return userFavorites.some(meetup => meetup.id === meetupId);
  }

  const context = {
    favorites: userFavorites,
    totalFavorites: userFavorites.length,
    addFavorite: addFavoriteHandler,
    removeFavorite: removeFavoriteHandler,
    itemIsFavorite: itemIsFavoriteHandler,
  };
  return (
    <FavoritesContext.Provider value={context}>
      {props.children}
    </FavoritesContext.Provider>
  );
}

export default FavoritesContext;

In this FavoritesContextProvider React component, a State is declared to store the Meetup list, and the add and delete functions, and the function to determine whether the Meetup ID exists in the Meetup list are implemented.

Please note the declaration of “const context”. When this React Component is reloaded, the Meetup list will be cleared to an empty array.

At the same time, addFavorite, removeFavorite, and itemIsFavorite of this React Component are all bound to the implementation of the FavoritesContextProvider React component.

context api in react js

When the user clicks “To Favorites”, the information of the Meetup project will be added to the Meetup list.

import { useContext } from "react";
import classes from "./MeetupItem.module.css";
import Card from "../ui/Card";

import FavoritesContext from "../../store/favorites-context";

function MeetupItem({ id, title, image, address, description }) {

   const favoritesCtx = useContext(FavoritesContext);

   const itemIsFavorite = favoritesCtx.itemIsFavorite(id);

    function toggleFavoriteStatusHandler() {
        if (itemIsFavorite) {
            favoritesCtx.removeFavorite(id);
        } else {
            favoritesCtx.addFavorite({
                id: id,
                title: title,
                image: image,
                address: address,
                description: description
            })
        }

    }


  return (
    <li className={classes.item}>
      <Card>
        <div className={classes.image}>
          <img src={image} alt={title} />
        </div>
        <div className={classes.content}>
          <h3>{title}</h3>
          <address>{address}</address>
          <p>{description}</p>
        </div>
        <div className={classes.actions}>
          <button onClick={toggleFavoriteStatusHandler}>{itemIsFavorite ? "Remove from Favorites" : "To Favorites"}</button>
        </div>
      </Card>
    </li>
  );
}

export default MeetupItem;

const favoritesCtx = useContext(FavoritesContext); This statement accesses the Meetup list. First, determine whether the Meetup selected by the user already exists in the list. If not, add it to the list. If yes, remove it from the list.

When this React component changes the Meetup list, another React component will also receive the notification and re-render.

context api in react js
import { useContext } from "react";
import { Link } from "react-router-dom/cjs/react-router-dom";
import classes from "./MainNavigation.module.css";
import FavoritesContext from "../../store/favorites-context";

function MainNavigation() {
  const favoritesCtx = useContext(FavoritesContext);

  return (
    <header className={classes.header}>
      <div className={classes.logo}>React Meetups</div>
      <nav>
        <ul>
          <li>
            <Link to="/">All Meetups</Link>
          </li>
          <li>
            <Link to="/new-meetup">Add New Meetup</Link>
          </li>
          <li>
            <Link to="/favorites">My Favorites<span className={classes.badge}>{favoritesCtx.totalFavorites}</span></Link>
          </li>
        </ul>
      </nav>
    </header>
  );
}

export default MainNavigation;
Context Provider

Online React course: Maximilian Schwarzmüller

Next.js

If you think it is well written, please forward this article.

Spread the love

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *