Change the style of individual element in React component which return multiple repeated elements

Viewed 176

I'm rendering a Canvas component in react, which return a list of <rect> elements, what Im trying to achieve is to change the color of the clicked <rect> only, however in my code whenever i click on one of the elements, the complete list of elements are updated, how can i update the clicked <rect> element only?

below is my code:

import { useState } from "react";
import styles from "./Canvas.module.css";

let data = [
  {
    id: "1",
    x: "50",
    y: "20",
  },
  {
    id: "2",
    x: "90",
    y: "20",
  },
  {
    id: "3",
    x: "130",
    y: "20",
  },
];

const Canvas = () => {
  const [redRectangle, setRedRectangle] = useState();

  const setColorHandler = () => {
    setRedRectangle(styles.rect);
  };

  let arr = data.map((element) => {
    return (
      <rect
        className={redRectangle}
        key={element.id}
        width="30"
        height="4"
        x={element.x}
        y={element.y}
        onClick={setColorHandler}
      />
    );
  });

  return (
    <svg width="800" height="600" id="svg">
      {arr}
    </svg>
  );
};

export default Canvas;

before running the code

enter image description here

after clicking on one <rect>

enter image description here

2 Answers

First of all, create a separate component for rect. After creating it, add a component level state to the rect component, specifying the color. Then map the rect component in the canvas function.

After mapping, create a function to change the class of a single rect component using the id. Whenever you call the function pass the id of the element as a parameter to the function. After doing that, use a forEach loop to check if elementID received from the parameter is equal to the currentElement Id. And if it is equal, then change the state for that specific component.

Thanks

It's happening because U are assigning one className to all the elements. By clicking on one of them, that className is changed and all of them get updated. What U need to do is this: 1- U don't need the state delete it. 2-Define another className in your CSS file named changed-to-red and style it like U want. 3-On your click handler function toggle the className like below:

const setColorHandler = (e)=> {
   e.currentTarget.classList.toggle("changed-to-red")
}
Related