javascript - document.execCommand (‘cut’/‘copy’ ) 在小书签中被拒绝

标签 javascript firefox bookmarklet

我正在开发一个小书签,它可以创建当前浏览器选项卡的 href 链接并将其复制到剪贴板。此书签适用于 Safari:

javascript:
!function(a){
var%20b=document.createElement("textarea"),
c=document.getSelection();
b.textContent=a,document.body.appendChild(b),
c.removeAllRanges(),b.select(),
document.execCommand("copy"),
c.removeAllRanges(),
document.body.removeChild(b)}
('<a%20title="'+document.title+'"%20href="'+document.location.href+'">'+document.title+'</a>');

但在 Firefox 65 中,我收到错误消息“document.execCommand(‘cut’/‘copy’) 被拒绝,因为它不是从短时间运行的用户生成的事件处理程序中调用的。”在看Copying to clipboard with document.execCommand('copy') fails with big texts我正在尝试在解决答案中指出的问题的函数之前生成链接的 html。但是,使用下面的代码,我得到了一个新的浏览器选项卡,其中包含文本“true”并且没有复制到剪贴板的链接。

javascript:
const text = ('<a%20title="'+document.title+'"%20href="'+document.location.href+'">'+document.title+'</a>');
!function(a){
var%20b=document.createElement("textarea"),
c=document.getSelection();
b.textContent=a,document.body.appendChild(b),
c.removeAllRanges(),
b.select(),
document.execCommand("copy"),
c.removeAllRanges(),
document.body.removeChild(b)}('text');

这是 href 链接生成的时间问题吗?还是别的?

最佳答案

您的问题与the other Q/A 中的问题不同:在您的情况下,您没有任何用户触发的事件。

所以不,这不是时间问题,只是您需要这样的事件。

要强制执行它,您可以显示启动画面,要求小书签的用户单击页面。从此点击事件中,您将调用 execCommand('copy')

javascript:(function(a){
  var splash = document.createElement('div'),
    msg = document.createElement('span');
  splash.style='position:fixed;top:0;left:0;width:100vw;height:100vh;display:flex;justify-content:center;align-items:center;background:#FFF;z-index:999999';
  msg.textContent = 'click me';
  splash.append(msg);
  // wait for the click event
  splash.onclick = evt => {
    var b=document.createElement("textarea"),
    c=document.getSelection();
    b.textContent=a,
    document.body.appendChild(b),
    c.removeAllRanges(),
    b.select(),
    document.execCommand("copy"),
    c.removeAllRanges(),
    document.body.removeChild(b),
    document.body.removeChild(splash);
  };
  document.body.append(splash);
})

这是一个实际发生的例子(显然不是书签):

(function(a){
  var splash = document.createElement('div'),
    msg = document.createElement('span');
  splash.style='position:fixed;top:0;left:0;width:100vw;height:100vh;display:flex;justify-content:center;align-items:center;background:#FFF;z-index:999999';
  msg.textContent = 'click me';
  splash.append(msg);
  // wait for the click event
  splash.onclick = evt => {
    var b=document.createElement("textarea"),
    c=document.getSelection();
    b.textContent=a,
    document.body.appendChild(b),
    c.removeAllRanges(),
    b.select(),
    document.execCommand("copy"),
    c.removeAllRanges(),
    document.body.removeChild(b),
    document.body.removeChild(splash);
  };
  document.body.append(splash);
})
('<a%20title="'+document.title+'"%20href="'+document.location.href+'">'+document.title+'</a>');
<textarea>You can paste here to check what's been copied</textarea>

关于javascript - document.execCommand (‘cut’/‘copy’ ) 在小书签中被拒绝,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54608727/

相关文章:

javascript - Angular promise 队列并显示加载数据

angularjs - Angular ui-可排序 : Stop click event on drop in Firefox

Ajax 帖子被 firefox 中止(在 Chrome 或 IE 中看不到)

HTML5 在 Firefox 中显示嵌入式音频、视频的下载按钮

javascript - 书签标题

javascript - 添加包含 JavaScript 的书签,而不是 URL

javascript - 在 3D 数组中设置一个值会改变其他值

javascript - 无法使用 $pull (Mongoose) 删除用户模型数组中的对象

javascript - 在 node js/javascript 中使用 OR 条件时,传入的参数必须是 Buffer 或 12 个字节的字符串或 24 个十六进制字符的字符串