前端实现一键复制

本文介绍了如何在HTML和JavaScript中利用navigator.clipboardAPI实现在点击按钮时自动复制服务器信息(如MAC地址、CPU序列号等),并处理了浏览器兼容性问题,以提高技术人员获取license的效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言

需求: 因项目需要License认证,认证页面有服务器信息。 服务器信息可一键复制发送给技术人员,方便生成license。使用​navigator.clipboard​ 全局对象就是来处理剪贴板的,对于clipboard​ 的API,JS剪切板操作一文写的很清楚。
问题: 项目发布后发现,只有我开发环境可以实现一键复制。原因:只有 HTTPS 协议的页面才能使用Clipboard API。不过,开发环境(localhost)允许使用非加密协议
解决方案: 使用clipboard.js插件

下面是两种方式实现一键复制,需要的 小伙伴各取所需

项目效果如下:

在这里插入图片描述

一、JS实现一键复制

限制:js Clipboard API 对安全性有要求,项目需使用https

html代码

 <fieldset id="systemField">
      <legend>服务器信息</legend>
      <div style="padding:10px">
        <div class="copyDiv">
          <button id="copyBtn">{{replicatedShow ? "已复制":"一键复制"}}</button>
        </div>
        <div id="systemInfoBtn">
          <div class="text item">
            <span>MAC地址: </span> <span class="spanLabel">{{systemForm.macAddressList}}</span>
          </div>
          <div class="text item">
            <span>CPU序列号: </span> <span class="spanLabel">{{systemForm.cpuSerial}}</span>
          </div>
          <div class="text item">
            <span>主板序列号: </span> <span class="spanLabel">{{systemForm.mainBoardSerial}}</span>
          </div>
        </div>
      </div>
</fieldset>

js代码

 mounted: function () {
    const clipboard = navigator.clipboard;
    const button = document.getElementById("copyBtn");
    button.addEventListener("click", async () => {
      if (!clipboard) {
        this.$Tips.tipWarningBox("当前浏览器不支持剪切板复制!");
        return;
      }
      var content = document.getElementById("systemInfoBtn").innerText;
      try {
      //将信息写入剪切板,显示已复制,3s后显示一键复制
        await clipboard.writeText(content);
        this.replicatedShow = true;
        setTimeout(() => {
          this.replicatedShow = false;
        }, 3000);
      } catch (error) {
        console.log("failed", error);
      }
    });
  },

完整代码

<template lang="html">
  <div v-loading="loading" class="licenseDiv">
    <fieldset id="systemField">
      <legend>服务器信息</legend>
      <div style="padding:10px">
        <div class="copyDiv">
          <button id="copyBtn">{{replicatedShow ? "已复制" :"一键复制"}}</button>
        </div>
        <div id="systemInfoBtn">
          <div class="text item">
            <span>MAC地址: </span> <span class="spanLabel">{{systemForm.macAddressList}}</span>
          </div>
          <div class="text item">
            <span>CPU序列号: </span> <span class="spanLabel">{{systemForm.cpuSerial}}</span>
          </div>
          <div class="text item">
            <span>主板序列号: </span> <span class="spanLabel">{{systemForm.mainBoardSerial}}</span>
          </div>
        </div>
      </div>
    </fieldset>
  </div>
</template>
<script>
export default {
  data() {
    return {
      loading: false,
      systemForm: {},
      replicatedShow: false,
    };
  },
  created: function () {
    this.getSystemData();
  },
  mounted: function () {
    const clipboard = navigator.clipboard;
    const button = document.getElementById("copyBtn");
    button.addEventListener("click", async () => {
      if (!clipboard) {
        this.$Tips.tipWarningBox("当前浏览器不支持剪切板复制!");
        return;
      }
      var content = document.getElementById("systemInfoBtn").innerText;
      try {
        await clipboard.writeText(content);
        this.replicatedShow = true;
        setTimeout(() => {
          this.replicatedShow = false;
        }, 3000);
      } catch (error) {
        console.log("failed", error);
      }
    });
  },
  methods: {
    getSystemData() {
      this.systemForm.macAddressList = "01:30:16:9a:92:04";
      this.systemForm.cpuSerial = "0F3BFBDF120405F0";
      this.systemForm.mainBoardSerial =
        "VMware-42 1a 76 d2 8c 6f 58 c4-a8 85 78 51 11 71 cd 3a";
    },
  },
};
</script>

<style lang="less" scoped>
.licenseDiv {
  padding: 10px;
  width: 45%;
  height: 100vh;
  margin: 2% auto;
}
.text {
  font-size: 12px;
}
.item {
  padding: 4px 0;
}
.spanLabel {
  padding-left: 6px;
  color: #b1b0b0;
}
.copyDiv {
  float: right;
  margin: -20px -8px 0 0;
  display: none;
}
// 鼠标悬浮显示按钮
#systemField:hover .copyDiv {
  display: block;
}
// 按钮样式
#copyBtn {
  display: inline-block;
  line-height: 1;
  white-space: nowrap;
  cursor: pointer;
  background: #fff;
  border: 1px solid #dcdfe6;
  color: #606266;
  -webkit-appearance: none;
  text-align: center;
  box-sizing: border-box;
  outline: 0;
  margin: 0;
  transition: 0.1s;
  font-weight: 500;
  padding: 3px;
  // padding: 12px 20px;
  font-size: 12px;
  border-radius: 3px;
}
// 按钮悬浮效果
#copyBtn:hover {
  color: #409eff;
  border-color: #c6e2ff;
  background-color: #ecf5ff;
}
</style>

文本选中效果
项目中没有用到这个效果,把代码贴出来,有备无患

//文本选中效果
function selectText(element) {
  if (window.getSelection && document.createRange) {
    var selection = window.getSelection();
    var range = document.createRange();
    range.selectNodeContents(element);
    selection.removeAllRanges();
    selection.addRange(range);
  } else if (document.body.createTextRange) { // 支持 IE < 9
    var textRange = document.body.createTextRange();
    textRange.moveToElementText(element);
    textRange.select();
  }
}
 
// 使用方法:
var element = document.getElementById('systemInfoBtn');
selectText(element);

二、clipboard.js插件实现一键复制

官网文档非常清楚,需要的小伙伴直接去看官网

1.安装插件

npm install clipboard --save

2.在所需组件引入

import Clipboard from “clipboard”

3.传入一个DOM 选择器, HTML 元素, 或者 HTML 元素数组作为参数,来实例化对象

var clipboard = new Clipboard(“#copyBtn”) //调用就能复制

4.使用
触发器的data-clipboard-target要与复制目标的id一致

html代码:

	<!--触发器  data-clipboard-target="#systemInfoBtn"-->
 <div class="copyDiv">
   <button id="copyBtn" data-clipboard-target="#systemInfoBtn">{{replicatedShow ? "已复制" :"一键复制"}}</button>
  </div>
  <!--目标   id="systemInfoBtn" -->
  <div id="systemInfoBtn">
    <div class="text item">
      <span>MAC地址: </span> <span class="spanLabel">{{systemForm.macAddressList}}</span>
    </div>
    <div class="text item">
      <span>CPU序列号: </span> <span class="spanLabel">{{systemForm.cpuSerial}}</span>
    </div>
    <div class="text item">
      <span>主板序列号: </span> <span class="spanLabel">{{systemForm.mainBoardSerial}}</span>
    </div>
  </div>

js代码:

 let self = this;
 const button = document.getElementById("copyBtn");
 button.addEventListener("click", async () => {
   var clipboard = new Clipboard("#copyBtn");
   //复制成功后的操作:改为已复制,3s后还原为一键复制
   clipboard.on("success", function (e) {
     self.replicatedShow = true;
     //取消对文本的选择
     e.clearSelection();
     setTimeout(() => {
       self.replicatedShow = false;
     }, 3000);
   });

   clipboard.on("error", function (e) {
     self.$Tips.tipWarningBox("当前浏览器不支持剪切板复制!");
   });

完整代码

<template lang="html">
  <div v-loading="loading" class="licenseDiv">
    <fieldset id="systemField">
      <legend>服务器信息</legend>
      <div style="padding:10px">
        <div class="copyDiv">
          <button id="copyBtn"  data-clipboard-target="#systemInfoBtn">{{replicatedShow ? "已复制" :"一键复制"}}</button>
        </div>
        <div id="systemInfoBtn">
          <div class="text item">
            <span>MAC地址: </span> <span class="spanLabel">{{systemForm.macAddressList}}</span>
          </div>
          <div class="text item">
            <span>CPU序列号: </span> <span class="spanLabel">{{systemForm.cpuSerial}}</span>
          </div>
          <div class="text item">
            <span>主板序列号: </span> <span class="spanLabel">{{systemForm.mainBoardSerial}}</span>
          </div>
        </div>
      </div>
    </fieldset>
  </div>
</template>
<script>
export default {
  data() {
    return {
      loading: false,
      systemForm: {},
      replicatedShow: false,
    };
  },
  created: function () {
    this.getSystemData();
  },
  mounted: function () {
   let self = this;
   const button = document.getElementById("copyBtn");
   button.addEventListener("click", async () => {
     //实例化对象
     var clipboard = new Clipboard("#copyBtn");
      //复制成功后的操作:改为已复制,3s后还原为一键复制
     clipboard.on("success", function (e) {
       //取消本文选择效果
       self.replicatedShow = true;
       e.clearSelection();
       setTimeout(() => {
         self.replicatedShow = false;
       }, 3000);
     });

     clipboard.on("error", function (e) {
       self.$Tips.tipWarningBox("当前浏览器不支持剪切板复制!");
     });
   }); 
  },
  methods: {
    getSystemData() {
      this.systemForm.macAddressList = "01:30:16:9a:92:04";
      this.systemForm.cpuSerial = "0F3BFBDF120405F0";
      this.systemForm.mainBoardSerial =
        "VMware-42 1a 76 d2 8c 6f 58 c4-a8 85 78 51 11 71 cd 3a";
    },
  },
};
</script>

<style lang="less" scoped>
.licenseDiv {
  padding: 10px;
  width: 45%;
  height: 100vh;
  margin: 2% auto;
}
.text {
  font-size: 12px;
}
.item {
  padding: 4px 0;
}
.spanLabel {
  padding-left: 6px;
  color: #b1b0b0;
}
.copyDiv {
  float: right;
  margin: -20px -8px 0 0;
  display: none;
}
// 鼠标悬浮显示按钮
#systemField:hover .copyDiv {
  display: block;
}
// 按钮样式
#copyBtn {
  display: inline-block;
  line-height: 1;
  white-space: nowrap;
  cursor: pointer;
  background: #fff;
  border: 1px solid #dcdfe6;
  color: #606266;
  -webkit-appearance: none;
  text-align: center;
  box-sizing: border-box;
  outline: 0;
  margin: 0;
  transition: 0.1s;
  font-weight: 500;
  padding: 3px;
  // padding: 12px 20px;
  font-size: 12px;
  border-radius: 3px;
}
// 按钮悬浮效果
#copyBtn:hover {
  color: #409eff;
  border-color: #c6e2ff;
  background-color: #ecf5ff;
}
</style>
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值