仿vue实现邮件在线签名生成器

基于vue双向数据绑定的思想,实现一个在线邮件签名生成器。

直接上演示代码:

<!doctype html>

<html>

<head>

<meta charset="UTF-8">

<title>邮件签名在线生成器|轻轻简记</title>

<link rel="shortcut icon" href="http://www.qingqingjianji.com/favicon.ico" type="image/x-icon">

<link rel="stylesheet" type="text/css" href="https://cdn.bootcss.com/bootstrap/4.0.0/css/bootstrap.min.css">

<style type="text/css">

.copyright{

margin-top: 15px;

background: #fff;

font-size: 14px;

color: #666;

text-align: center;

padding-top: 14px;

padding-bottom: 28px;

border-top: 2px solid #e3e3e3;

box-shadow: 0 0 3px rgba(0,0,0,.03);

}

.form-group{

margin-bottom: 7px;

}

</style>

</head>

<body>

<div style="margin-top:20px;">

<div>

<div>

<form>

<div>

<div>

<label class="col-sm-3 control-label">姓名</label>

<div><input name="s1" id="username" type="text" v-model="name" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">英文名</label>

<div><input name="s2" type="text" v-model="englishName" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">公司名</label>

<div><input name="s3" type="text" v-model="company" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">部门</label>

<div><input name="s4" type="text" v-model="def" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">职位</label>

<div><input name="s5" type="text" v-model="position" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">电话</label>

<div><input name="s6" type="text" v-model="tel" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">传真</label>

<div><input name="s7" type="text" v-model="fax" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">手机</label>

<div><input name="s8" type="text" v-model="mob" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">地址</label>

<div><input name="s9" type="text" v-model="add" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">中文申明</label>

<div><input name="s9" type="text" v-model="zhshenmin" oninput=vue.bind(this);></div>

</div>

</div>

<div>

<div>

<label class="col-sm-3 control-label">英文申明</label>

<div><input name="s9" type="text" v-model="enshenmin" oninput=vue.bind(this);></div>

</div>

</div>

<button type="button" class="btn btn-block btn-info" onclick="ClickCopy('code')">拷贝</button>

</form>

</div>

<div>

<div id="app">

<div>

<div id="EffectBox">

<h3>实时预览</h3>

<div id="code">

<style type="text/css">

.g {clear:both; height:0;}

.mailsign {font-size:12px; color:#808080; margin:0 35px; line-height:22px;}

.logo {width:305px; height:35px; margin:20px 0 10px -15px;}

.name {font-weight:700; font-size:14px; float:left; color:#808080; height:30px; line-height:30px;}

.position {float:left; margin-left:8px; color:#808080; height:30px; line-height:30px;}

.company1 {clear:both; font-weight:700; font-size:14px; color:#808080;}

.company2 {clear:both; font-weight:700; font-size:14px; color:#808080; margin-bottom:10px;}

.add .zip { margin-left:5px; color:#a0a0a0; font-size:10px;}

.website a {color:#808080; text-decoration:none !important;}

.state{

color: #a0a0a0;

margin: 10px auto;

padding: 5px 0px;

border-top: 1px solid #CCC;

border-radius: 0;

}

.state h4 { margin:0;}

.state p {margin:0; font-size:7.5pt;}

.def{font-size: 13px;display: inline-block;padding-right: 8px;}

.username{

font-weight:700; font-size:14px; color:#808080;

}

</style>

<div>

<div><span class="def username">{{name}}</span><span>{{englishName}}</span></div>

<div><span>{{company}}</span></div>

<div><span>{{def}}</span><span>{{position}}</span></div>

<div>电话/Tel:<span>{{tel}}</span></div>

<div>传真/Fax:<span>{{fax}}</span></div>

<div>手机/Mob:<span>{{mob}}</span></div>

<div>地址/Add:<span>{{add}}</span></div>

<div>

<p>{{zhshenmin}}</p>

<p>{{enshenmin}}</p>

</div>

</div>

</div>

</div>

</div>

</div>

</div>

</div>

<div>

<div>

<div>

<div>

<p><a href="http://www.qingqingjianji.com/">首页</a></p>

<p>Copyright © 轻轻简记,All Rights Reserved</p>

</div>

</div>

</div>

</div>

</div>

<script type="text/javascript">

// Object.defineProperty(obj, prop, descriptor)可以在一个对象上定义新属性或修改现有属性

// obj指要修改的对象

// prop新增或修改属性

// descriptor属性的描述

// 对象的属性主要分为两种,一种是数值型的,一种是访问型的。

// 如果一个描述符不具有value,writable,get 和 set 任意一个关键字,那么它将被认为是一个数据描述符

// 如果有value和writable就是数据型

// descriptor描述对象主要包含:

// configurable(表示对象的属性是否可以被删除,以及除writable特性外的其他特性是否可以被修改。)

// enumerable(定义了对象的属性是否可以forinobj或Object.keys)

// value

// writable(定义属性值是否可写,即是否可修改)

// get

// set

function Vue(obj){

this.$el = document.getElementById(obj.el);

this.options = obj;

//创建原型为null的空对象,和直接赋值一个{}有差异,直接赋值{}它是有原型的,即原型是对象

this.tempData = Object.create(null);

var flag = this.initCheck();

if(flag)

this.init();

}

Vue.prototype = {

init:function(){

var self = this;

self.template();

self.watch();

},

initCheck:function(){

var self = this;

if(!self.$el && window.console){

console.log("····没有定义模板ID····");

return false;

}

if(!self.options.data && window.console){

console.log("····没有定义数据对象····");

return false;

}

return true;

},

template:function(){

this.template = this.$el.innerHTML;

},

watch:function(){

var self = this;

var data = self.options.data;

//获取参数data对象的所有属性名

var dataKeys = Object.keys(data);

if(dataKeys && dataKeys.length > 0){

dataKeys.forEach(function(item){

if(self.hasOwnProperty(item)) return;

Object.defineProperty(self,item,{

configurable:true,

enumerable:true,

get:function(){

return self.tempData[item];

},

set:function(newVal){

if(newVal !== self.tempData[item]){

self.tempData[item] = newVal;

self.updateTemplate();

}

}

})

//定义属性后把把实例化data上的值赋值给属性

self[item] = data[item];

});

}

},

updateTemplate:function(){

var self = this;

var reg = /{{(.+?)}}/g;

self.el.innerHTML = self.template.replace(reg,function(str,1){

return self[$1] || "";

});

},

bind:function(node){

var self = this;

if(!node) return;

var nodeName = node.getAttribute('v-model');

var val;

if(node.tagName === "SELECT"){

val = node.options[node.selectedIndex].text;

}else{

val = node.value;

}

self[nodeName] = val;

}

}

</script>

<script type="text/javascript">

var vue = new Vue({

el:'app',

data:{

name:'姓名',

englishName:'英文名',

company:'某某股份有限公司',

position:'职位',

def:'部门',

add:'--',

tel:'--',

fax:'--',

mob:'--',

zhshenmin:'本邮件载有秘密信息,请您恪守保密义务;未经授权者不得复印、公开、使用本邮件及内容!谢谢合作!',

enshenmin:'This email communication is confidential,Recipient(s) named above is (are) obligated to maintain secrecy. Any unauthorized dissemination, distribution or copying of this communication is (are) strictly prohibited. Thank you.'

}

});

//点击复制,动态创建一个文本框,然后选择文本框的值,然后执行浏览器的复制命令

function ClickCopy(obj){

 if(!obj) return;

 var username = document.getElementById('username').value.trim();

 if(!username){

 alert("请输入你的姓名");

 return false;

 }

 var tempTextarea = document.createElement('textarea');

 tempTextarea.id = "htm";

 tempTextarea.value = document.getElementById(obj).innerHTML;

 document.body.appendChild(tempTextarea);

 document.getElementById("htm").select();

 setTimeout(function(){

 document.body.removeChild(document.getElementById("htm"));

 },0);

    var result=document.execCommand("Copy"); //执行浏览器复制命令

    if(result){

     alert("复制成功,去邮件签名输入框粘贴"); 

    }else{

     alert("当前浏览器不支持该功能,请切换浏览器!");

    }

}

</script>

</body>

</html>

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,948评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,371评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,490评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,521评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,627评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,842评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,997评论 3 408
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,741评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,203评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,534评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,673评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,339评论 4 330
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,955评论 3 313
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,770评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,000评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,394评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,562评论 2 349

推荐阅读更多精彩内容

  • 1. tab列表折叠效果 html: 能源系统事业部 岗位名称: 工作地点 岗位名...
    lilyping阅读 1,843评论 0 1
  • 在学习weex的过程中看到了常用标签相关的内容,为了自己以后能够快速查阅特整理出此文档。 a 简介组件定义了指向某...
    TyroneTang阅读 4,652评论 1 3
  • 尝试和大家一起探讨以下问题: view绘制渲染机制和runloop什么关系? 所谓的列表卡顿,到底是什么原因引发的...
    朽木自雕也阅读 3,024评论 4 9
  • HTML 5 HTML5概述 因特网上的信息是以网页的形式展示给用户的,因此网页是网络信息传递的载体。网页文件是用...
    阿啊阿吖丁阅读 3,872评论 0 0
  • 有效性 安全性 可及性 经济性 依从性可塑性助推性
    秦健勇阅读 572评论 0 0