diff --git a/package-lock.json b/package-lock.json index 956361465..8f41e00d6 100644 --- a/package-lock.json +++ b/package-lock.json @@ -14,8 +14,8 @@ "@atlaskit/pragmatic-drag-and-drop-hitbox": "^1.1.0", "@atlaskit/pragmatic-drag-and-drop-react-drop-indicator": "^3.2.0", "@babel/plugin-transform-react-pure-annotations": "^7.27.1", - "@dnd-kit/core": "^6.3.1", - "@dnd-kit/sortable": "^10.0.0", + "@dnd-kit/helpers": "^0.3.2", + "@dnd-kit/react": "^0.3.2", "@emotion/react": "^11.13.5", "@emotion/styled": "^11.13.5", "@faker-js/faker": "^10.0.0", @@ -1175,57 +1175,92 @@ "node": ">=20.19.0" } }, - "node_modules/@dnd-kit/accessibility": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/@dnd-kit/accessibility/-/accessibility-3.1.1.tgz", - "integrity": "sha512-2P+YgaXF+gRsIihwwY1gCsQSYnu9Zyj2py8kY5fFvUM1qm2WA2u639R6YNVfU4GWr+ZM5mqEsfHZZLoRONbemw==", + "node_modules/@dnd-kit/abstract": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/abstract/-/abstract-0.3.2.tgz", + "integrity": "sha512-uvPVK+SZYD6Viddn9M0K0JQdXknuVSxA/EbMlFRanve3P/XTc18oLa5zGftKSGjfQGmuzkZ34E26DSbly1zi3Q==", "dev": true, + "license": "MIT", "dependencies": { - "tslib": "^2.0.0" - }, - "peerDependencies": { - "react": ">=16.8.0" + "@dnd-kit/geometry": "^0.3.2", + "@dnd-kit/state": "^0.3.2", + "tslib": "^2.6.2" } }, - "node_modules/@dnd-kit/core": { - "version": "6.3.1", - "resolved": "https://registry.npmjs.org/@dnd-kit/core/-/core-6.3.1.tgz", - "integrity": "sha512-xkGBRQQab4RLwgXxoqETICr6S5JlogafbhNsidmrkVv2YRs5MLwpjoF2qpiGjQt8S9AoxtIV603s0GIUpY5eYQ==", + "node_modules/@dnd-kit/collision": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/collision/-/collision-0.3.2.tgz", + "integrity": "sha512-pNmNSLCI8S9fNQ7QJ3fBCDjiT0sqBhUFcKgmyYaGvGCAU+kq0AP8OWlh0JSisc9k5mFyxmRpmFQcnJpILz/RPA==", "dev": true, + "license": "MIT", "dependencies": { - "@dnd-kit/accessibility": "^3.1.1", - "@dnd-kit/utilities": "^3.2.2", - "tslib": "^2.0.0" - }, - "peerDependencies": { - "react": ">=16.8.0", - "react-dom": ">=16.8.0" + "@dnd-kit/abstract": "^0.3.2", + "@dnd-kit/geometry": "^0.3.2", + "tslib": "^2.6.2" } }, - "node_modules/@dnd-kit/sortable": { - "version": "10.0.0", - "resolved": "https://registry.npmjs.org/@dnd-kit/sortable/-/sortable-10.0.0.tgz", - "integrity": "sha512-+xqhmIIzvAYMGfBYYnbKuNicfSsk4RksY2XdmJhT+HAC01nix6fHCztU68jooFiMUB01Ky3F0FyOvhG/BZrWkg==", + "node_modules/@dnd-kit/dom": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/dom/-/dom-0.3.2.tgz", + "integrity": "sha512-cIUAVgt2szQyz6JRy7I+0r+xeyOAGH21Y15hb5bIyHoDEaZBvIDH+OOlD9eoLjCbsxDLN9WloU2CBi3OE6LYDg==", "dev": true, + "license": "MIT", "dependencies": { - "@dnd-kit/utilities": "^3.2.2", - "tslib": "^2.0.0" - }, - "peerDependencies": { - "@dnd-kit/core": "^6.3.0", - "react": ">=16.8.0" + "@dnd-kit/abstract": "^0.3.2", + "@dnd-kit/collision": "^0.3.2", + "@dnd-kit/geometry": "^0.3.2", + "@dnd-kit/state": "^0.3.2", + "tslib": "^2.6.2" } }, - "node_modules/@dnd-kit/utilities": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/@dnd-kit/utilities/-/utilities-3.2.2.tgz", - "integrity": "sha512-+MKAJEOfaBe5SmV6t34p80MMKhjvUz0vRrvVJbPT0WElzaOJ/1xs+D+KDv+tD/NE5ujfrChEcshd4fLn0wpiqg==", + "node_modules/@dnd-kit/geometry": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/geometry/-/geometry-0.3.2.tgz", + "integrity": "sha512-3UBPuIS7E3oGiHxOE8h810QA+0pnrnCtGxl4Os1z3yy5YkC/BEYGY+TxWPTQaY1/OMV7GCX7ZNMlama2QN3n3w==", "dev": true, + "license": "MIT", "dependencies": { - "tslib": "^2.0.0" + "@dnd-kit/state": "^0.3.2", + "tslib": "^2.6.2" + } + }, + "node_modules/@dnd-kit/helpers": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/helpers/-/helpers-0.3.2.tgz", + "integrity": "sha512-pj7pCE6BiysNetpPnzb3BJOrcKiqueUr1LFg6wYoi2fIFYpz66n2Ojd7HTwfwkpv0oyC3QlvA6Dk8cOmi6VavA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@dnd-kit/abstract": "^0.3.2", + "tslib": "^2.6.2" + } + }, + "node_modules/@dnd-kit/react": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/react/-/react-0.3.2.tgz", + "integrity": "sha512-1Opg1xw6I75Z95c+rF2NJa0pdGb8rLAENtuopKtJ1J0PudWlz+P6yL137xy/6DV43uaRmNGtsdbMbR0yRYJ72g==", + "dev": true, + "license": "MIT", + "dependencies": { + "@dnd-kit/abstract": "^0.3.2", + "@dnd-kit/dom": "^0.3.2", + "@dnd-kit/state": "^0.3.2", + "tslib": "^2.6.2" }, "peerDependencies": { - "react": ">=16.8.0" + "react": "^18.0.0 || ^19.0.0", + "react-dom": "^18.0.0 || ^19.0.0" + } + }, + "node_modules/@dnd-kit/state": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/@dnd-kit/state/-/state-0.3.2.tgz", + "integrity": "sha512-dLUIkoYrIJhGXfF2wGLTfb46vUokEsO/OoE21TSfmahYrx7ysTmnwbePsznFaHlwgZhQEh6AlLvthLCeY21b1A==", + "dev": true, + "license": "MIT", + "dependencies": { + "@preact/signals-core": "^1.10.0", + "tslib": "^2.6.2" } }, "node_modules/@emnapi/core": { @@ -2760,6 +2795,17 @@ "url": "https://opencollective.com/popperjs" } }, + "node_modules/@preact/signals-core": { + "version": "1.14.0", + "resolved": "https://registry.npmjs.org/@preact/signals-core/-/signals-core-1.14.0.tgz", + "integrity": "sha512-AowtCcCU/33lFlh1zRFf/u+12rfrhtNakj7UpaGEsmMwUKpKWMVvcktOGcwBBNiB4lWrZWc01LhiyyzVklJyaQ==", + "dev": true, + "license": "MIT", + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/preact" + } + }, "node_modules/@radix-ui/colors": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/@radix-ui/colors/-/colors-3.0.0.tgz", @@ -14292,10 +14338,11 @@ } }, "node_modules/tslib": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.4.0.tgz", - "integrity": "sha512-d6xOpEDfsi2CZVlPQzGeux8XMwLT9hssAsaPYExaQMuYskwb+x1x7J371tWlbBdWHroy99KnVB6qIkUbs5X3UQ==", - "dev": true + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-2.8.1.tgz", + "integrity": "sha512-oJFu94HQb+KVduSUQL7wnpmqnfmLsOA/nAh6b6EH0wCEoK0/mPeXU6c3wKDV83MkOuHPRHtSXKKU99IBazS/2w==", + "dev": true, + "license": "0BSD" }, "node_modules/type-check": { "version": "0.4.0", diff --git a/package.json b/package.json index 4e3f2404c..b54c8a570 100644 --- a/package.json +++ b/package.json @@ -66,8 +66,8 @@ "@atlaskit/pragmatic-drag-and-drop-hitbox": "^1.1.0", "@atlaskit/pragmatic-drag-and-drop-react-drop-indicator": "^3.2.0", "@babel/plugin-transform-react-pure-annotations": "^7.27.1", - "@dnd-kit/core": "^6.3.1", - "@dnd-kit/sortable": "^10.0.0", + "@dnd-kit/helpers": "^0.3.2", + "@dnd-kit/react": "^0.3.2", "@emotion/react": "^11.13.5", "@emotion/styled": "^11.13.5", "@faker-js/faker": "^10.0.0", diff --git a/stories/react/advanced/With dnd-kit.stories.tsx b/stories/react/advanced/With dnd-kit.stories.tsx index f2049f36e..b777e510d 100644 --- a/stories/react/advanced/With dnd-kit.stories.tsx +++ b/stories/react/advanced/With dnd-kit.stories.tsx @@ -1,120 +1,67 @@ import type { Meta, StoryObj } from "@storybook/react-vite"; import { VList } from "../../../src"; -import React, { CSSProperties, forwardRef, useCallback, useState } from "react"; -import { - DndContext, - closestCenter, - KeyboardSensor, - PointerSensor, - useSensor, - useSensors, - DragOverlay, -} from "@dnd-kit/core"; -import { - arrayMove, - SortableContext, - sortableKeyboardCoordinates, - verticalListSortingStrategy, - useSortable, -} from "@dnd-kit/sortable"; -import { CSS } from "@dnd-kit/utilities"; +import React, { CSSProperties, useRef, useState } from "react"; +import { range } from "../common"; +import { DragDropProvider, DragOverlay } from "@dnd-kit/react"; +import { useSortable } from "@dnd-kit/react/sortable"; +import { move } from "@dnd-kit/helpers"; export default { component: VList, } as Meta; -const Item = forwardRef( - ({ id, style, ...props }, ref) => { - return ( -
- {id} -
- ); - }, -); - -const SortableItem = (props: { id: number }) => { - const { - attributes, - listeners, - setNodeRef, - transform, - transition, - isDragging, - } = useSortable({ id: props.id }); +const itemStyle: CSSProperties = { + height: 50, + borderBottom: "solid 1px #ccc", + background: "#fff", +}; - const style: CSSProperties = { - transform: CSS.Transform.toString(transform), - transition, - cursor: "grab", - visibility: isDragging ? "hidden" : undefined, - }; +const SortableItem = ({ id, index }: { id: number; index: number }) => { + const { ref, isDragging } = useSortable({ id, index }); return ( - +
+ {id} +
); }; export const Default: StoryObj = { name: "With dnd-kit", render: () => { - const [items, setItems] = useState(() => - Array.from({ length: 1000 }, (_, i) => i + 1), - ); - const [activeId, setActiveId] = useState(null); - const sensors = useSensors( - useSensor(PointerSensor), - useSensor(KeyboardSensor, { - coordinateGetter: sortableKeyboardCoordinates, - }), - ); + const [items, setItems] = useState(() => range(1000, (i) => i + 1)); + const snapshot = useRef(items); return ( - { - setActiveId(event.active.id); - }, [])} - onDragEnd={useCallback((event) => { - const { active, over } = event; - - if (active.id !== over.id) { - setItems((items) => { - const oldIndex = items.indexOf(active.id); - const newIndex = items.indexOf(over.id); - return arrayMove(items, oldIndex, newIndex); - }); + { + snapshot.current = structuredClone(items); + }} + onDragOver={(event) => { + setItems((items) => move(items, event)); + }} + onDragEnd={(event) => { + if (event.canceled) { + setItems(snapshot.current); } - setActiveId(null); - }, [])} + }} > - - - {items.map((id) => ( - - ))} - - + + {items.map((id, index) => ( + + ))} + - {activeId != null ? : null} + {(source) =>
{source.id}
}
-
+ ); }, };