Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[bug] Click events not firing after dragging element with pull: 'clone' #2397

Open
Prabhu-Kathiresan opened this issue Aug 17, 2024 · 0 comments

Comments

@Prabhu-Kathiresan
Copy link

Prabhu-Kathiresan commented Aug 17, 2024

Describe the bug
I am using sortable.js in my react app, and i have the use-case where I wanted to either drag and drop item from sourceList or if I click on the sourceList item, that item get appended to the targetList.

The click event is triggering fine until I drag the item from sourceList, once I drag the item the click event on the dragged item is getting removed.

I have a sourceList as follow

const SourceList = ({ dataTypes, onClick, onDragStart }) => {
  const listRef = useRef(null);

  useEffect(() => {
    if (listRef.current) {
      Sortable.create(listRef.current, {
        group: {
          name: 'shared',
          put: false,
          pull: 'clone'
        },
        animation: 150,
        sort: false, // Prevent sorting within this list
        onStart: (event) => {
          if (onDragStart) {
            onDragStart(event);
          }
        },
      });
    }

    return () => {
      if (listRef.current && listRef.current.sortable) {
        listRef.current.sortable.destroy();
      }
    };
  }, [onDragStart]);

  const handleClick = (dataType) => {
    if (onClick) {
      onClick(dataType);
    }
  };

  return (
    <ul ref={listRef} style={{ listStyleType: 'none', padding: 0 }}>
      {dataTypes.map((dataType) => (
        <li
          key={dataType.id}
          style={{ padding: '10px', border: '1px solid #ccc', margin: '5px', cursor: 'pointer' }}
          onClick={() => handleClick(dataType)}
        >
          {dataType.content}
        </li>
      ))}
    </ul>
  );
};

And TagretList as follow

const TargetList = ({ items, onDrop }) => {
  const listRef = useRef(null);

  useEffect(() => {
    if (listRef.current) {
      Sortable.create(listRef.current, {
        group: 'shared',
        animation: 150,
        sort: true,
        onEnd: (event) => {
          if (onDrop) {
            onDrop(event);
          }
        },
      });
    }

    return () => {
      if (listRef.current && listRef.current.sortable) {
        listRef.current.sortable.destroy();
      }
    };
  }, [items, onDrop]);

  return (
    <ul ref={listRef} style={{ listStyleType: 'none', padding: 0, minHeight: 200 }}>
      {items.map((item) => (
        <li key={item.id} style={{ padding: '10px', border: '1px solid #ccc', margin: '5px' }}>
          {item.content}
        </li>
      ))}
    </ul>
  );
};

And in my App.jsx

const App = () => {
  const [sourceItems,] = useState([
    { id: 1, content: 'Type A' },
    { id: 2, content: 'Type B' },
  ]);
  const [targetItems, setTargetItems] = useState([]);

  const handleClick = (dataType) => {
    const newItem = {
      id: Date.now(), // Unique id
      content: dataType.content,
    };
    setTargetItems((prevItems) => [...prevItems, newItem]);
  };

  const handleDrop = (event) => {
    const draggedContent = event.item.textContent;
    console.log(draggedContent);
    const newItem = {
      id: Date.now(), // Unique id
      content: draggedContent,
    };
    setTargetItems((prevItems) => [...prevItems, newItem]);
  };

  return (
    <div style={{ display: 'flex', justifyContent: 'space-between' }}>
      <div style={{ width: '45%', border: '1px solid #ededed' }}>
        <h3>Data Types</h3>
        <SourceList dataTypes={sourceItems} onClick={handleClick} />
      </div>
      <div style={{ width: '45%', border: '1px solid #ededed' }}>
        <h3>Target List</h3>
        <TargetList items={targetItems} onDrop={handleDrop} />
      </div>
    </div>
  );
};

Attaching video for reference,

Screen.Recording.2024-08-17.at.10.22.32.AM.mov

To Reproduce
Steps to reproduce the behavior:

  1. Go to '...'
  2. Click on '....'
  3. Scroll down to '....'
  4. See error

Expected behavior

Cloned element on the target list should have the click event, instead the source list element should maintain the click events associated to it.

Information

Versions - Look in your package.json for this information:
sortablejs = ^1.15.2
@types/sortablejs = ^1.15.8

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant