Moving elements in react-grid-layout

483 views Asked by At

I'm creating a React project in which I use react-grid-layout. I'm creating multiple grids inside each other using recursion. The component looks like this:

import "./styles.css";
import GridLayout from "react-grid-layout";
import { useState } from "react";
import "react-grid-layout/css/styles.css";
import "react-resizable/css/styles.css";

export default function CustomLayout({ layout, onDragStart, onDragStop }) {
  const [isDraggable, setIsDraggable] = useState(true);

  return (
    <GridLayout
      className="layout"
      onDragStart={onDragStart}
      onDragStop={onDragStop}
      layout={layout}
      cols={24}
      rowHeight={80}
      width={1600}
      isDraggable={isDraggable}
    >
      {layout.map((item) => {
        if (item.children) {
          return (
            <div
              key={item.i}
              style={{ background: "pink", border: "1px solid black" }}
            >
              <CustomLayout
                layout={item.children}
                onDragStart={() => {
                  setIsDraggable(false);
                }}
                onDragStop={() => {
                  setIsDraggable(true);
                }}
              />
            </div>
          );
        } else {
          return (
            <div key={item.i} style={{ background: "purple" }}>
              {item.i}
            </div>
          );
        }
      })}
    </GridLayout>
  );
}

I was able to add the functionality to make elements on the child grids draggable (using [isDraggable, setIsDraggable]), but the problem is: if I move an element on the third level grid, I won't be able to move an element on the main grid until I move element on the second level grid. How can this behavior be corrected?
P.S. you can interact with my code here

1

There are 1 answers

0
Listopad02 On BEST ANSWER

Well, i figured it out:

import "./styles.css";
import GridLayout from "react-grid-layout";
import { useState } from "react";
import "react-grid-layout/css/styles.css";
import "react-resizable/css/styles.css";

export default function CustomLayout({ layout, onDragStart, onDragStop }) {

  return (
    <GridLayout
      className="layout"
      onDragStart={(a, b, c, d, e) => e.stopPropagation()}
      onDragStop={onDragStop}
      layout={layout}
      cols={24}
      rowHeight={80}
      width={1600}
    >
      {layout.map((item) => {
        if (item.children) {
          return (
            <div
              key={item.i}
              style={{ background: "pink", border: "1px solid black" }}
            >
              <CustomLayout
                layout={item.children}
              />
            </div>
          );
        } else {
          return (
            <div key={item.i} style={{ background: "purple" }}>
              {item.i}
            </div>
          );
        }
      })}
    </GridLayout>
  );
}

You have to add onDragStart={(a, b, c, d, e) => e.stopPropagation()} with e being fifth param, otherwise it won't work.
Furthermore, you no longer need isDraggable state