The problem
Typically, this is how copying text is done (taken from here):
- Create a
<textarea>element to be appended to the document. Set itsvalueto the string that we want to copy to the clipboard. - Append said
<textarea>element to the current HTML document. - Use
HTMLInputElement.select()to select the contents of the<textarea>element. - Use
document.execCommand('copy')to copy the contents of the<textarea>to the clipboard. - Remove the
<textarea>element from the document.
The code looks like this:
function copyToClipboard(text) {
const el = document.createElement('textarea');
el.value = text;
document.body.appendChild(el);
el.select();
document.execCommand('copy');
document.body.removeChild(el);
};There are two problems with this approach:
- There may be some flashing due to the temporary
<textarea>element. - It will unselect whatever the user is selecting.
We can work around both, but the function will become much longer.
Solution
When the user initiates a copy action, the user agent fires a clipboard event name copy.
W3C Specification
- Use
addEventListenerto attach our custom event handler, which will override the current data with our text. - Use
document.execCommand('copy')to trigger the copy action. - Use
removeEventListenerto remove our event handler.
function copyToClipboard(text) {
const listener = function(ev) {
ev.preventDefault();
ev.clipboardData.setData('text/plain', text);
};
document.addEventListener('copy', listener);
document.execCommand('copy');
document.removeEventListener('copy', listener);
}Bonus
You can even copy rich text!
function copyRichText(text) {
const listener = function(ev) {
ev.preventDefault();
ev.clipboardData.setData('text/html', text);
ev.clipboardData.setData('text/plain', text);
};
document.addEventListener('copy', listener);
document.execCommand('copy');
document.removeEventListener('copy', listener);
}
copyRichText('<i>Markup</i> <b>text</b>. Paste me into a rich text editor.');Browser compatibility
According to MDN Web Docs, this should work on all major browsers except Internet Explorer.
Works very well. Thanks for posting this tip.