From 9ac0e75f9abc77000f4e5f6de7d318206c0b58b0 Mon Sep 17 00:00:00 2001 From: Juanjo Diaz Date: Mon, 28 Nov 2022 19:17:24 +0100 Subject: [PATCH] fix: sync local clipboard to remote on canvas focus --- core/clipboard.js | 26 ++++++-------------------- tests/test.clipboard.js | 14 ++++++-------- 2 files changed, 12 insertions(+), 28 deletions(-) diff --git a/core/clipboard.js b/core/clipboard.js index d2e0de3c0..79822e1dc 100644 --- a/core/clipboard.js +++ b/core/clipboard.js @@ -10,8 +10,7 @@ export default class Clipboard { this._eventHandlers = { 'copy': this._handleCopy.bind(this), - 'paste': this._handlePaste.bind(this), - 'pasteOnWindows': this._handlePasteOnWindow.bind(this) + 'focus': this._handleFocus.bind(this) }; // ===== EVENT HANDLERS ===== @@ -40,7 +39,7 @@ export default class Clipboard { } } - async _handlePaste(e) { + async _handleFocus() { try { if (navigator.permissions && navigator.permissions.query) { const permission = await navigator.permissions.query({ name: "clipboard-read", allowWithoutGesture: false }); @@ -50,26 +49,15 @@ export default class Clipboard { // Some browsers might error due to lack of support, e.g. Firefox. } - let data; if (navigator.clipboard.readText) { try { - data = await navigator.clipboard.readText(); + const data = await navigator.clipboard.readText(); + this.onpaste(data); } catch (e) { /* Do nothing */ return; } - } else if (e.clipboardData) { - data = e.clipboardData.getData('text/plain'); } - this.onpaste(data); - } - - // For some reason, the paste event doesn't trigger on the canvas element. - // As a workaround, we capture it on the window and check if the active - // element is the canvas. - async _handlePasteOnWindow(e) { - if (document.activeElement !== this._target) return; - this._eventHandlers.paste(e); } // ===== PUBLIC METHODS ===== @@ -77,15 +65,13 @@ export default class Clipboard { grab() { if (!Clipboard.isSupported) return; this._target.addEventListener('copy', this._eventHandlers.copy); - // this._target.addEventListener('paste', this._eventHandlers.paste); - window.addEventListener('paste', this._eventHandlers.pasteOnWindows); + this._target.addEventListener('focus', this._eventHandlers.focus); } ungrab() { if (!Clipboard.isSupported) return; this._target.removeEventListener('copy', this._eventHandlers.copy); - // this._target.removeEventListener('paste', this._eventHandlers.paste); - window.removeEventListener('paste', this._eventHandlers.pasteOnWindows); + this._target.removeEventListener('focus', this._eventHandlers.focus); } } diff --git a/tests/test.clipboard.js b/tests/test.clipboard.js index 7b400e605..5861b290e 100644 --- a/tests/test.clipboard.js +++ b/tests/test.clipboard.js @@ -46,16 +46,14 @@ describe('Automatic Clipboard Sync', function () { it('should copy local pasted data to the server clipboard', async function () { const text = 'Another random string for testing'; const clipboard = new Clipboard(); - clipboard.onpaste = pasterText => expect(pasterText).to.equal(text); + + clipboard.onpaste = pastedText => expect(pastedText).to.equal(text); if (Clipboard.isSupported) { - const clipboardData = new DataTransfer(); - clipboardData.setData("text/plain", text); - const clipboardEvent = new ClipboardEvent('paste', { clipboardData }); - // Force initialization since the constructor is broken in Firefox - if (!clipboardEvent.clipboardData.items.length) { - clipboardEvent.clipboardData.items.add(text, "text/plain"); + if (navigator.clipboard.readText) { + navigator.clipboard.readText.restore(); + sinon.stub(navigator.clipboard, "readText").returns(text); } - await clipboard._handlePaste(clipboardEvent); + await clipboard._handleFocus(); if (navigator.clipboard.readText) { expect(navigator.clipboard.readText).to.have.been.called; }