From 0d60d4033955abf67599ec9671bde24b1c6e701a Mon Sep 17 00:00:00 2001 From: Bill Dwyer Date: Thu, 10 Nov 2016 13:39:36 -0800 Subject: [PATCH] Clipboard bugfix Brings over bug fix for table clipboard issue that was fixed on the internal repo. --- packages/table/src/common/clipboard.ts | 29 ++++++++++++++++++++++---- 1 file changed, 25 insertions(+), 4 deletions(-) diff --git a/packages/table/src/common/clipboard.ts b/packages/table/src/common/clipboard.ts index 9711427d8a..377095096d 100644 --- a/packages/table/src/common/clipboard.ts +++ b/packages/table/src/common/clipboard.ts @@ -30,7 +30,7 @@ export const Clipboard = { * See `Clipboard.copy` */ copyCells(cells: string[][]) { - const table = document.createElement("tbody"); + const table = document.createElement("table"); Clipboard.applySelectableStyles(table); for (const row of cells) { const tr = table.appendChild(document.createElement("tr")); @@ -40,7 +40,8 @@ export const Clipboard = { } } - return Clipboard.copyElement(table); + const tsv = cells.map((row) => row.join("\t")).join("\n"); + return Clipboard.copyElement(table, tsv); }, /** @@ -54,13 +55,19 @@ export const Clipboard = { Clipboard.applySelectableStyles(text); text.value = value; - return Clipboard.copyElement(text); + return Clipboard.copyElement(text, value); }, /** * Copies the element and its children to the clipboard. Returns a boolean * indicating whether the copy succeeded. * + * If a plaintext argument is supplied, we add both the text/html and + * text/plain mime types to the clipboard. This preserves the built in + * semantics of copying elements to the clipboard while allowing custom + * plaintext output for programs that can't cope with HTML data in the + * clipboard. + * * Verified on Firefox 47, Chrome 51. * * Note: Sometimes the copy does not succeed. Presumably, in order to @@ -69,7 +76,7 @@ export const Clipboard = { * inconsistent limit at about 300KB or 40,000 cells. Depending on the on * the content of cells, your limits may vary. */ - copyElement(elem: HTMLElement) { + copyElement(elem: HTMLElement, plaintext?: string) { if (!Clipboard.isCopySupported()) { return false; } @@ -78,6 +85,20 @@ export const Clipboard = { document.body.appendChild(elem); try { window.getSelection().selectAllChildren(elem); + + if (plaintext != null) { + // add plaintext fallback + // http://stackoverflow.com/questions/23211018/copy-to-clipboard-with-jquery-js-in-chrome + elem.addEventListener("copy", (e: UIEvent) => { + e.preventDefault(); + const clipboardData = (e as any).clipboardData || (window as any).clipboardData; + if (clipboardData != null) { + clipboardData.setData("text/html", elem.outerHTML); + clipboardData.setData("text/plain", plaintext); + } + }); + } + return document.execCommand("copy"); } catch (err) { return false;