From 30fe30de6383a85b905e464498c972769d8061e5 Mon Sep 17 00:00:00 2001 From: Sean Doyle Date: Tue, 10 Dec 2024 15:38:17 -0500 Subject: [PATCH] Customize Attachment Preview URL Related to [#1154][] First, document the existing Attachment previewing process, including _which_ content types are supported out of the box. Next, resolve some `ManagedAttachment` to `Attachment` proxying issues. The `ManagedAttachment` class is what gets dispatched as part of `trix-attachment-add` events. It does not inherit from `Attachment`, but instead proxies method calls and property access. Prior to this commit, there were some proxy definition gaps. For example, the `ManagedAttachment` [declares a proxy for the `setAttribute` method][setAttribute]. Unfortunately, an `Attachment.setAttribute` method did not exist prior to these changes. This commit remedies that. Next, this commit adds proxy definitions for `Attachment.setPreviewURL` and `Attachment.getPreviewURL` so that event handlers can customize the value from the event-level `ManagedAttachment` instance, without deeply reaching into the `Attachment` instance (via `event.attachment.attachment`). [#1154]: https://github.com/basecamp/trix/issues/1154 [setAttribute]: https://github.com/basecamp/trix/blob/5db0ea49180de97f27b0becf47440690a1eaa39c/src/trix/models/managed_attachment.js#L22 --- README.md | 21 +++++++++++++++++++++ src/test/system/attachment_test.js | 23 +++++++++++++++++++++++ src/trix/models/attachment.js | 4 ++++ src/trix/models/managed_attachment.js | 2 ++ 4 files changed, 50 insertions(+) diff --git a/README.md b/README.md index c4008b844..80ee389e6 100644 --- a/README.md +++ b/README.md @@ -300,6 +300,27 @@ To store attachments, listen for the `trix-attachment-add` event. Upload the att If you don’t want to accept dropped or pasted files, call `preventDefault()` on the `trix-file-accept` event, which Trix dispatches just before the `trix-attachment-add` event. +## Previewing Attached Files + +Trix automatically previews attached image files. To determine whether or not to preview an attached file, Trix compares the file's content type against the [Trix.Attachment.previewablePattern](./src/trix/models/attachment.js#L7). By default, Trix will preview the following content types: + +* `image/gif` +* `image/png` +* `image/webp` +* `image/jpg` +* `image/jpeg` + +To customize an attachment's preview, listen for the `trix-attachment-add` event. When handling the event, set the attachment's `previewable` attribute, then change its preview URL by calling `setPreviewURL`: + +```js +addEventListener("trix-attachment-add", (event) => { + if (event.attachment.file instanceof File) { + event.attachment.setAttribute("previewable", true) + event.attachment.setPreviewURL("...") + } +}) +``` + # Editing Text Programmatically You can manipulate a Trix editor programmatically through the `Trix.Editor` interface, available on each `` element through its `editor` property. diff --git a/src/test/system/attachment_test.js b/src/test/system/attachment_test.js index 9cabe8602..9b4dcd005 100644 --- a/src/test/system/attachment_test.js +++ b/src/test/system/attachment_test.js @@ -156,6 +156,29 @@ testGroup("Attachments", { template: "editor_with_image" }, () => { assert.textAttributes([ 1, 2 ], {}) expectDocument(`${OBJECT_REPLACEMENT_CHARACTER}${OBJECT_REPLACEMENT_CHARACTER}\n`) }) + + test("setting previewURL makes an Attachment previewable", async () => { + getEditorElement().addEventListener("trix-attachment-add", async ({ attachment }) => { + attachment.setAttribute("previewable", true) + attachment.setPreviewURL("/loading.png") + + await delay(50) + + attachment.setPreviewURL("/loaded.png") + }, { once: true }) + + getComposition().insertFile(createFile()) + + const loadingImg = getEditorElement().querySelector("img") + + assert.ok(/loading.png$/.test(loadingImg.src), "sets previewURL to loading image") + + await delay(50) + + const loadedImg = getEditorElement().querySelector("img") + + assert.ok(/loaded.png$/.test(loadedImg.src), "sets previewURL to loaded image") + }) }) }) diff --git a/src/trix/models/attachment.js b/src/trix/models/attachment.js index 686abe5da..3ad842acf 100644 --- a/src/trix/models/attachment.js +++ b/src/trix/models/attachment.js @@ -32,6 +32,10 @@ export default class Attachment extends TrixObject { this.didChangeAttributes() } + setAttribute(attribute, value) { + this.setAttributes({ [attribute]: value }) + } + getAttribute(attribute) { return this.attributes.get(attribute) } diff --git a/src/trix/models/managed_attachment.js b/src/trix/models/managed_attachment.js index 588c2e6f7..2233219e2 100644 --- a/src/trix/models/managed_attachment.js +++ b/src/trix/models/managed_attachment.js @@ -23,6 +23,8 @@ ManagedAttachment.proxyMethod("attachment.setAttributes") ManagedAttachment.proxyMethod("attachment.isPending") ManagedAttachment.proxyMethod("attachment.isPreviewable") ManagedAttachment.proxyMethod("attachment.getURL") +ManagedAttachment.proxyMethod("attachment.getPreviewURL") +ManagedAttachment.proxyMethod("attachment.setPreviewURL") ManagedAttachment.proxyMethod("attachment.getHref") ManagedAttachment.proxyMethod("attachment.getFilename") ManagedAttachment.proxyMethod("attachment.getFilesize")