SortableJS/react-sortablejs

[bug] Sortable.get(event.target).sort not working as expected

FFdhorkin opened this issue · 0 comments

Describe the bug
I have a series of rows, each of which has a label that shows its current index.

Without an onChange handler, the controls reorder properly, but the index label is not updating.

With my onChange handler, nothing happens visually when I drag item # 3 over # 2 (though I can see a console.log showing the correct oldIndex and newIndex). When I drag item # 3 over item # 1, suddenly the index labels /controls fluctuate rapidly. It looks like item # 1 and # 3 are swapping positions repeatedly.

I originally tried to use setState in the onChange handler, but that seemed to lead to duplicate controls for some reason. (There were also errors about q.parentNode is null when I tried setState)

To Reproduce
Steps to reproduce the behavior:

  1. In child object, have an index in props that is used for displaying row #
  2. add onChange handler to container:
onChange={(event, sortable) => {
    event.stopPropagation();
    const { oldIndex, newIndex } = event;
    const order = sortable!.toArray();
    
    console.log(`${oldIndex}, ${newIndex}`);
    console.log(JSON.stringify(order));
    order.splice(newIndex!, 0, order.splice(oldIndex!, 1)[0]);
    console.log(JSON.stringify(order));
    Sortable.get(event.target)?.sort(order, true);
}}

Expected behavior

  • If you drag item # 3 over # 2, then the displayed order should be what was originally 1/3/2.
  • If you drag item # 3 over # 1, then the displayed order should be 3/1/2.

Actual behavior

  • If you drag item # 3 over # 2, nothing happens if there's an onChange. (Without onChange, it works, but index label isn't updating)
  • If you drag item # 3 over # 1, items # 1 and # 3 seem to swap rapidly

Information
Versions
react-sortable = ^6.1.4
react = ^18.2.0

Before drag:
image
Dragging # 3 over # 2:
image
Dragging # 3 over # 1 fluctuates between these states:
image
image

As a reference, here's what happens when I drag # 3 over # 2 if there's no onChange:
image

And here's what happens if I try to use this.setState to update order:
image