/*! * clipboard.js v2.0.4 * https://zenorocha.github.io/clipboard.js * * licensed mit © zeno rocha */ (function webpackuniversalmoduledefinition(root, factory) { if(typeof exports === 'object' && typeof module === 'object') module.exports = factory(); else if(typeof define === 'function' && define.amd) define([], factory); else if(typeof exports === 'object') exports["clipboardjs"] = factory(); else root["clipboardjs"] = factory(); })(this, function() { return /******/ (function(modules) { // webpackbootstrap /******/ // the module cache /******/ var installedmodules = {}; /******/ /******/ // the require function /******/ function __webpack_require__(moduleid) { /******/ /******/ // check if module is in cache /******/ if(installedmodules[moduleid]) { /******/ return installedmodules[moduleid].exports; /******/ } /******/ // create a new module (and put it into the cache) /******/ var module = installedmodules[moduleid] = { /******/ i: moduleid, /******/ l: false, /******/ exports: {} /******/ }; /******/ /******/ // execute the module function /******/ modules[moduleid].call(module.exports, module, module.exports, __webpack_require__); /******/ /******/ // flag the module as loaded /******/ module.l = true; /******/ /******/ // return the exports of the module /******/ return module.exports; /******/ } /******/ /******/ /******/ // expose the modules object (__webpack_modules__) /******/ __webpack_require__.m = modules; /******/ /******/ // expose the module cache /******/ __webpack_require__.c = installedmodules; /******/ /******/ // define getter function for harmony exports /******/ __webpack_require__.d = function(exports, name, getter) { /******/ if(!__webpack_require__.o(exports, name)) { /******/ object.defineproperty(exports, name, { enumerable: true, get: getter }); /******/ } /******/ }; /******/ /******/ // define __esmodule on exports /******/ __webpack_require__.r = function(exports) { /******/ if(typeof symbol !== 'undefined' && symbol.tostringtag) { /******/ object.defineproperty(exports, symbol.tostringtag, { value: 'module' }); /******/ } /******/ object.defineproperty(exports, '__esmodule', { value: true }); /******/ }; /******/ /******/ // create a fake namespace object /******/ // mode & 1: value is a module id, require it /******/ // mode & 2: merge all properties of value into the ns /******/ // mode & 4: return value when already ns object /******/ // mode & 8|1: behave like require /******/ __webpack_require__.t = function(value, mode) { /******/ if(mode & 1) value = __webpack_require__(value); /******/ if(mode & 8) return value; /******/ if((mode & 4) && typeof value === 'object' && value && value.__esmodule) return value; /******/ var ns = object.create(null); /******/ __webpack_require__.r(ns); /******/ object.defineproperty(ns, 'default', { enumerable: true, value: value }); /******/ if(mode & 2 && typeof value != 'string') for(var key in value) __webpack_require__.d(ns, key, function(key) { return value[key]; }.bind(null, key)); /******/ return ns; /******/ }; /******/ /******/ // getdefaultexport function for compatibility with non-harmony modules /******/ __webpack_require__.n = function(module) { /******/ var getter = module && module.__esmodule ? /******/ function getdefault() { return module['default']; } : /******/ function getmoduleexports() { return module; }; /******/ __webpack_require__.d(getter, 'a', getter); /******/ return getter; /******/ }; /******/ /******/ // object.prototype.hasownproperty.call /******/ __webpack_require__.o = function(object, property) { return object.prototype.hasownproperty.call(object, property); }; /******/ /******/ // __webpack_public_path__ /******/ __webpack_require__.p = ""; /******/ /******/ /******/ // load entry module and return exports /******/ return __webpack_require__(__webpack_require__.s = 0); /******/ }) /************************************************************************/ /******/ ([ /* 0 */ /***/ (function(module, exports, __webpack_require__) { "use strict"; var _typeof = typeof symbol === "function" && typeof symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof symbol === "function" && obj.constructor === symbol && obj !== symbol.prototype ? "symbol" : typeof obj; }; var _createclass = function () { function defineproperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; object.defineproperty(target, descriptor.key, descriptor); } } return function (constructor, protoprops, staticprops) { if (protoprops) defineproperties(constructor.prototype, protoprops); if (staticprops) defineproperties(constructor, staticprops); return constructor; }; }(); var _clipboardaction = __webpack_require__(1); var _clipboardaction2 = _interoprequiredefault(_clipboardaction); var _tinyemitter = __webpack_require__(3); var _tinyemitter2 = _interoprequiredefault(_tinyemitter); var _goodlistener = __webpack_require__(4); var _goodlistener2 = _interoprequiredefault(_goodlistener); function _interoprequiredefault(obj) { return obj && obj.__esmodule ? obj : { default: obj }; } function _classcallcheck(instance, constructor) { if (!(instance instanceof constructor)) { throw new typeerror("cannot call a class as a function"); } } function _possibleconstructorreturn(self, call) { if (!self) { throw new referenceerror("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; } function _inherits(subclass, superclass) { if (typeof superclass !== "function" && superclass !== null) { throw new typeerror("super expression must either be null or a function, not " + typeof superclass); } subclass.prototype = object.create(superclass && superclass.prototype, { constructor: { value: subclass, enumerable: false, writable: true, configurable: true } }); if (superclass) object.setprototypeof ? object.setprototypeof(subclass, superclass) : subclass.__proto__ = superclass; } /** * base class which takes one or more elements, adds event listeners to them, * and instantiates a new `clipboardaction` on each click. */ var clipboard = function (_emitter) { _inherits(clipboard, _emitter); /** * @param {string|htmlelement|htmlcollection|nodelist} trigger * @param {object} options */ function clipboard(trigger, options) { _classcallcheck(this, clipboard); var _this = _possibleconstructorreturn(this, (clipboard.__proto__ || object.getprototypeof(clipboard)).call(this)); _this.resolveoptions(options); _this.listenclick(trigger); return _this; } /** * defines if attributes would be resolved using internal setter functions * or custom functions that were passed in the constructor. * @param {object} options */ _createclass(clipboard, [{ key: 'resolveoptions', value: function resolveoptions() { var options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; this.action = typeof options.action === 'function' ? options.action : this.defaultaction; this.target = typeof options.target === 'function' ? options.target : this.defaulttarget; this.text = typeof options.text === 'function' ? options.text : this.defaulttext; this.container = _typeof(options.container) === 'object' ? options.container : document.body; } /** * adds a click event listener to the passed trigger. * @param {string|htmlelement|htmlcollection|nodelist} trigger */ }, { key: 'listenclick', value: function listenclick(trigger) { var _this2 = this; this.listener = (0, _goodlistener2.default)(trigger, 'click', function (e) { return _this2.onclick(e); }); } /** * defines a new `clipboardaction` on each click event. * @param {event} e */ }, { key: 'onclick', value: function onclick(e) { var trigger = e.delegatetarget || e.currenttarget; if (this.clipboardaction) { this.clipboardaction = null; } this.clipboardaction = new _clipboardaction2.default({ action: this.action(trigger), target: this.target(trigger), text: this.text(trigger), container: this.container, trigger: trigger, emitter: this }); } /** * default `action` lookup function. * @param {element} trigger */ }, { key: 'defaultaction', value: function defaultaction(trigger) { return getattributevalue('action', trigger); } /** * default `target` lookup function. * @param {element} trigger */ }, { key: 'defaulttarget', value: function defaulttarget(trigger) { var selector = getattributevalue('target', trigger); if (selector) { return document.queryselector(selector); } } /** * returns the support of the given action, or all actions if no action is * given. * @param {string} [action] */ }, { key: 'defaulttext', /** * default `text` lookup function. * @param {element} trigger */ value: function defaulttext(trigger) { return getattributevalue('text', trigger); } /** * destroy lifecycle. */ }, { key: 'destroy', value: function destroy() { this.listener.destroy(); if (this.clipboardaction) { this.clipboardaction.destroy(); this.clipboardaction = null; } } }], [{ key: 'issupported', value: function issupported() { var action = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : ['copy', 'cut']; var actions = typeof action === 'string' ? [action] : action; var support = !!document.querycommandsupported; actions.foreach(function (action) { support = support && !!document.querycommandsupported(action); }); return support; } }]); return clipboard; }(_tinyemitter2.default); /** * helper function to retrieve attribute value. * @param {string} suffix * @param {element} element */ function getattributevalue(suffix, element) { var attribute = 'data-clipboard-' + suffix; if (!element.hasattribute(attribute)) { return; } return element.getattribute(attribute); } module.exports = clipboard; /***/ }), /* 1 */ /***/ (function(module, exports, __webpack_require__) { "use strict"; var _typeof = typeof symbol === "function" && typeof symbol.iterator === "symbol" ? function (obj) { return typeof obj; } : function (obj) { return obj && typeof symbol === "function" && obj.constructor === symbol && obj !== symbol.prototype ? "symbol" : typeof obj; }; var _createclass = function () { function defineproperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; object.defineproperty(target, descriptor.key, descriptor); } } return function (constructor, protoprops, staticprops) { if (protoprops) defineproperties(constructor.prototype, protoprops); if (staticprops) defineproperties(constructor, staticprops); return constructor; }; }(); var _select = __webpack_require__(2); var _select2 = _interoprequiredefault(_select); function _interoprequiredefault(obj) { return obj && obj.__esmodule ? obj : { default: obj }; } function _classcallcheck(instance, constructor) { if (!(instance instanceof constructor)) { throw new typeerror("cannot call a class as a function"); } } /** * inner class which performs selection from either `text` or `target` * properties and then executes copy or cut operations. */ var clipboardaction = function () { /** * @param {object} options */ function clipboardaction(options) { _classcallcheck(this, clipboardaction); this.resolveoptions(options); this.initselection(); } /** * defines base properties passed from constructor. * @param {object} options */ _createclass(clipboardaction, [{ key: 'resolveoptions', value: function resolveoptions() { var options = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; this.action = options.action; this.container = options.container; 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. */ }, { key: 'initselection', value: function initselection() { if (this.text) { this.selectfake(); } else if (this.target) { this.selecttarget(); } } /** * creates a fake textarea element, sets its value from `text` property, * and makes a selection on it. */ }, { key: 'selectfake', value: function selectfake() { var _this = this; var isrtl = document.documentelement.getattribute('dir') == 'rtl'; this.removefake(); this.fakehandlercallback = function () { return _this.removefake(); }; this.fakehandler = this.container.addeventlistener('click', this.fakehandlercallback) || true; this.fakeelem = document.createelement('textarea'); // prevent zooming on ios this.fakeelem.style.fontsize = '12pt'; // reset box model this.fakeelem.style.border = '0'; this.fakeelem.style.padding = '0'; this.fakeelem.style.margin = '0'; // move element out of screen horizontally this.fakeelem.style.position = 'absolute'; this.fakeelem.style[isrtl ? 'right' : 'left'] = '-9999px'; // move element to the same position vertically var yposition = window.pageyoffset || document.documentelement.scrolltop; this.fakeelem.style.top = yposition + 'px'; this.fakeelem.setattribute('readonly', ''); this.fakeelem.value = this.text; this.container.appendchild(this.fakeelem); this.selectedtext = (0, _select2.default)(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. */ }, { key: 'removefake', value: function removefake() { if (this.fakehandler) { this.container.removeeventlistener('click', this.fakehandlercallback); this.fakehandler = null; this.fakehandlercallback = null; } if (this.fakeelem) { this.container.removechild(this.fakeelem); this.fakeelem = null; } } /** * selects the content from element passed on `target` property. */ }, { key: 'selecttarget', value: function selecttarget() { this.selectedtext = (0, _select2.default)(this.target); this.copytext(); } /** * executes the copy operation based on the current selection. */ }, { key: 'copytext', value: function copytext() { var succeeded = void 0; 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 */ }, { key: 'handleresult', value: function handleresult(succeeded) { this.emitter.emit(succeeded ? 'success' : 'error', { action: this.action, text: this.selectedtext, trigger: this.trigger, clearselection: this.clearselection.bind(this) }); } /** * moves focus away from `target` and back to the trigger, removes current selection. */ }, { key: 'clearselection', value: function clearselection() { if (this.trigger) { this.trigger.focus(); } window.getselection().removeallranges(); } /** * sets the `action` to be performed which can be either 'copy' or 'cut'. * @param {string} action */ }, { key: 'destroy', /** * destroy lifecycle. */ value: function destroy() { this.removefake(); } }, { key: 'action', set: function set() { var action = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : '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: function get() { return this._action; } /** * sets the `target` property using an element * that will be have its content copied. * @param {element} target */ }, { key: 'target', set: function set(target) { if (target !== undefined) { if (target && (typeof target === 'undefined' ? 'undefined' : _typeof(target)) === 'object' && target.nodetype === 1) { if (this.action === 'copy' && target.hasattribute('disabled')) { throw new error('invalid "target" attribute. please use "readonly" instead of "disabled" attribute'); } if (this.action === 'cut' && (target.hasattribute('readonly') || target.hasattribute('disabled'))) { throw new error('invalid "target" attribute. you can\'t cut text from elements with "readonly" or "disabled" attributes'); } this._target = target; } else { throw new error('invalid "target" value, use a valid element'); } } } /** * gets the `target` property. * @return {string|htmlelement} */ , get: function get() { return this._target; } }]); return clipboardaction; }(); module.exports = clipboardaction; /***/ }), /* 2 */ /***/ (function(module, exports) { function select(element) { var selectedtext; if (element.nodename === 'select') { element.focus(); selectedtext = element.value; } else if (element.nodename === 'input' || element.nodename === 'textarea') { var isreadonly = element.hasattribute('readonly'); if (!isreadonly) { element.setattribute('readonly', ''); } element.select(); element.setselectionrange(0, element.value.length); if (!isreadonly) { element.removeattribute('readonly'); } selectedtext = element.value; } else { if (element.hasattribute('contenteditable')) { element.focus(); } var selection = window.getselection(); var range = document.createrange(); range.selectnodecontents(element); selection.removeallranges(); selection.addrange(range); selectedtext = selection.tostring(); } return selectedtext; } module.exports = select; /***/ }), /* 3 */ /***/ (function(module, exports) { function e () { // keep this empty so it's easier to inherit from // (via https://github.com/lipsmack from https://github.com/scottcorgan/tiny-emitter/issues/3) } e.prototype = { on: function (name, callback, ctx) { var e = this.e || (this.e = {}); (e[name] || (e[name] = [])).push({ fn: callback, ctx: ctx }); return this; }, once: function (name, callback, ctx) { var self = this; function listener () { self.off(name, listener); callback.apply(ctx, arguments); }; listener._ = callback return this.on(name, listener, ctx); }, emit: function (name) { var data = [].slice.call(arguments, 1); var evtarr = ((this.e || (this.e = {}))[name] || []).slice(); var i = 0; var len = evtarr.length; for (i; i < len; i++) { evtarr[i].fn.apply(evtarr[i].ctx, data); } return this; }, off: function (name, callback) { var e = this.e || (this.e = {}); var evts = e[name]; var liveevents = []; if (evts && callback) { for (var i = 0, len = evts.length; i < len; i++) { if (evts[i].fn !== callback && evts[i].fn._ !== callback) liveevents.push(evts[i]); } } // remove event from queue to prevent memory leak // suggested by https://github.com/lazd // ref: https://github.com/scottcorgan/tiny-emitter/commit/c6ebfaa9bc973b33d110a84a307742b7cf94c953#commitcomment-5024910 (liveevents.length) ? e[name] = liveevents : delete e[name]; return this; } }; module.exports = e; /***/ }), /* 4 */ /***/ (function(module, exports, __webpack_require__) { var is = __webpack_require__(5); var delegate = __webpack_require__(6); /** * validates all params and calls the right * listener function based on its target type. * * @param {string|htmlelement|htmlcollection|nodelist} target * @param {string} type * @param {function} callback * @return {object} */ function listen(target, type, callback) { if (!target && !type && !callback) { throw new error('missing required arguments'); } if (!is.string(type)) { throw new typeerror('second argument must be a string'); } if (!is.fn(callback)) { throw new typeerror('third argument must be a function'); } if (is.node(target)) { return listennode(target, type, callback); } else if (is.nodelist(target)) { return listennodelist(target, type, callback); } else if (is.string(target)) { return listenselector(target, type, callback); } else { throw new typeerror('first argument must be a string, htmlelement, htmlcollection, or nodelist'); } } /** * adds an event listener to a html element * and returns a remove listener function. * * @param {htmlelement} node * @param {string} type * @param {function} callback * @return {object} */ function listennode(node, type, callback) { node.addeventlistener(type, callback); return { destroy: function() { node.removeeventlistener(type, callback); } } } /** * add an event listener to a list of html elements * and returns a remove listener function. * * @param {nodelist|htmlcollection} nodelist * @param {string} type * @param {function} callback * @return {object} */ function listennodelist(nodelist, type, callback) { array.prototype.foreach.call(nodelist, function(node) { node.addeventlistener(type, callback); }); return { destroy: function() { array.prototype.foreach.call(nodelist, function(node) { node.removeeventlistener(type, callback); }); } } } /** * add an event listener to a selector * and returns a remove listener function. * * @param {string} selector * @param {string} type * @param {function} callback * @return {object} */ function listenselector(selector, type, callback) { return delegate(document.body, selector, type, callback); } module.exports = listen; /***/ }), /* 5 */ /***/ (function(module, exports) { /** * check if argument is a html element. * * @param {object} value * @return {boolean} */ exports.node = function(value) { return value !== undefined && value instanceof htmlelement && value.nodetype === 1; }; /** * check if argument is a list of html elements. * * @param {object} value * @return {boolean} */ exports.nodelist = function(value) { var type = object.prototype.tostring.call(value); return value !== undefined && (type === '[object nodelist]' || type === '[object htmlcollection]') && ('length' in value) && (value.length === 0 || exports.node(value[0])); }; /** * check if argument is a string. * * @param {object} value * @return {boolean} */ exports.string = function(value) { return typeof value === 'string' || value instanceof string; }; /** * check if argument is a function. * * @param {object} value * @return {boolean} */ exports.fn = function(value) { var type = object.prototype.tostring.call(value); return type === '[object function]'; }; /***/ }), /* 6 */ /***/ (function(module, exports, __webpack_require__) { var closest = __webpack_require__(7); /** * delegates event to a selector. * * @param {element} element * @param {string} selector * @param {string} type * @param {function} callback * @param {boolean} usecapture * @return {object} */ function _delegate(element, selector, type, callback, usecapture) { var listenerfn = listener.apply(this, arguments); element.addeventlistener(type, listenerfn, usecapture); return { destroy: function() { element.removeeventlistener(type, listenerfn, usecapture); } } } /** * delegates event to a selector. * * @param {element|string|array} [elements] * @param {string} selector * @param {string} type * @param {function} callback * @param {boolean} usecapture * @return {object} */ function delegate(elements, selector, type, callback, usecapture) { // handle the regular element usage if (typeof elements.addeventlistener === 'function') { return _delegate.apply(null, arguments); } // handle element-less usage, it defaults to global delegation if (typeof type === 'function') { // use `document` as the first parameter, then apply arguments // this is a short way to .unshift `arguments` without running into deoptimizations return _delegate.bind(null, document).apply(null, arguments); } // handle selector-based usage if (typeof elements === 'string') { elements = document.queryselectorall(elements); } // handle array-like based usage return array.prototype.map.call(elements, function (element) { return _delegate(element, selector, type, callback, usecapture); }); } /** * finds closest match and invokes callback. * * @param {element} element * @param {string} selector * @param {string} type * @param {function} callback * @return {function} */ function listener(element, selector, type, callback) { return function(e) { e.delegatetarget = closest(e.target, selector); if (e.delegatetarget) { callback.call(element, e); } } } module.exports = delegate; /***/ }), /* 7 */ /***/ (function(module, exports) { var document_node_type = 9; /** * a polyfill for element.matches() */ if (typeof element !== 'undefined' && !element.prototype.matches) { var proto = element.prototype; proto.matches = proto.matchesselector || proto.mozmatchesselector || proto.msmatchesselector || proto.omatchesselector || proto.webkitmatchesselector; } /** * finds the closest parent that matches a selector. * * @param {element} element * @param {string} selector * @return {function} */ function closest (element, selector) { while (element && element.nodetype !== document_node_type) { if (typeof element.matches === 'function' && element.matches(selector)) { return element; } element = element.parentnode; } } module.exports = closest; /***/ }) /******/ ]); });