以下是 复制文本到剪贴板插件clipboard特效代码 的示例演示效果:
部分效果截图:
HTML代码(index.html):
<!doctype html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>复制文本到剪贴板插件clipboard</title>
<link rel="stylesheet" href="css/bootstrap.min.css">
<link rel="stylesheet" type="text/css" href="css/zzsc-demo.css">
</head>
<body>
<header class="zzsc-header">
<div class="zzsc-demo center">
<a href="index.html" class="current">target-input</a>
<a href="index2.html">textarea</a>
<a href="index3.html">div</a>
<a href="index4.html">text参数</a>
</div>
</header>
<section class="zzsc-container">
<div class="container">
<div class="row mt50">
<div class="col-lg-12">
<div class="input-group">
<input type="text" id="foo" class="form-control" value="复制这里的文字到剪切板中...">
<span class="input-group-btn">
<button class="btn btn-default" type="button" data-clipboard-action="copy" data-clipboard-target="#foo">复制到剪切板</button>
</span>
</div><!-- /input-group -->
</div><!-- /.col-lg-6 -->
</div><!-- /.row -->
</div>
</section>
<script src="js/clipboard.min.js"></script>
<!-- 3. Instantiate clipboard -->
<script>
var clipboard = new Clipboard('.btn');
clipboard.on('success', function(e) {
alert("文字已复制到剪贴板中");
console.log(e);
});
clipboard.on('error', function(e) {
console.log(e);
});
</script>
</body>
</html>
HTML代码(index2.html):
<!doctype html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>复制文本到剪贴板插件clipboard</title>
<link rel="stylesheet" href="css/bootstrap.min.css">
<link rel="stylesheet" type="text/css" href="css/zzsc-demo.css">
</head>
<body>
<header class="zzsc-header">
<div class="zzsc-demo center">
<a href="index.html">target-input</a>
<a href="index2.html" class="current">textarea</a>
<a href="index3.html">div</a>
<a href="index4.html">text参数</a>
</div>
</header>
<section class="zzsc-container">
<div class="container">
<p>点击“剪切”按钮将文本剪切到剪贴板中。</p>
<div class="row mt50">
<div class="col-lg-12">
<textarea id="bar" class="form-control" rows="3">剪切这些文本(你也可以自己输入文本)</textarea><br>
<button type="button" class="btn btn-default" data-clipboard-action="cut" data-clipboard-target="#bar">剪切</button>
</div><!-- /.col-lg-6 -->
</div><!-- /.row -->
</div>
</section>
<script src="js/clipboard.min.js"></script>
<script>
var clipboard = new Clipboard('.btn');
clipboard.on('success', function(e) {
alert("文字已复制到剪贴板中");
console.log(e);
});
clipboard.on('error', function(e) {
console.log(e);
});
</script>
</body>
</html>
JS代码(clipboard-action.js):
import select from 'select';
/** * Inner class which performs selection from either `text` or `target` * properties and then executes copy or cut operations. */
export default class ClipboardAction{
/** * @param{
Object}
options */
constructor(options){
this.resolveOptions(options);
this.initSelection();
}
/** * Defines base properties passed from constructor. * @param{
Object}
options */
resolveOptions(options ={
}
){
this.action = options.action;
this.emitter = options.emitter;
this.target = options.target;
this.text = options.text;
this.trigger = options.trigger;
this.selectedText = '';
}
/** * Decides which selection strategy is going to be applied based * on the existence of `text` and `target` properties. */
initSelection(){
if (this.text && this.target){
throw new Error('Multiple attributes declared,use either "target" or "text"');
}
else if (this.text){
this.selectFake();
}
else if (this.target){
this.selectTarget();
}
else{
throw new Error('Missing required attributes,use either "target" or "text"');
}
}
/** * Creates a fake textarea element,sets its value from `text` property,* and makes a selection on it. */
selectFake(){
this.removeFake();
this.fakeHandler = document.body.addEventListener('click',() => this.removeFake());
this.fakeElem = document.createElement('textarea');
this.fakeElem.style.position = 'absolute';
this.fakeElem.style.left = '-9999px';
this.fakeElem.style.top = (window.pageYOffset || document.documentElement.scrollTop) + 'px';
this.fakeElem.setAttribute('readonly','');
this.fakeElem.value = this.text;
document.body.appendChild(this.fakeElem);
this.selectedText = select(this.fakeElem);
this.copyText();
}
/** * Only removes the fake element after another click event,that way * a user can hit `Ctrl+C` to copy because selection still exists. */
removeFake(){
if (this.fakeHandler){
document.body.removeEventListener('click');
this.fakeHandler = null;
}
if (this.fakeElem){
document.body.removeChild(this.fakeElem);
this.fakeElem = null;
}
}
/** * Selects the content from element passed on `target` property. */
selectTarget(){
this.selectedText = select(this.target);
this.copyText();
}
/** * Executes the copy operation based on the current selection. */
copyText(){
let succeeded;
try{
succeeded = document.execCommand(this.action);
}
catch (err){
succeeded = false;
}
this.handleResult(succeeded);
}
/** * Fires an event based on the copy operation result. * @param{
Boolean}
succeeded */
handleResult(succeeded){
if (succeeded){
this.emitter.emit('success',{
action:this.action,text:this.selectedText,trigger:this.trigger,clearSelection:this.clearSelection.bind(this)}
);
}
else{
this.emitter.emit('error',{
action:this.action,trigger:this.trigger,clearSelection:this.clearSelection.bind(this)}
);
}
}
/** * Removes current selection and focus from `target` element. */
clearSelection(){
if (this.target){
this.target.blur();
}
window.getSelection().removeAllRanges();
}
/** * Sets the `action` to be performed which can be either 'copy' or 'cut'. * @param{
String}
action */
set action(action = 'copy'){
this._action = action;
if (this._action !== 'copy' && this._action !== 'cut'){
throw new Error('Invalid "action" value,use either "copy" or "cut"');
}
}
/** * Gets the `action` property. * @return{
String}
*/
get action(){
return this._action;
}
/** * Sets the `target` property using an element * that will be have its content copied. * @param{
Element}
target */
set target(target){
if (target !== undefined){
if (target && typeof target === 'object' && target.nodeType === 1){
this._target = target;
}
else{
throw new Error('Invalid "target" value,use a valid Element');
}
}
}
/** * Gets the `target` property. * @return{
String|HTMLElement}
*/
get target(){
return this._target;
}
/** * Destroy lifecycle. */
destroy(){
this.removeFake();
}
}
JS代码(clipboard.min.js):
/*! * clipboard.js v1.5.5 * https://zenorocha.github.io/clipboard.js * * Licensed MIT © Zeno Rocha */
!function(t){
if("object"==typeof exports&&"undefined"!=typeof module)module.exports=t();
else if("function"==typeof define&&define.amd)define([],t);
else{
var e;
e="undefined"!=typeof window?window:"undefined"!=typeof global?global:"undefined"!=typeof self?self:this,e.Clipboard=t()}
}
(function(){
var t,e,n;
return function t(e,n,r){
function o(a,c){
if(!n[a]){
if(!e[a]){
var s="function"==typeof require&&require;
if(!c&&s)return s(a,!0);
if(i)return i(a,!0);
var u=new Error("Cannot find module '"+a+"'");
throw u.code="MODULE_NOT_FOUND",u}
var l=n[a]={
exports:{
}
}
;
e[a][0].call(l.exports,function(t){
var n=e[a][1][t];
return o(n?n:t)}
,l,l.exports,t,e,n,r)}
return n[a].exports}
for(var i="function"==typeof require&&require,a=0;
a<r.length;
a++)o(r[a]);
return o}
({
1:[function(t,e,n){
var r=t("matches-selector");
e.exports=function(t,e,n){
for(var o=n?t:t.parentNode;
o&&o!==document;
){
if(r(o,e))return o;
o=o.parentNode}
}
}
,{
"matches-selector":2}
],2:[function(t,e,n){
function r(t,e){
if(i)return i.call(t,e);
for(var n=t.parentNode.querySelectorAll(e),r=0;
r<n.length;
++r)if(n[r]==t)return!0;
return!1}
var o=Element.prototype,i=o.matchesSelector||o.webkitMatchesSelector||o.mozMatchesSelector||o.msMatchesSelector||o.oMatchesSelector;
e.exports=r}
,{
}
],3:[function(t,e,n){
function r(t,e,n,r){
var i=o.apply(this,arguments);
return t.addEventListener(n,i),{
destroy:function(){
t.removeEventListener(n,i)}
}
}
function o(t,e,n,r){
return function(n){
n.delegateTarget=i(n.target,e,!0),n.delegateTarget&&r.call(t,n)}
}
var i=t("closest");
e.exports=r}
,{
closest:1}
],4:[function(t,e,n){
n.node=function(t){
return void 0!==t&&t instanceof HTMLElement&&1===t.nodeType}
,n.nodeList=function(t){
var e=Object.prototype.toString.call(t);
return void 0!==t&&("[object NodeList]"===e||"[object HTMLCollection]"===e)&&"length"in t&&(0===t.length||n.node(t[0]))}
,n.string=function(t){
return"string"==typeof t||t instanceof String}
,n.function=function(t){
var e=Object.prototype.toString.call(t);
return"[object Function]"===e}
}
,{
}
],5:[function(t,e,n){
function r(t,e,n){
if(!t&&!e&&!n)throw new Error("Missing required arguments");
if(!c.string(e))throw new TypeError("Second argument must be a String");
if(!c.function(n))throw new TypeError("Third argument must be a Function");
if(c.node(t))return o(t,e,n);
if(c.nodeList(t))return i(t,e,n);
if(c.string(t))return a(t,e,n);
throw new TypeError("First argument must be a String,HTMLElement,HTMLCollection,or NodeList")}
function o(t,e,n){
return t.addEventListener(e,n),{
destroy:function(){
t.removeEventListener(e,n)}
}
}
function i(t,e,n){
return Array.prototype.forEach.call(t,function(t){
t.addEventListener(e,n)}
),{
destroy:function(){
Array.prototype.forEach.call(t,function(t){
t.removeEventListener(e,n)}
)}
}
}
function a(t,e,n){
return s(document.body,t,e,n)}
var c=t("./is"),s=t("delegate");
e.exports=r}
,{
"./is":4,delegate:3}
],6:[function(t,e,n){
function r(t){
var e;
if("INPUT"===t.nodeName||"TEXTAREA"===t.nodeName)t.focus(),t.setSelectionRange(0,t.value.length),e=t.value;
else{
t.hasAttribute("contenteditable")&&t.focus();
var n=window.getSelection(),r=document.createRange();
r.selectNodeContents(t),n.removeAllRanges(),n.addRange(r),e=n.toString()}
return e}
e.exports=r}
,{
}
],7:[function(t,e,n){
function r(){
}
r.prototype={
on:function(t,e,n){
var r=this.e||(this.e={
}
);
return(r[t]||(r[t]=[])).push({
fn:e,ctx:n}
),this}
,once:function(t,e,n){
function r(){
o.off(t,r),e.apply(n,arguments)}
var o=this;
return r._=e,this.on(t,r,n)}
,emit:function(t){
var e=[].slice.call(arguments,1),n=((this.e||(this.e={
}
))[t]||[]).slice(),r=0,o=n.length;
for(r;
o>r;
r++)n[r].fn.apply(n[r].ctx,e);
return this}
,off:function(t,e){
var n=this.e||(this.e={
}
),r=n[t],o=[];
if(r&&e)for(var i=0,a=r.length;
a>i;
i++)r[i].fn!==e&&r[i].fn._!==e&&o.push(r[i]);
return o.length?n[t]=o:delete n[t],this}
}
,e.exports=r}
,{
}
],8:[function(t,e,n){
"use strict";
function r(t){
return t&&t.__esModule?t:{
"default":t}
}
function o(t,e){
if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}
n.__esModule=!0;
var i=function(){
function t(t,e){
for(var n=0;
n<e.length;
n++){
var r=e[n];
r.enumerable=r.enumerable||!1,r.configurable=!0,"value"in r&&(r.writable=!0),Object.defineProperty(t,r.key,r)}
}
return function(e,n,r){
return n&&t(e.prototype,n),r&&t(e,r),e}
}
(),a=t("select"),c=r(a),s=function(){
function t(e){
o(this,t),this.resolveOptions(e),this.initSelection()}
return t.prototype.resolveOptions=function t(){
var e=arguments.length<=0||void 0===arguments[0]?{
}
:arguments[0];
this.action=e.action,this.emitter=e.emitter,this.target=e.target,this.text=e.text,this.trigger=e.trigger,this.selectedText=""}
,t.prototype.initSelection=function t(){
if(this.text&&this.target)throw new Error('Multiple attributes declared,use either "target" or "text"');
if(this.text)this.selectFake();
else{
if(!this.target)throw new Error('Missing required attributes,use either "target" or "text"');
this.selectTarget()}
}
,t.prototype.selectFake=function t(){
var e=this;
this.removeFake(),this.fakeHandler=document.body.addEventListener("click",function(){
return e.removeFake()}
),this.fakeElem=document.createElement("textarea"),this.fakeElem.style.position="absolute",this.fakeElem.style.left="-9999px",this.fakeElem.style.top=(window.pageYOffset||document.documentElement.scrollTop)+"px",this.fakeElem.setAttribute("readonly",""),this.fakeElem.value=this.text,document.body.appendChild(this.fakeElem),this.selectedText=c.default(this.fakeElem),this.copyText()}
,t.prototype.removeFake=function t(){
this.fakeHandler&&(document.body.removeEventListener("click"),this.fakeHandler=null),this.fakeElem&&(document.body.removeChild(this.fakeElem),this.fakeElem=null)}
,t.prototype.selectTarget=function t(){
this.selectedText=c.default(this.target),this.copyText()}
,t.prototype.copyText=function t(){
var e=void 0;
try{
e=document.execCommand(this.action)}
catch(n){
e=!1}
this.handleResult(e)}
,t.prototype.handleResult=function t(e){
e?this.emitter.emit("success",{
action:this.action,text:this.selectedText,trigger:this.trigger,clearSelection:this.clearSelection.bind(this)}
):this.emitter.emit("error",{
action:this.action,trigger:this.trigger,clearSelection:this.clearSelection.bind(this)}
)}
,t.prototype.clearSelection=function t(){
this.target&&this.target.blur(),window.getSelection().removeAllRanges()}
,t.prototype.destroy=function t(){
this.removeFake()}
,i(t,[{
key:"action",set:function t(){
var e=arguments.length<=0||void 0===arguments[0]?"copy":arguments[0];
if(this._action=e,"copy"!==this._action&&"cut"!==this._action)throw new Error('Invalid "action" value,use either "copy" or "cut"')}
,get:function t(){
return this._action}
}
,{
key:"target",set:function t(e){
if(void 0!==e){
if(!e||"object"!=typeof e||1!==e.nodeType)throw new Error('Invalid "target" value,use a valid Element');
this._target=e}
}
,get:function t(){
return this._target}
}
]),t}
();
n.default=s,e.exports=n.default}
,{
select:6}
],9:[function(t,e,n){
"use strict";
function r(t){
return t&&t.__esModule?t:{
"default":t}
}
function o(t,e){
if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}
function i(t,e){
if("function"!=typeof e&&null!==e)throw new TypeError("Super expression must either be null or a function,not "+typeof e);
t.prototype=Object.create(e&&e.prototype,{
constructor:{
value:t,enumerable:!1,writable:!0,configurable:!0}
}
),e&&(Object.setPrototypeOf?Object.setPrototypeOf(t,e):t.__proto__=e)}
function a(t,e){
var n="data-clipboard-"+t;
if(e.hasAttribute(n))return e.getAttribute(n)}
n.__esModule=!0;
var c=t("./clipboard-action"),s=r(c),u=t("tiny-emitter"),l=r(u),f=t("good-listener"),d=r(f),h=function(t){
function e(n,r){
o(this,e),t.call(this),this.resolveOptions(r),this.listenClick(n)}
return i(e,t),e.prototype.resolveOptions=function t(){
var e=arguments.length<=0||void 0===arguments[0]?{
}
:arguments[0];
this.action="function"==typeof e.action?e.action:this.defaultAction,this.target="function"==typeof e.target?e.target:this.defaultTarget,this.text="function"==typeof e.text?e.text:this.defaultText}
,e.prototype.listenClick=function t(e){
var n=this;
this.listener=d.default(e,"click",function(t){
return n.onClick(t)}
)}
,e.prototype.onClick=function t(e){
var n=e.delegateTarget||e.currentTarget;
this.clipboardAction&&(this.clipboardAction=null),this.clipboardAction=new s.default({
action:this.action(n),target:this.target(n),text:this.text(n),trigger:n,emitter:this}
)}
,e.prototype.defaultAction=function t(e){
return a("action",e)}
,e.prototype.defaultTarget=function t(e){
var n=a("target",e);
return n?document.querySelector(n):void 0}
,e.prototype.defaultText=function t(e){
return a("text",e)}
,e.prototype.destroy=function t(){
this.listener.destroy(),this.clipboardAction&&(this.clipboardAction.destroy(),this.clipboardAction=null)}
,e}
(l.default);
n.default=h,e.exports=n.default}
,{
"./clipboard-action":8,"good-listener":5,"tiny-emitter":7}
]}
,{
}
,[9])(9)}
);
CSS代码(zzsc-demo.css):
@import url(http://fonts.useso.com/css?family=Raleway:200,500,700,800);@font-face{font-family:'icomoon';src:url('../fonts/icomoon.eot?rretjt');src:url('../fonts/icomoon.eot?#iefixrretjt') format('embedded-opentype'),url('../fonts/icomoon.woff?rretjt') format('woff'),url('../fonts/icomoon.ttf?rretjt') format('truetype'),url('../fonts/icomoon.svg?rretjt#icomoon') format('svg');font-weight:normal;font-style:normal;}
[class^="icon-"],[class*=" icon-"]{font-family:'icomoon';speak:none;font-style:normal;font-weight:normal;font-variant:normal;text-transform:none;line-height:1;/* Better Font Rendering =========== */
-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;}
body,html{font-size:100%;padding:0;margin:0;}
/* Reset */
*,*:after,*:before{-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;}
/* Clearfix hack by Nicolas Gallagher:http://nicolasgallagher.com/micro-clearfix-hack/ */
.clearfix:before,.clearfix:after{content:" ";display:table;}
.clearfix:after{clear:both;}
body{background:#494A5F;color:#D5D6E2;font-weight:500;font-size:1.05em;font-family:"Microsoft YaHei","宋体","Segoe UI","Lucida Grande",Helvetica,Arial,sans-serif,FreeSans,Arimo;}
a{color:#2fa0ec;text-decoration:none;outline:none;}
a:hover,a:focus{color:#74777b;}
.zzsc-container{margin:0 auto;text-align:center;overflow:hidden;}
.zzsc-content{font-size:150%;padding:1em 0;}
.zzsc-content h2{margin:0 0 2em;opacity:0.1;}
.zzsc-content p{margin:1em 0;padding:5em 0 0 0;font-size:0.65em;}
.bgcolor-1{background:#f0efee;}
.bgcolor-2{background:#f9f9f9;}
.bgcolor-3{background:#e8e8e8;}
/*light grey*/
.bgcolor-4{background:#2f3238;color:#fff;}
/*Dark grey*/
.bgcolor-5{background:#df6659;color:#521e18;}
/*pink1*/
.bgcolor-6{background:#2fa8ec;}
/*sky blue*/
.bgcolor-7{background:#d0d6d6;}
/*White tea*/
.bgcolor-8{background:#3d4444;color:#fff;}
/*Dark grey2*/
.bgcolor-9{background:#ef3f52;color:#fff;}
/*pink2*/
.bgcolor-10{background:#64448f;color:#fff;}
/*Violet*/
.bgcolor-11{background:#3755ad;color:#fff;}
/*dark blue*/
.bgcolor-12{background:#3498DB;color:#fff;}
/*light blue*/
.bgcolor-20{background:#494A5F;color:#D5D6E2;}
/* Header */
.zzsc-header{padding:1em 190px 1em;letter-spacing:-1px;text-align:center;background:#66677c;}
.zzsc-header h1{color:#D5D6E2;font-weight:600;font-size:2em;line-height:1;margin-bottom:0;font-family:"Microsoft YaHei","宋体","Segoe UI","Lucida Grande",Helvetica,Arial,sans-serif,FreeSans,Arimo;}
.zzsc-header h1 span{font-family:"Microsoft YaHei","宋体","Segoe UI","Lucida Grande",Helvetica,Arial,sans-serif,FreeSans,Arimo;display:block;font-size:60%;font-weight:400;padding:0.8em 0 0.5em 0;color:#c3c8cd;}
/*nav*/
.zzsc-demo a{color:#fff;text-decoration:none;}
.zzsc-demo{width:100%;padding-bottom:1.2em;}
.zzsc-demo a{display:inline-block;margin:0.5em;padding:0.6em 1em;border:3px solid #fff;font-weight:700;}
.zzsc-demo a:hover{opacity:0.6;}
.zzsc-demo a.current{background:#1d7db1;color:#fff;}
/* Top Navigation Style */
.zzsc-links{position:relative;display:inline-block;white-space:nowrap;font-size:1.5em;text-align:center;}
.zzsc-links::after{position:absolute;top:0;left:50%;margin-left:-1px;width:2px;height:100%;background:#dbdbdb;content:'';-webkit-transform:rotate3d(0,0,1,22.5deg);transform:rotate3d(0,0,1,22.5deg);}
.zzsc-icon{display:inline-block;margin:0.5em;padding:0em 0;width:1.5em;text-decoration:none;}
.zzsc-icon span{display:none;}
.zzsc-icon:before{margin:0 5px;text-transform:none;font-weight:normal;font-style:normal;font-variant:normal;font-family:'icomoon';line-height:1;speak:none;-webkit-font-smoothing:antialiased;}
/* footer */
.zzsc-footer{width:100%;padding-top:10px;}
.zzsc-small{font-size:0.8em;}
.center{text-align:center;}
.mt50{margin-top:50px;}
/****/
.related{color:#fff;background:#494A5F;text-align:center;font-size:1.25em;padding:0.5em 0;overflow:hidden;}
.related > a{vertical-align:top;width:calc(100% - 20px);max-width:340px;display:inline-block;text-align:center;margin:20px 10px;padding:25px;font-family:"Microsoft YaHei","宋体","Segoe UI","Lucida Grande",Helvetica,Arial,sans-serif,FreeSans,Arimo;}
.related a{display:inline-block;text-align:left;margin:20px auto;padding:10px 20px;opacity:0.8;-webkit-transition:opacity 0.3s;transition:opacity 0.3s;-webkit-backface-visibility:hidden;}
.related a:hover,.related a:active{opacity:1;}
.related a img{max-width:100%;opacity:0.8;border-radius:4px;}
.related a:hover img,.related a:active img{opacity:1;}
.related h3{font-family:"Microsoft YaHei",sans-serif;}
.related a h3{font-weight:300;margin-top:0.15em;color:#fff;}
/* icomoon */
.icon-zzsc-home-outline:before{content:"\e5000";}
.icon-zzsc-arrow-forward-outline:before{content:"\e5001";}
@media screen and (max-width:50em){.zzsc-header{padding:3em 10% 4em;}
.zzsc-header h1{font-size:2em;}
}
@media screen and (max-width:40em){.zzsc-header h1{font-size:1.5em;}
}
@media screen and (max-width:30em){.zzsc-header h1{font-size:1.2em;}
}