使用document.execCommand('copy')复制大文本到剪贴板失败

11

我正在使用一个隐藏的文本区域来放置一些文本,选择它,然后使用document.execCommand将其复制到剪贴板。通常这样做可以成功,但当文本很大时会失败(返回false)。在Chrome v55中,它似乎在大约180K个字符左右就会失败。

这种方式可以复制的数据量是否有限制?普通的Ctrl+C似乎不受相同的限制。

注意:有人将此标记为可能是Does document.execCommand('copy') have a size limitation?的重复问题。虽然这可能是类似的问题,但那个问题被标记为一个我不使用的特定框架,并且还没有得到解答。我认为我的问题更加普遍且仍然相关。

我附上参考代码。

      function copyTextToClipboard(text) {
        var textArea = document.createElement('textarea');
        textArea.style.position = 'fixed';
        textArea.style.top = 0;
        textArea.style.left = 0;
        textArea.style.width = '2em';
        textArea.style.height = '2em';
        textArea.style.padding = 0;
        textArea.style.border = 'none';
        textArea.style.outline = 'none';
        textArea.style.boxShadow = 'none';
        textArea.style.background = 'transparent';
        textArea.value = text;
        document.body.appendChild(textArea);
        textArea.select();
        try {
          var successful = document.execCommand('copy');
          var msg = successful ? 'successful' : 'unsuccessful';
          console.log('Copying text command was ' + msg);
        } catch (err) {
          console.log('Oops, unable to copy');
        }
        document.body.removeChild(textArea);
      }

可能是Does document.execCommand('copy') have a size limitation?的重复问题。 - Tushar Vaghela
1
那个问题没有解决。 - Pablo Varasa
2个回答

17
问题与渲染长文本所需的时间有关,而不是execCommand('copy')调用本身。Firefox会显示一个相当解释性的错误消息:

document.execCommand('cut'/'copy')被拒绝,因为它没有在一个短时间运行的用户生成事件处理程序中调用。

代码需要花费太长时间来生成文本,因此浏览器不将其识别为半受信任事件...... 解决方案是先生成此文本,然后仅在侦听到用户手势时调用execCommand。例如,可以侦听mousedown事件以生成文本,仅在mouseup事件中才真正执行复制命令。

const text = ('some text a bit repetitive ' + Date.now()).repeat(50000);

function copyTextToClipboard(text) {
  // first we create the textArea
  var textArea = document.createElement('textarea');
  textArea.style.position = 'absolute';
  textArea.style.opacity = '0';
  textArea.value = text;
  document.body.appendChild(textArea);

  var execCopy = e => {   // triggered on mouseup
    textArea.select();
    var successful = document.execCommand('copy');
    var msg = successful ? 'successful' : 'unsuccessful';
    console.log('Copying text command was ' + msg);
    document.body.removeChild(textArea);
  };
  // here the magic
  btn.addEventListener('mouseup', execCopy, {
    once: true 
  });
}
// triggered on mousedown
btn.onmousedown = e => copyTextToClipboard(text);
<button id="btn">copy some text in your clipboard</button>
<p>May struggle your browser a little bit, it's quite a long text... Please be patient</p>


0

我曾经遇到过类似的问题,并想出了以下解决方法:如何将超大文本复制到剪贴板?

思路是检查要复制到剪贴板的内容大小,如果超过150k个符号,则创建一个文本文件并将其提供给用户。

使用5年后,我从终端用户那里没有听到任何抱怨。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接