点击复制文本字符串

54
我想要能够在点击时复制文本字符串,而不需要按钮。文本字符串将位于一个"span"类中。
  1. 用户将鼠标悬停在文本字符串上
  2. 用户点击文本字符串
  3. 文本字符串被复制到剪贴板

你卡在“没有按钮”的部分了吗?也就是说,你想知道如何为一个span元素编写点击事件处理程序吗?(提示:它非常、非常类似于按钮上的点击事件处理程序。)如果直到用户点击才会发生任何事情,那么你关于悬停的第一点似乎不相关。 - nnnnnn
@matthew 你复制完后想要把内容粘贴到哪里呢? - mayank
12个回答

69

您可以将copy事件附加到<span>元素上,在事件处理程序中使用document.execCommand("copy"),使用event.clipboardData.setData()方法将span.textContent设置为event.clipboardData

const span = document.querySelector("span");

span.onclick = function() {
  document.execCommand("copy");
}

span.addEventListener("copy", function(event) {
  event.preventDefault();
  if (event.clipboardData) {
    event.clipboardData.setData("text/plain", span.textContent);
    console.log(event.clipboardData.getData("text"))
  }
});
<span>text</span>


1
如何通过单击兄弟DIV按钮来实现此操作? - Flo
@Flo 你可以使用相同的模式。将 copy 事件附加到一个元素上,在事件处理程序中设置剪贴板数据。 - guest271314
我如何在没有“复制”事件的情况下获取clipboardData?例如从另一个事件处理程序,比如单击另一个元素的事件处理程序中获取。但是“复制”事件没有触发。 - Chloe
3
如果用户已经选择了一些文本,这段代码容易出现问题。请参阅 https://dev59.com/H1cO5IYBdhLWcg3w7lgm#53977796 获取完整解决方案。 - Natesh bhat

45

试试这个。document.execCommand('copy')

  1. 点击元素并复制文本,然后将其粘贴到临时输入元素中。
  2. 然后从此输入框中复制文本。

function copy(that){
var inp =document.createElement('input');
document.body.appendChild(inp)
inp.value =that.textContent
inp.select();
document.execCommand('copy',false);
inp.remove();
}
<p onclick="copy(this)">hello man</p>


这种方法很有效,但如何复制包括换行符的文本呢?(在js中为\n,在html中为 )我已经设置了一个onclick事件到<code>标签上,所以用户只需点击即可复制代码,但仍然无法复制新行。如果需要,我可以提供更多解释和代码。 - Malmadork
这个有效了,非常感谢你的帮助!! - Aryan
这个可以正常使用,但你有没有想过如何在Bootstrap模态框中让它正常运作? - Hashmi

24

使用剪贴板 API!

最简单的现代解决方案是:

navigator.clipboard.writeText(value)

该值以后可以通过以下方式访问:

navigator.clipboard.readText()

注意:这需要使用 https,因此默认情况下无法在 localhost 上运行。

NOTE: To use in an iframe, you'll need to add write (and maybe read) permissions

<iframe src='' allow='clipboard-read; clipboard-write'/>
注意:要在浏览器扩展程序(网页)中使用,您需要执行以下操作之一:
1. 从用户触发的事件(例如点击)中调用; 2. 在清单文件中添加“clipboardWrite”权限。

NOTE: To use in the dev console, use copy() instead

copy('string')

W3Schools 教程

CanIUse


2
终于!我正要说“难道没有人考虑使用navigator.clipboard吗?” - user14018874
2
我其实很惊讶这不是最佳答案。Clipboard API 很强大。 - PCPbiscuit
FireFox 112: 未捕获的类型错误:navigator.clipboard 未定义 - mtoloo

22

这是 Code pen

<link href='https://fonts.googleapis.com/css?family=Oswald' rel='stylesheet' type='text/css'> 
<p style="color:wheat;font-size:55px;text-align:center;">How to copy a TEXT to Clipboard on a Button-Click</p>

<center>
<p id="p1">This is  TEXT 1</p>
<p id="p2">This is TEXT 2</p><br/>

<button onclick="copyToClipboard('#p1')">Copy TEXT 1</button>
<button onclick="copyToClipboard('#p2')">Copy TEXT 2</button>

<br/><br/><input class="textBox" type="text" id="" placeholder="Dont belive me?..TEST it here..;)" />
</center>

Jquery的代码在这里

function copyToClipboard(element) {
  var $temp = $("<input>");
  $("body").append($temp);
  $temp.val($(element).text()).select();
  document.execCommand("copy");
  $temp.remove();
}

7
人们在搜索如何复制文本时,可能会考虑使用jQuery作为选项,尽管OP可能不会直接从我的答案中受益,但很多社区成员会受益。 - Black Mamba

10

在复制文本的同时,您还需要确保在将其复制到剪贴板后,任何先前选择的组件仍然保持选中状态。

以下是完整代码:

const copyToClipboard = str => {
  const el = document.createElement('textarea');  // Create a <textarea> element
  el.value = str;                                 // Set its value to the string that you want copied
  el.setAttribute('readonly', '');                // Make it readonly to be tamper-proof
  el.style.position = 'absolute';                 
  el.style.left = '-9999px';                      // Move outside the screen to make it invisible
  document.body.appendChild(el);                  // Append the <textarea> element to the HTML document
  const selected =            
    document.getSelection().rangeCount > 0        // Check if there is any content selected previously
      ? document.getSelection().getRangeAt(0)     // Store selection if found
      : false;                                    // Mark as false to know no selection existed before
  el.select();                                    // Select the <textarea> content
  document.execCommand('copy');                   // Copy - only works as a result of a user action (e.g. click events)
  document.body.removeChild(el);                  // Remove the <textarea> element
  if (selected) {                                 // If a selection existed before copying
    document.getSelection().removeAllRanges();    // Unselect everything on the HTML document
    document.getSelection().addRange(selected);   // Restore the original selection
  }
};

添加来源请参考此链接


2
这应该是正确的答案。被接受的答案有误。 - user0103
我已经阅读了你的回答和原始内容,但不知何故,在将相关元素复制后,无法让浏览器(Firefox)重新选择先前选择的文本。不确定如何进行调试;没有控制台问题。 - Martin

4

guest271314的回答应用于多个元素:

spans = document.querySelectorAll(".class");
for (const span of spans) {
  span.onclick = function() {
    document.execCommand("copy");
  }

  span.addEventListener("copy", function(event) {
    event.preventDefault();
    if (event.clipboardData) {
      event.clipboardData.setData("text/plain", span.textContent);
      console.log(event.clipboardData.getData("text"))
    }
  });
}
<span class="class">text</span>
<br>
<span class="class">text2</span>


4

execCommand() 方法曾经用于将文本复制到剪贴板,但已被弃用,在现代 Web 开发中不应再使用。相反,navigator.clipboard API 现在是浏览器中执行剪贴板操作的推荐方式。该 API 是内置的浏览器 Web API,这意味着它既安全又易于集成到您的 Web 应用程序中,无需任何外部依赖。

剪贴板 API 可用于在 Web 应用程序中实现剪切、复制和粘贴功能。

以下代码片段仅会复制所点击的 span 元素的内容。

jQuery:

$(document).on('click', 'span', function() {
      let copyText = $(this)[0].textContent
      navigator.clipboard.writeText(copyText)
})

Javascript

document.addEventListener('click', function(event) {
  if (event.target.tagName === 'SPAN') {
    let copyText = event.target.textContent;
    navigator.clipboard.writeText(copyText);
  }
});

可以根据需要进行自定义。


3

这是最合适的方法。它将复制所有带有“copy”类的元素中的文本。

var copy = document.querySelectorAll(".copy"); 

for (const copied of copy) { 
  copied.onclick = function() { 
    document.execCommand("copy"); 
  };  
  copied.addEventListener("copy", function(event) { 
    event.preventDefault(); 
    if (event.clipboardData) { 
      event.clipboardData.setData("text/plain", copied.textContent);
      console.log(event.clipboardData.getData("text"))
    };
  });
};
.copy {
            
  cursor: copy;
            
}
<p><span class="copy">Text</span></p>
<p><span class="copy">More Text</span></p>
<p><span class="copy">Even More Text</span></p>


3

HTML:

<button type='button' id='btn'>Copy</button>

JS

document.querySelect('#btn').addEventListener('click', function() {
   copyToClipboard('copy this text');
});

JS / 函数:

function copyToClipboard(text) {
    var selected = false;
    var el = document.createElement('textarea');
    el.value = text;
    el.setAttribute('readonly', '');
    el.style.position = 'absolute';
    el.style.left = '-9999px';
    document.body.appendChild(el);
    if (document.getSelection().rangeCount > 0) {
        selected = document.getSelection().getRangeAt(0)
    }
    el.select();
    document.execCommand('copy');
    document.body.removeChild(el);
    if (selected) {
        document.getSelection().removeAllRanges();
        document.getSelection().addRange(selected);
    }
};

2

你也可以使用 onclick,像这样:

 function copyCode() {
  const Code = document.querySelector("input");
  Code.select();
  document.execCommand("copy", false);
}
<input type="input"  />
<button onclick={copyCode()}>Copy</button>


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