Dragging a PDF onto another PDF deletes it
Nobody has claimed this yet.
Assessment
- Difficulty
- 2/5
- Estimated time
- 1-3 hours
- Newbie friendliness
- 78/100
- Issue type
- Bug
- Clarity
- Clearly specified
- Activity status
- Quiet
- Tech stack
- javascript
- Domain
- frontend
Research direction
Start in src/editor/attachments/drag_and_drop.js at #dropOntoImage and compare its behavior with #reorderInGallery and the gallery checks in src/nodes/image_gallery_node.js. Run the browser test suite with the PDF or video reproduction. Done means dropping an unsupported previewable attachment is a no-op rather than deleting it, with gallery markers considered separately.
Written by the indexing model from the issue text.
Description
Dragging a PDF onto another PDF deletes the dragged one. It is not added to a gallery and not returned to where it came from, so the attachment is simply lost. The usual gallery drop markers appear beforehand, so it looks like a supported drop right up until the content disappears.
This affects any previewable non-image attachment, so videos too.
Steps to reproduce
- Attach a PDF, press Enter, attach a second PDF, so there are two standalone attachments.
- Wait for both first-page thumbnails to render. This matters: the attachments have to be previewable for the drop target to match.
- Drag the second PDF onto the middle of the first.
Expected: either they form a gallery, or nothing happens.
Actual: the dragged PDF is deleted.
Cause
The drop target is resolved in the DOM, where the selector matches any previewable attachment:
// src/editor/attachments/drag_and_drop.js
const targetFigure = element.closest("figure.attachment--preview[data-lexical-node-key]")
Gallery membership, though, is decided on content type, which excludes PDFs and videos:
// src/nodes/image_gallery_node.js
static isValidChild(node) {
return $isActionTextAttachmentNode(node) && node.isPreviewableImage
}
#dropOntoImage removes the dragged node before consulting the gallery, and re-inserts it only when $findOrCreateGalleryForImage returns one. When those two checks disagree, the node is removed and never put back:
#dropOntoImage(draggedNode, targetKey, position) {
const targetNode = $getNodeByKey(targetKey)
if (!targetNode || !$isActionTextAttachmentNode(targetNode)) return
if (draggedNode.is(targetNode)) return
draggedNode.remove()
const gallery = $findOrCreateGalleryForImage(targetNode)
if (gallery) {
if (position === "before") {
targetNode.insertBefore(draggedNode)
} else {
targetNode.insertAfter(draggedNode)
}
}
}
#reorderInGallery has the same remove-then-insert shape but always inserts, so it is unaffected.
Suggested fix
Resolve the gallery first and bail out before mutating anything, so an unsupported drop is a no-op rather than a deletion.
Separately, it would be worth not showing the gallery drop markers for a target that cannot accept the drop, since the DOM-level attachment--preview check is broader than isValidChild.
Version
lexxy 0.9.29, Rails 8.2.0.alpha, Active Storage with the Poppler previewer. Reproduced in Chromium via the browser test suite.
- Dominant language
- JavaScript
- Stars
- 1.2k
- Forks
- 119
- Avg merge
- 2d 11h
- Merged PRs (30d)
- 11
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
More from basecamp/lexxy
-
Difficulty 1/5 Under an hour Newbie friendliness 92/100
-
Korean IME: Enter in an attachment caption duplicates the last composed syllable into the editor Open
Difficulty 2/5 1-3 hours Newbie friendliness 87/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
-
Difficulty 1/5 Under an hour Newbie friendliness 85/100
Similar issues
-
Difficulty 2/5 1-3 hours Newbie friendliness 88/100
HarperFast/skills#96 ·
-
[Block] Latest Posts [Type] Bug
Difficulty 2/5 1-3 hours Newbie friendliness 76/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 78/100
Automattic/studio#4908 ·
-
Difficulty 2/5 1-3 hours Newbie friendliness 74/100
-
Difficulty 2/5 1-3 hours Newbie friendliness 86/100
sugarlabs/musicblocks#8847 ·