优雅的 alert()

把警示窗改为显示在页面右上角,显示几秒后会自动关闭。以滑鼠点按窗口会立即关闭,并把内容复制到系统剪贴簿。

目前为 2020-01-20 提交的版本。查看 最新版本

// ==UserScript==
// @name         elegant alert()
// @name:zh-TW   優雅的 alert()
// @name:zh-CN   优雅的 alert()
// @description:en     Customized alert box at the top right corner, auto close in a few seconds. Click on the alert box will close it immediately and copy the alert message to clipboard.
// @description:zh-TW  把警示窗改為顯示在頁面右上角,顯示幾秒後會自動關閉。以滑鼠點按窗口會立即關閉,並把內容複製到系統剪貼簿。
// @description:zh-CN  把警示窗改为显示在页面右上角,显示几秒后会自动关闭。以滑鼠点按窗口会立即关闭,并把内容复制到系统剪贴簿。
// @namespace    https://greasyfork.org/zh-TW/users/393133-evan-tseng
// @author       Evan Tseng
// @version      1.02
// @match        */*
// @run-at       document-start
// @grant        none
// @description Customized alert box at the top right corner, auto close in a few seconds. Click on the alert box will close it immediately and copy the alert message to clipboard.
// ==/UserScript==

(async function() {
	'use strict';

	const boxFont = '400 14pt Helvetica',
		  boxFontColor = '#000',
		  boxColor = 'rgba(240,240,210,.85)',
		  boxHoverColor = 'rgba(255,255,230,.85)',
		  popBgColor = '#F00',
		  countdownColor1 = 'rgba(0,0,255,.1)',
		  countdownColor2 = 'rgba(0,0,255,.1)',
		  duration = 6000;

	var alertWrap = null;
	const ElegantAlertBox = function(msg){
		this.exist = true;
		this.createBox = function(text){
			var box = this,
				alBox = document.createElement('div');
			alBox.innerHTML = text + '<div class="bar"></div>';
			alBox.onclick = function(){
				window.Clipboard.copy(text);
				box.close();
			};
			return alBox;
		};
		this.show = function(){
			var box = this;
			setTimeout(function(){
				box.elm.setAttribute("class", "normal");
				setTimeout(function(){
					if(box.exist)	box.close();
				}, duration);
			},60);
		};
		this.close = function(){
			var box = this;
			box.elm.setAttribute("class", "close");
			setTimeout(function(){
				if(box.exist) {
					alertWrap.removeChild(box.elm);
					box.exist = false;
				}
			}, 1000);
		};
		this.elm = this.createBox(msg);
		alertWrap.appendChild(this.elm);
		this.show();
		return this.elm;
	};

	window.Clipboard = (function(window, document, navigator) {
		var textArea, copy;
		function isOS() {
			return navigator.userAgent.match(/ipad|iphone/i);
		}
		function createTextArea(text) {
			textArea = document.createElement('textArea');
			textArea.value = text;
			document.body.appendChild(textArea);
		}
		function selectText() {
			var range,
				selection;
			if (isOS()) {
				range = document.createRange();
				range.selectNodeContents(textArea);
				selection = window.getSelection();
				selection.removeAllRanges();
				selection.addRange(range);
				textArea.setSelectionRange(0, -1);
			} else {
				textArea.select();
			}
		}
		function copyToClipboard() {
			document.execCommand('copy');
			document.body.removeChild(textArea);
		}
		copy = function(text) {
			createTextArea(text);
			selectText();
			copyToClipboard();
		};
		return {
			copy: copy
		};
	})(window, document, navigator);

	window.alert = function(message){
		if(!alertWrap) {
			const css = '.elegantAlertBoxWrapper { position:fixed; top:8mm; right:10mm; max-width:40vw; text-align:right; z-index:2147483647; -webkit-user-select:none; user-select:none }'+
				  '.elegantAlertBoxWrapper>div { position:relative; font:'+ boxFont +'; line-height:1.4; color:'+ boxFontColor +'; background:'+ popBgColor +'; max-height:0; overflow:hidden; padding:2px 2mm; margin-bottom:1.5mm; border-radius:5px; opacity:0; cursor:pointer; box-shadow:inset 0 0 0 1px rgba(255,255,255,.8), 0 1px 2mm rgba(0,0,0,.7); backdrop-filter:blur(2px); -webkit-backdrop-filter:blur(2px); }'+
				  '.elegantAlertBoxWrapper>div>.bar { position: absolute; left:0; bottom:0; width:100%; height:100%; background:'+countdownColor1+' }'+
				  '.elegantAlertBoxWrapper>.normal { background:'+ boxColor +'; opacity:1; max-height:4.4em; overflow:scroll; transition:max-height 0s, opacity 0s, background .2s 0s }'+
				  '.elegantAlertBoxWrapper>.normal>.bar, .elegantAlertBoxWrapper>.close>.bar { background: '+countdownColor2+'; width:0; transition:'+(duration-30)+'ms linear}'+
				  '.elegantAlertBoxWrapper>.close { background:'+ boxColor +'; opacity:0; max-height:0; padding:0 2mm; margin:0; transition:all .8s ease-in-out }'+
				  '.elegantAlertBoxWrapper>div:hover { background:'+ boxHoverColor +'; z-index:2; box-shadow:inset 0 0 0 1px rgba(255,255,255,.8), 0 1px 2mm rgba(0,0,0,.8); transition:all .1s }'+
				  '.elegantAlertBoxWrapper>div:active { box-shadow:0 0 0 1px #777, inset 0 1px 2px #555 }',
				  cssStyle = document.createElement('style');
			if(cssStyle.styleSheet)	cssStyle.styleSheet.cssText = css;
			else	cssStyle.appendChild(document.createTextNode(css));
			document.querySelector('head').appendChild(cssStyle);

			alertWrap = document.createElement('div');
			document.body.appendChild(alertWrap);
			alertWrap.setAttribute("class", "elegantAlertBoxWrapper");
		}
		var alertBox = new ElegantAlertBox(message);
	};

})();