Skip to content

Commit

Permalink
DEP Replace react-dnd with dnd-kit
Browse files Browse the repository at this point in the history
  • Loading branch information
GuySartorelli committed Dec 19, 2024
1 parent f9e0402 commit c26d42d
Show file tree
Hide file tree
Showing 18 changed files with 210 additions and 306 deletions.
2 changes: 1 addition & 1 deletion client/dist/js/TinyMCE_sslink-file.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion client/dist/js/TinyMCE_ssmedia.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion client/dist/js/bundle.js

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion client/dist/styles/bundle.css

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion client/src/components/BackButton/BackButton.js
Original file line number Diff line number Diff line change
Expand Up @@ -54,4 +54,4 @@ BackButton.propTypes = {

export { BackButton as Component };

export default droppable('GalleryItem')(BackButton);
export default droppable(BackButton);
9 changes: 6 additions & 3 deletions client/src/components/GalleryItem/GalleryItem.js
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,10 @@ class GalleryItem extends Component {
thumbnailClassNames.push('gallery-item__thumbnail--no-preview');
}

if (this.props.item.type === 'folder') {
thumbnailClassNames.push('gallery-item__thumbnail--folder');
}

// Check loading status of thumbnail
switch (this.props.loadState) {
// Show loading indicator for preloading images
Expand Down Expand Up @@ -603,10 +607,9 @@ function mapDispatchToProps(dispatch) {
}

const ConnectedGalleryItem = connect(mapStateToProps, mapDispatchToProps)(GalleryItem);
const type = 'GalleryItem';

const File = createSelectable(draggable(type)(ConnectedGalleryItem));
const Folder = createSelectable(droppable(type)(File));
const File = createSelectable(draggable(ConnectedGalleryItem));
const Folder = createSelectable(droppable(File));
export {
GalleryItem as Component,
Folder,
Expand Down
56 changes: 28 additions & 28 deletions client/src/components/GalleryItem/GalleryItem.scss
Original file line number Diff line number Diff line change
Expand Up @@ -298,23 +298,23 @@ $gallery-item-label-height: 40px;
}

.gallery-item--archive .gallery-item__thumbnail {
background: $white url("../../images/icon_archive.png") center center no-repeat;
background: transparent url("../../images/icon_archive.png") center center no-repeat;
}

.gallery-item--audio .gallery-item__thumbnail {
background: $white url("../../images/icon_audio.png") center center no-repeat;
background: transparent url("../../images/icon_audio.png") center center no-repeat;
}

.gallery-item--video .gallery-item__thumbnail {
background: $white url("../../images/icon_video.png") center center no-repeat;
background: transparent url("../../images/icon_video.png") center center no-repeat;
}

.gallery-item--document .gallery-item__thumbnail {
background: $white url("../../images/icon_document.png") center center no-repeat;
background: transparent url("../../images/icon_document.png") center center no-repeat;
}

.gallery-item--false .gallery-item__thumbnail {
background: $white url("../../images/icon_file.png") center center no-repeat;
background: transparent url("../../images/icon_file.png") center center no-repeat;
}

// Individual progress bar
Expand Down Expand Up @@ -417,35 +417,20 @@ $gallery-item-label-height: 40px;
.gallery-item--dragging {
opacity: 0.2;

&.gallery-item {
cursor: grabbing;
}

.gallery-item__drag-layer-item & {
.gallery-item__drag-layer & {
opacity: 1;
}
}

.gallery-item__drag-layer {
position: fixed;
inset: 0;
pointer-events: none;
z-index: 100;
}

.gallery-item__drag-layer-preview {
transform: scale(0.4) translate(-100%, -160%);
border: 1px solid $component-active-border-color;

.gallery-item__thumbnail {
transform: scale(2.5) translate(22px, 16px);
}
}

.gallery-item__drag-layer-item {
transform: scale(0.4);
transform-origin: 0 0;
display: inline-block;
position: relative;
opacity: 1;
inset: 0;
z-index: 100;
cursor: grabbing;

.gallery-item {
border-width: 2px;
Expand All @@ -456,14 +441,29 @@ $gallery-item-label-height: 40px;
.gallery-item__title {
display: none;
}

.gallery-item__thumbnail--folder,
.gallery-item__drag-layer-count {
transform: scale(2.5);
}

.gallery-item__thumbnail--folder {
transform-origin: top center;
background-position: center;
}
}

.gallery-item__drag-layer-preview {
pointer-events: none;
border: 1px solid $component-active-border-color;
}

.gallery-item__drag-layer-count {
display: inline-block;
position: absolute;
font-size: 1rem;
top: -45%;
left: 25%;
top: 0;
right: 0;
z-index: 105;
}

Expand Down
92 changes: 27 additions & 65 deletions client/src/components/GalleryItem/GalleryItemDragLayer.js
Original file line number Diff line number Diff line change
@@ -1,76 +1,38 @@
import React, { Component } from 'react';
import React from 'react';
import PropTypes from 'prop-types';
import { DragLayer } from 'react-dnd';
import Badge from 'components/Badge/Badge';
import GalleryItem from './GalleryItem';

class GalleryItemDragLayer extends Component {
getOffset() {
const {
offset,
dragged,
} = this.props;
return {
transform: offset && `translate(${offset.x + dragged.x}px, ${offset.y + dragged.y}px)`,
};
}
function GalleryItemDragLayer(props) {
const { draggingItems, draggingItemProps } = props;
const selectionCount = draggingItems.length;
const shadows = [
selectionCount > 1
? <div key="1" className="gallery-item__drag-shadow" />
: null,
selectionCount > 2
? <div key="2" className="gallery-item__drag-shadow gallery-item__drag-shadow--second" />
: null,
];

render() {
if (!this.props.isDragging) {
return null;
}
const { item } = this.props;
if (!item.selected) {
return null;
}
const selectionCount = item.selected.length;
const shadows = [
selectionCount > 1
? <div key="1" className="gallery-item__drag-shadow" />
: null,
selectionCount > 2
? <div key="2" className="gallery-item__drag-shadow gallery-item__drag-shadow--second" />
: null,
];

return (
<div className="gallery-item__drag-layer">
<div className="gallery-item__drag-layer-item" style={this.getOffset()}>
<div className="gallery-item__drag-layer-preview">
{shadows}
<GalleryItem {...item.props} isDragging />
</div>
{selectionCount > 1
? (
<Badge
className="gallery-item__drag-layer-count"
status="info"
message={`${selectionCount}`}
/>
)
: null
}
</div>
return (
<div className="gallery-item__drag-layer">
<div className="gallery-item__drag-layer-preview">
{shadows}
<GalleryItem {...draggingItemProps} isDragging />
{selectionCount > 1 && <Badge
className="gallery-item__drag-layer-count"
status="info"
message={`${selectionCount}`}
/>}
</div>
);
}
</div>
);
}

GalleryItemDragLayer.propTypes = {
item: PropTypes.object,
offset: PropTypes.shape({
x: PropTypes.number.isRequired,
y: PropTypes.number.isRequired,
}),
isDragging: PropTypes.bool.isRequired,
draggingItems: PropTypes.arrayOf(PropTypes.number).isRequired,
draggingItemProps: PropTypes.object.isRequired,
};

const collect = (monitor) => ({
item: monitor.getItem(),
offset: monitor.getInitialClientOffset(),
dragged: monitor.getDifferenceFromInitialOffset(),
isDragging: monitor.isDragging(),
});

// eslint-disable-next-line new-cap
export default DragLayer(collect)(GalleryItemDragLayer);
export default GalleryItemDragLayer;
25 changes: 12 additions & 13 deletions client/src/components/GalleryItem/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@ Displays a file/folder as a thumbnail with relevant actions.

## Example
```js
<GalleryItem item={{id: 2}} selectable={true} />
<GalleryItem item={{id: 2, exists: true, type: 'file', category: 'document'}} selectable={true} />
<GalleryItem item={{id: 2, exists: true, type: 'folder', category: 'folder'}} selectable={true} />
```

## Properties
Expand All @@ -29,13 +30,13 @@ Helps apply react-dnd to Files, so that the file can interact with dragging.
## Example

```js
const draggableComponent = draggable('Item')(Component);
const draggableComponent = draggable(Component);
```

## Properties
* `item` (object) (required): File details to display for.
* `onDrag` (function): Callback for when the item is starting or ending being dragged.
* `selectedFiles` (array): A list of ids that have been selected.

* `item` (object) (required): File details to display for. Minimally needs a unique `id` property.
* `canDrag` (bool): Whether this item can be dragged right now. Assumed `true` if missing.

# droppable HOC

Expand All @@ -44,18 +45,16 @@ Helps apply react-dnd to Folders, so that a file could be dragged on it with the
## Example

```js
const droppableComponent = droppable('Item')(Component);
const droppableComponent = droppable(Component);
```

## Properties

* `item` (object) (required): File details to display for.
* `item` (object) (required): File details to display for. Minimally needs a unique `id` property.

# GalleryItemDragLayer Component

The custom preview item to show instead of the HTML5 default preview.

__NOTE__: This does lose some nice functionality, like the "slingshot back" to place effect when dropping onto nothing droppable.
The custom preview item to show instead of just dragging the existing file/folder presentation

## Example

Expand All @@ -64,6 +63,6 @@ __NOTE__: This does lose some nice functionality, like the "slingshot back" to p
```

## Properties
* `item` (object): File details to display for.
* `offset` (object): Co-ordinates for the item's offset.
* `isDragging` (boolean): Is an item currently being dragged.

* `draggingItemProps` (object) (required): Props for the item being dragged.
* `draggingItems` (array) (required): Array of IDs of all items being dragged (includes selected items).
96 changes: 25 additions & 71 deletions client/src/components/GalleryItem/draggable.js
Original file line number Diff line number Diff line change
@@ -1,75 +1,29 @@
import React, { Component } from 'react';
import React from 'react';
import PropTypes from 'prop-types';
import { DragSource } from 'react-dnd';
import { getEmptyImage } from 'react-dnd-html5-backend';

export default function draggable(type) {
const spec = {
canDrag(props) {
return props.canDrag;
},
beginDrag(props) {
const { id } = props.item;
if (typeof props.onDrag === 'function') {
props.onDrag(true, id);
}
const selected = props.selectedFiles.concat([]);
if (!selected.includes(id)) {
selected.push(id);
}

return { selected, props };
},
endDrag(props) {
const { id } = props.item;
if (typeof props.onDrag === 'function') {
props.onDrag(false, id);
}
},
import { useDraggable } from '@dnd-kit/core';

export default function draggable(Item) {
function DraggableItem(props) {
const canDrag = typeof props.canDrag === 'boolean' ? props.canDrag : true;
const { attributes, listeners, setNodeRef } = useDraggable({ disabled: !canDrag, id: props.item.id, data: { props } });
const item = <Item {...props} />;

return <div
className="gallery-item__draggable"
// The `draggable` attribute is needed to tell react-selectable to not start selecting on mousedown
draggable
ref={setNodeRef}
{...listeners}
{...attributes}
>{ item }</div>;
}

DraggableItem.propTypes = {
item: PropTypes.shape({
id: PropTypes.number.isRequired,
}).isRequired,
canDrag: PropTypes.bool,
};

const collect = (connect, monitor) => ({
connectDragPreview: connect.dragPreview(),
connectDragSource: connect.dragSource(),
isDragging: monitor.isDragging(),
});

// eslint-disable-next-line new-cap
const dragItem = DragSource(type, spec, collect);

return (Item) => {
class DraggableItem extends Component {
componentDidMount() {
// Use empty image as a drag preview so browsers don't draw it
// and we can draw whatever we want on the custom drag layer instead.
this.props.connectDragPreview(getEmptyImage(), {
// IE fallback: specify that we'd rather screenshot the node
// when it already knows it's being dragged so we can hide it with CSS.
captureDraggingState: true,
});
}

render() {
const { connectDragSource } = this.props;
const item = <Item {...this.props} />;

if (typeof item.type === 'string') {
return connectDragSource(item);
}
return connectDragSource(<div className="gallery-item__draggable">{ item }</div>);
}
}

DraggableItem.propTypes = {
connectDragSource: PropTypes.func.isRequired,
connectDragPreview: PropTypes.func.isRequired,
item: PropTypes.shape({
id: PropTypes.number.isRequired,
}).isRequired,
onDrag: PropTypes.func,
selectedFiles: PropTypes.arrayOf(PropTypes.number),
};

return dragItem(DraggableItem);
};
return DraggableItem;
}
Loading

0 comments on commit c26d42d

Please sign in to comment.