在 Mac 版 Chrome 上拦截 cmd+c(用于自定义复制)不可靠,我做错了什么?

问题描述 投票:0回答:1

对于我工作中的内部工具,我试图拦截并覆盖 ctrl/cmd+c 快捷方式。

上下文:下面的脚本被添加到从我的应用程序导出的 html 文件中。其目的是确保当用户复制一段文本时,我的自定义标记会完全按原样写入剪贴板,而不会在正常复制文本时添加 Chrome 添加的任何样式元素。

从功能上来说,我希望它的工作方式与 ctrl/cmd+c 正常工作方式完全一样,以免破坏我同事的肌肉记忆工作流程。我们中的一些人使用 Mac,一些人使用 PC,但我们都使用 Chrome。

<script>
document.addEventListener('keydown', function (event) {
  event.stopPropagation();
  var selected ='';
  var element = '';
  if ((event.ctrlKey || event.metaKey) && (event.key === 'c' || event.key === 'C')) {
    selected = window.getSelection();
    if (selected != '') {
       var selectedElement = document.createElement('div');
       selectedElement.setAttribute('id','selection');
       for (var i = 0, len = selected.rangeCount; i < len; ++i) {
          selectedElement.appendChild(selected.getRangeAt(i).cloneContents());
       }
       document.getElementById('export').appendChild(selectedElement);
       element = document.getElementById('selection');
    } else { element = document.getElementById('export'); }
    navigator.clipboard.write([new ClipboardItem({
      'text/plain': new Blob([element.innerText], {type: 'text/plain'}),
      'text/html': new Blob([element.innerHTML], {type: 'text/html'})
    })])
  document.getElementById('selection').remove();
  }
});
</script>

keydown 事件侦听器正在检查 ctrl/cmd 与“c”/“C”的组合。触发时,脚本首先检查选择是否存在。如果是这样,所选文本将被克隆并附加到文档中,以使 Chrome 将其呈现为单独的 div 元素,然后写入剪贴板,然后再次删除。这似乎是一种迂回的做事方式,但这是我能找到的访问所选内容的innerText和innerHTML的唯一方法(通过暂时将所选内容变成它自己的div元素),并且它有效。

如果未选择任何内容,则包含整个文档的名为“export”的 div 元素将被写入剪贴板(我认为如果您想复制整个文本,能够跳过 ctrl/cmd+a 会很方便)。

无论如何,这一切都不重要。我的问题是该脚本每次都能在 PC 版 Chrome 上可靠地运行。但是当我在 Mac 上尝试时,快捷方式似乎在大约三分之二的时间里被忽略,即它没有被拦截,并且剪贴板内容是您在没有脚本的情况下获得的内容。真的很奇怪:我可以连续十次按下 cmd+c 并粘贴到剪贴板检查器中,结果是不可预测的。

为什么这样的东西只能在某些时候起作用?我究竟做错了什么? event.metaKey 是否已知不可靠?免责声明:我不是经验丰富的编码员,请保持温柔。 🥲

javascript google-chrome addeventlistener
1个回答
1
投票

感谢使用 copy 事件和

preventDefault()
对此解决方案的评论中的
somethinghere
!在 PC 和 Mac 上都可以使用。

<script>
document.addEventListener('copy', (event) => {
  event.preventDefault();
  var selected ='';
  var element = '';
  selected = window.getSelection();
  if (selected != '') {
     var selectedElement = document.createElement('div');
     selectedElement.setAttribute('id','selection');
     for (var i = 0, len = selected.rangeCount; i < len; ++i) {
        selectedElement.appendChild(selected.getRangeAt(i).cloneContents());
     }
     document.getElementById('export').appendChild(selectedElement);
     element = document.getElementById('selection');
  } else { element = document.getElementById('export'); }
  navigator.clipboard.write([new ClipboardItem({
    'text/plain': new Blob([element.innerText], {type: 'text/plain'}),
    'text/html': new Blob([element.innerHTML], {type: 'text/html'})
  })])
  document.getElementById('selection').remove();
});
</script>
© www.soinside.com 2019 - 2024. All rights reserved.