当涂 微网站开发公司,团购网站前景,湛江网上房地产,成都哪里可以做网站文章目录Vue常用特性表单基本操作表单修饰符自定义指令Vue.directive 注册全局指令Vue.directive 注册全局指令 带参数自定义指令局部指令计算属性 computed侦听器 watch过滤器过滤器中传递参数生命周期常用的 钩子函数数组变异方法替换数组动态数组响应式数据图书列表案例1、 …
文章目录Vue常用特性表单基本操作表单修饰符自定义指令Vue.directive 注册全局指令Vue.directive 注册全局指令 带参数自定义指令局部指令计算属性 computed侦听器 watch过滤器过滤器中传递参数生命周期常用的 钩子函数数组变异方法替换数组动态数组响应式数据图书列表案例1、 提供的静态数据2、 把提供好的数据渲染到页面上3、 添加图书4 修改图书-上5 修改图书-下6 删除图书常用特性应用场景1 过滤器2 自定义指令3 计算属性生命周期案例代码Vue常用特性 表单基本操作 获取单选框中的值 通过v-model !-- 1、 两个单选框需要同时通过v-model 双向绑定 一个值 2、 每一个单选框必须要有value属性 且value 值不能一样 3、 当某一个单选框选中的时候 v-model 会将当前的 value值 改变 data 中的 数据gender 的值就是选中的值我们只需要实时监控他的值就可以了--input typeradio idmale value1 v-modelgenderlabel formale男/labelinput typeradio idfemale value2 v-modelgenderlabel forfemale女/labelscriptnew Vue({data: {// 默认会让当前的 value 值为 2 的单选框选中gender: 2, },})/script获取复选框中的值 通过v-model和获取单选框中的值一样复选框 checkbox 这种的组合时 data 中的 hobby 我们要定义成数组 否则无法实现多选 !-- 1、 复选框需要同时通过v-model 双向绑定 一个值 2、 每一个复选框必须要有value属性 且value 值不能一样 3、 当某一个单选框选中的时候 v-model 会将当前的 value值 改变 data 中的 数据hobby 的值就是选中的值我们只需要实时监控他的值就可以了--divspan爱好/spaninput typecheckbox idball value1 v-modelhobbylabel forball篮球/labelinput typecheckbox idsing value2 v-modelhobbylabel forsing唱歌/labelinput typecheckbox idcode value3 v-modelhobbylabel forcode写代码/label/div
scriptnew Vue({data: {// 默认会让当前的 value 值为 2 和 3 的复选框选中hobby: [2, 3],},})
/script获取下拉框和文本框中的值 通过v-model divspan职业/span!--1、 需要给select 通过v-model 双向绑定 一个值 2、 每一个option 必须要有value属性 且value 值不能一样 3、 当某一个option选中的时候 v-model 会将当前的 value值 改变 data 中的 数据occupation 的值就是选中的值我们只需要实时监控他的值就可以了--!-- multiple 多选 --select v-modeloccupation multipleoption value0请选择职业.../optionoption value1教师/optionoption value2软件工程师/optionoption value3律师/option/select!-- textarea 是 一个双标签 不需要绑定value 属性的 --textarea v-modeldesc/textarea/div
scriptnew Vue({data: {// 默认会让当前的 value 值为 2 和 3 的下拉框选中occupation: [2, 3],desc: nihao},})
/script表单修饰符 .number 转换为数值 注意点当开始输入非数字的字符串时因为Vue无法将字符串转换成数值所以属性值将实时更新成相同的字符串。即使后面输入数字也将被视作字符串。 .trim 自动过滤用户输入的首尾空白字符 只能去掉首尾的 不能去除中间的空格 .lazy 将input事件切换成change事件 .lazy 修饰符延迟了同步更新属性值的时机。即将原本绑定在 input 事件的同步逻辑转变为绑定在 change 事件上 在失去焦点 或者 按下回车键时才更新 !-- 自动将用户的输入值转为数值类型 --
input v-model.numberage typenumber!--自动过滤用户输入的首尾空白字符 --
input v-model.trimmsg!-- 在“change”时而非“input”时更新 --
input v-model.lazymsg 自定义指令
内置指令不能满足我们特殊的需求Vue允许我们自定义指令
Vue.directive 注册全局指令
!-- 使用自定义的指令只需在对用的元素中加上v-的前缀形成类似于内部指令v-ifv-text的形式。
--
input typetext v-focus
script
// 注意点
// 1、 在自定义指令中 如果以驼峰命名的方式定义 如 Vue.directive(focusA,function(){})
// 2、 在HTML中使用的时候 只能通过 v-focus-a 来使用 // 注册一个全局自定义指令 v-focus
Vue.directive(focus, {// 当绑定元素插入到 DOM 中。 其中 el为dom元素inserted: function (el) {// 聚焦元素el.focus();}
});
new Vue({el:#app
});
/scriptVue.directive 注册全局指令 带参数 input typetext v-colormsgscript typetext/javascript/*自定义指令-带参数bind - 只调用一次在指令第一次绑定到元素上时候调用*/Vue.directive(color, {// bind声明周期, 只调用一次指令第一次绑定到元素时调用。在这里可以进行一次性的初始化设置// el 为当前自定义指令的DOM元素 // binding 为自定义的函数形参 通过自定义属性传递过来的值 存在 binding.value 里面bind: function(el, binding){// 根据指令的参数设置背景色// console.log(binding.value.color)el.style.backgroundColor binding.value.color;}});var vm new Vue({el: #app,data: {msg: {color: blue}}});/script自定义指令局部指令
局部指令需要定义在 directives 的选项 用法和全局用法一样局部指令只能在当前组件里面使用当全局指令和局部指令同名时以局部指令为准
input typetext v-colormsginput typetext v-focusscript typetext/javascript/*自定义指令-局部指令*/var vm new Vue({el: #app,data: {msg: {color: red}},//局部指令需要定义在 directives 的选项directives: {color: {bind: function(el, binding){el.style.backgroundColor binding.value.color;}},focus: {inserted: function(el) {el.focus();}}}});/script计算属性 computed
模板中放入太多的逻辑会让模板过重且难以维护 使用计算属性可以让模板更加的简洁计算属性是基于它们的响应式依赖进行缓存的computed比较适合对多个变量或者对象进行处理后返回一个结果值也就是数多个变量中的某一个值发生了变化则我们监控的这个值也就会发生变化 div idapp!-- 当多次调用 reverseString 的时候 只要里面的 num 值不改变 他会把第一次计算的结果直接返回直到data 中的num值改变 计算属性才会重新发生计算--div{{reverseString}}/divdiv{{reverseString}}/div!-- 调用methods中的方法的时候 他每次会重新调用 --div{{reverseMessage()}}/divdiv{{reverseMessage()}}/div/divscript typetext/javascript/*计算属性与方法的区别:计算属性是基于依赖进行缓存的而方法不缓存*/var vm new Vue({el: #app,data: {msg: Nihao,num: 100},methods: {reverseMessage: function(){console.log(methods)return this.msg.split().reverse().join();}},//computed 属性 定义 和 data 已经 methods 平级 computed: {// reverseString 这个是我们自己定义的名字 reverseString: function(){console.log(computed)var total 0;// 当data 中的 num 的值改变的时候 reverseString 会自动发生计算 for(var i0;ithis.num;i){total i;}// 这里一定要有return 否则 调用 reverseString 的 时候无法拿到结果 return total;}}});/script侦听器 watch 使用watch来响应数据的变化一般用于异步或者开销较大的操作watch 中的属性 一定是data 中 已经存在的数据当需要监听一个对象的改变时普通的watch方法无法监听到对象内部属性的改变只有data中的数据才能够监听到变化此时就需要deep属性对对象进行深度监听 div idappdivspan名/spanspaninput typetext v-modelfirstName/span/divdivspan姓/spanspaninput typetext v-modellastName/span/divdiv{{fullName}}/div/divscript typetext/javascript/*侦听器*/var vm new Vue({el: #app,data: {firstName: Jim,lastName: Green,// fullName: Jim Green},//watch 属性 定义 和 data 已经 methods 平级 watch: {// 注意 这里firstName 对应着data 中的 firstName // 当 firstName 值 改变的时候 会自动触发 watchfirstName: function(val) {this.fullName val this.lastName;},// 注意 这里 lastName 对应着data 中的 lastName lastName: function(val) {this.fullName this.firstName val;}}});/script过滤器 Vue.js允许自定义过滤器可被用于一些常见的文本格式化。过滤器可以用在两个地方双花括号插值和v-bind表达式。过滤器应该被添加在JavaScript表达式的尾部由“管道”符号指示支持级联操作过滤器不改变真正的data而只是改变渲染的结果并返回过滤后的版本全局注册时是filter没有s的。而局部过滤器是filters是有s的 div idappinput typetext v-modelmsg!-- upper 被定义为接收单个参数的过滤器函数表达式 msg 的值将作为参数传入到函数中 --div{{msg | upper}}/div!-- 支持级联操作upper 被定义为接收单个参数的过滤器函数表达式msg 的值将作为参数传入到函数中。然后继续调用同样被定义为接收单个参数的过滤器 lower 将upper 的结果传递到lower中--div{{msg | upper | lower}}/divdiv :abcmsg | upper测试数据/div/divscript typetext/javascript// lower 为全局过滤器 Vue.filter(lower, function(val) {return val.charAt(0).toLowerCase() val.slice(1);});var vm new Vue({el: #app,data: {msg: },//filters 属性 定义 和 data 已经 methods 平级 // 定义filters 中的过滤器为局部过滤器 filters: {// upper 自定义的过滤器名字 // upper 被定义为接收单个参数的过滤器函数表达式 msg 的值将作为参数传入到函数中upper: function(val) {// 过滤器中一定要有返回值 这样外界使用过滤器的时候才能拿到结果return val.charAt(0).toUpperCase() val.slice(1);}}});/script过滤器中传递参数 div idbox!--filterA 被定义为接收三个参数的过滤器函数。其中 message 的值作为第一个参数普通字符串 arg1 作为第二个参数表达式 arg2 的值作为第三个参数。--{{ message | filterA(arg1, arg2) }}/divscript// 在过滤器中 第一个参数 对应的是 管道符前面的数据 n 此时对应 message// 第2个参数 a 对应 实参 arg1 字符串// 第3个参数 b 对应 实参 arg2 字符串Vue.filter(filterA,function(n,a,b){if(n10){return na;}else{return nb;}});new Vue({el:#box,data:{message: 哈哈哈}})/script生命周期
事物从出生到死亡的过程Vue实例从创建 到销毁的过程 这些过程中会伴随着一些函数的自调用。我们称这些函数为钩子函数 常用的 钩子函数
beforeCreate在实例初始化之后数据观测和事件配置之前被调用 此时data 和 methods 以及页面的DOM结构都没有初始化 什么都做不了created在实例创建完成后被立即调用此时data 和 methods已经可以使用 但是页面还没有渲染出来beforeMount在挂载开始之前被调用 此时页面上还看不到真实数据 只是一个模板页面而已mountedel被新创建的vm.$el替换并挂载到实例上去之后调用该钩子。 数据已经真实渲染到页面上 在这个钩子函数里面我们可以使用一些第三方的插件beforeUpdate数据更新时调用发生在虚拟DOM打补丁之前。 页面上数据还是旧的updated由于数据更改导致的虚拟DOM重新渲染和打补丁在这之后会调用该钩子。 页面上数据已经替换成最新的beforeDestroy实例销毁之前调用destroyed实例销毁后调用
数组变异方法 在 Vue 中直接修改对象属性的值无法触发响应式。当你直接修改了对象属性的值你会发现只有数据改了但是页面内容并没有改变变异数组方法即保持数组方法原有功能不变的前提下对其进行功能拓展
push()往数组最后面添加一个元素成功返回当前数组的长度pop()删除数组的最后一个元素成功返回删除元素的值shift()删除数组的第一个元素成功返回删除元素的值unshift()往数组最前面添加一个元素成功返回当前数组的长度splice()有三个参数第一个是想要删除的元素的下标必选第二个是想要删除的个数必选第三个是删除 后想要在原位置替换的值sort()sort() 使数组按照字符编码默认从小到大排序,成功返回排序后的数组reverse()reverse() 将数组倒序成功返回倒序后的数组
替换数组
不会改变原始数组但总是返回一个新数组
filterfilter() 方法创建一个新的数组新数组中的元素是通过检查指定数组中符合条件的所有元素。concatconcat() 方法用于连接两个或多个数组。该方法不会改变现有的数组sliceslice() 方法可从已有的数组中返回选定的元素。该方法并不会修改数组而是返回一个子数组
动态数组响应式数据
Vue.set(a,b,c) 让 触发视图重新更新一遍数据动态起来a是要更改的数据 、 b是数据的第几项、 c是更改后的数据
图书列表案例 静态列表效果基于数据实现模板效果处理每行的操作按钮
1、 提供的静态数据
数据存放在vue 中 data 属性中 var vm new Vue({el: #app,data: {books: [{id: 1,name: 三国演义,date: },{id: 2,name: 水浒传,date: },{id: 3,name: 红楼梦,date: },{id: 4,name: 西游记,date: }]}}); var vm new Vue({el: #app,data: {books: [{id: 1,name: 三国演义,date: },{id: 2,name: 水浒传,date: },{id: 3,name: 红楼梦,date: },{id: 4,name: 西游记,date: }]}});2、 把提供好的数据渲染到页面上
利用 v-for循环 遍历 books 将每一项数据渲染到对应的数据中 tbodytr :keyitem.id v-foritem in books!-- 对应的id 渲染到页面上 --td{{item.id}}/td!-- 对应的name 渲染到页面上 --td{{item.name}}/tdtd{{item.date}}/tdtd!-- 阻止 a 标签的默认跳转 --a href click.prevent修改/aspan|/spana href click.prevent删除/a/td/tr
/tbody3、 添加图书 通过双向绑定获取到输入框中的输入内容给按钮添加点击事件把输入框中的数据存储到 data 中的 books 里面
divh1图书管理/h1div classbookdivlabel forid编号/label!-- 3.1、通过双向绑定获取到输入框中的输入的 id --input typetext idid v-modelidlabel forname名称/label!-- 3.2、通过双向绑定获取到输入框中的输入的 name --input typetext idname v-modelname!-- 3.3、给按钮添加点击事件 --button clickhandle提交/button/div/div
/divscript typetext/javascript/*图书管理-添加图书*/var vm new Vue({el: #app,data: {id: ,name: ,books: [{id: 1,name: 三国演义,date: },{id: 2,name: 水浒传,date: },{id: 3,name: 红楼梦,date: },{id: 4,name: 西游记,date: }]},methods: {handle: function(){// 3.4 定义一个新的对象book 存储 获取到输入框中 书 的id和名字 var book {};book.id this.id;book.name this.name;book.date ;// 3.5 把book 通过数组的变异方法 push 放到 books 里面this.books.push(book);//3.6 清空输入框this.id ;this.name ;}}});/script4 修改图书-上
点击修改按钮的时候 获取到要修改的书籍名单 4.1 给修改按钮添加点击事件 需要把当前的图书的id 传递过去 这样才知道需要修改的是哪一本书籍 把需要修改的书籍名单填充到表单里面 4.2 根据传递过来的id 查出books 中 对应书籍的详细信息4.3 把获取到的信息填充到表单 div idappdiv classgriddivh1图书管理/h1div classbookdivlabel forid编号/labelinput typetext idid v-modelid :disabledflaglabel forname名称/labelinput typetext idname v-modelnamebutton clickhandle提交/button/div/div/divtabletheadtrth编号/thth名称/thth时间/thth操作/th/tr/theadtbodytr :keyitem.id v-foritem in bookstd{{item.id}}/tdtd{{item.name}}/tdtd{{item.date}}/tdtd!--- 4.1 给修改按钮添加点击事件 需要把当前的图书的id 传递过去 这样才知道需要修改的是哪一本书籍--- a href click.preventtoEdit(item.id)修改/aspan|/spana href click.prevent删除/a/td/tr/tbody/table/div/divscript typetext/javascript/*图书管理-添加图书*/var vm new Vue({el: #app,data: {flag: false,id: ,name: ,books: [{id: 1,name: 三国演义,date: },{id: 2,name: 水浒传,date: },{id: 3,name: 红楼梦,date: },{id: 4,name: 西游记,date: }]},methods: {handle: function(){// 3.4 定义一个新的对象book 存储 获取到输入框中 书 的id和名字 var book {};book.id this.id;book.name this.name;book.date ;// 3.5 把book 通过数组的变异方法 push 放到 books 里面this.books.push(book);//3.6 清空输入框this.id ;this.name ;},toEdit: function(id){console.log(id)//4.2 根据传递过来的id 查出books 中 对应书籍的详细信息var book this.books.filter(function(item){return item.id id;});console.log(book)//4.3 把获取到的信息填充到表单// this.id 和 this.name 通过双向绑定 绑定到了表单中 一旦数据改变视图自动更新this.id book[0].id;this.name book[0].name;}}});/script5 修改图书-下
5.1 定义一个标识符 主要是控制 编辑状态下当前编辑书籍的id 不能被修改 即 处于编辑状态下 当前控制书籍编号的输入框禁用5.2 通过属性绑定给书籍编号的 绑定 disabled 的属性 flag 为 true 即为禁用5.3 flag 默认值为false 处于编辑状态 要把 flag 改为true 即当前表单为禁用5.4 复用添加方法 用户点击提交的时候依然执行 handle 中的逻辑如果 flag为true 即 表单处于不可输入状态 此时执行的用户编辑数据数据
div idappdiv classgriddivh1图书管理/h1div classbookdivlabel forid编号/label!-- 5.2 通过属性绑定 绑定 disabled 的属性 flag 为 true 即为禁用 --input typetext idid v-modelid :disabledflaglabel forname名称/labelinput typetext idname v-modelnamebutton clickhandle提交/button/div/div/divtabletheadtrth编号/thth名称/thth时间/thth操作/th/tr/theadtbodytr :keyitem.id v-foritem in bookstd{{item.id}}/tdtd{{item.name}}/tdtd{{item.date}}/tdtda href click.preventtoEdit(item.id)修改/aspan|/spana href click.prevent删除/a/td/tr/tbody/table/div/div
script typetext/javascript/*图书管理-添加图书*/var vm new Vue({el: #app,data: {// 5.1 定义一个标识符 主要是控制 编辑状态下当前编辑书籍的id 不能被修改 // 即 处于编辑状态下 当前控制书籍编号的输入框禁用 flag: false,id: ,name: ,},methods: {handle: function() {/*5.4 复用添加方法 用户点击提交的时候依然执行 handle 中的逻辑如果 flag为true 即 表单处于不可输入状态 此时执行的用户编辑数据数据 */ if (this.flag) {// 编辑图书// 5.5 根据当前的ID去更新数组中对应的数据 this.books.some((item) {if (item.id this.id) {// 箭头函数中 this 指向父级作用域的this item.name this.name;// 完成更新操作之后需要终止循环return true;}});// 5.6 编辑完数据后表单要处以可以输入的状态this.flag false;// 5.7 如果 flag为false 表单处于输入状态 此时执行的用户添加数据 } else { var book {};book.id this.id;book.name this.name;book.date ;this.books.push(book);// 清空表单this.id ;this.name ;}// 清空表单this.id ;this.name ;},toEdit: function(id) {/*5.3 flag 默认值为false 处于编辑状态 要把 flag 改为true 即当前表单为禁 用 */ this.flag true;console.log(id)var book this.books.filter(function(item) {return item.id id;});console.log(book)this.id book[0].id;this.name book[0].name;}}});/script6 删除图书 6.1 给删除按钮添加事件 把当前需要删除的书籍id 传递过来6.2 根据id从数组中查找元素的索引6.3 根据索引删除数组元素 tbodytr :keyitem.id v-foritem in bookstd{{item.id}}/tdtd{{item.name}}/tdtd{{item.date}}/tdtda href click.preventtoEdit(item.id)修改/aspan|/span!-- 6.1 给删除按钮添加事件 把当前需要删除的书籍id 传递过来 -- a href click.preventdeleteBook(item.id)删除/a/td/tr
/tbodyscript typetext/javascript/*图书管理-添加图书*/var vm new Vue({methods: {deleteBook: function(id){// 删除图书#// 6.2 根据id从数组中查找元素的索引// var index this.books.findIndex(function(item){// return item.id id;// });#// 6.3 根据索引删除数组元素// this.books.splice(index, 1);// -------------------------#// 方法二通过filter方法进行删除# 6.4 根据filter 方法 过滤出来id 不是要删除书籍的id # 因为 filter 是替换数组不会修改原始数据 所以需要 把 不是要删除书籍的id 赋值给 books this.books this.books.filter(function(item){return item.id ! id;});}}});/script常用特性应用场景 1 过滤器
Vue.filter 定义一个全局过滤器 tr :keyitem.id v-foritem in bookstd{{item.id}}/tdtd{{item.name}}/td!-- 1.3 调用过滤器 --td{{item.date | format(yyyy-MM-dd hh:mm:ss)}}/tdtda href click.preventtoEdit(item.id)修改/aspan|/spana href click.preventdeleteBook(item.id)删除/a/td
/trscript#1.1 Vue.filter 定义一个全局过滤器Vue.filter(format, function(value, arg) {function dateFormat(date, format) {if (typeof date string) {var mts date.match(/(\/Date\((\d)\)\/)/);if (mts mts.length 3) {date parseInt(mts[2]);}}date new Date(date);if (!date || date.toUTCString() Invalid Date) {return ;}var map {M: date.getMonth() 1, //月份 d: date.getDate(), //日 h: date.getHours(), //小时 m: date.getMinutes(), //分 s: date.getSeconds(), //秒 q: Math.floor((date.getMonth() 3) / 3), //季度 S: date.getMilliseconds() //毫秒 };format format.replace(/([yMdhmsqS])/g, function(all, t) {var v map[t];if (v ! undefined) {if (all.length 1) {v 0 v;v v.substr(v.length - 2);}return v;} else if (t y) {return (date.getFullYear() ).substr(4 - all.length);}return all;});return format;}return dateFormat(value, arg);})
#1.2 提供的数据 包含一个时间戳 为毫秒数[{id: 1,name: 三国演义,date: 2525609975000},{id: 2,name: 水浒传,date: 2525609975000},{id: 3,name: 红楼梦,date: 2525609975000},{id: 4,name: 西游记,date: 2525609975000}];
/script2 自定义指令
让表单自动获取焦点通过Vue.directive 自定义指定
!-- 2.2 通过v-自定义属性名 调用自定义指令 --
input typetext idid v-modelid :disabledflag v-focusscript# 2.1 通过Vue.directive 自定义指定Vue.directive(focus, {inserted: function (el) {el.focus();}});/script3 计算属性
通过计算属性计算图书的总数 图书的总数就是计算数组的长度 div classtotalspan图书总数/span!-- 3.2 在页面上 展示出来 --span{{total}}/span
/divscript typetext/javascript/*计算属性与方法的区别:计算属性是基于依赖进行缓存的而方法不缓存*/var vm new Vue({data: {flag: false,submitFlag: false,id: ,name: ,books: []},computed: {total: function(){// 3.1 计算图书的总数return this.books.length;}},});/script
生命周期
案例代码
!DOCTYPE html
html langenheadmeta charsetUTF-8titleDocument/titlestyle typetext/css.grid {margin: auto;width: 530px;text-align: center;}.grid table {border-top: 1px solid #C2D89A;width: 100%;border-collapse: collapse;}.grid th,td {padding: 10;border: 1px dashed #F3DCAB;height: 35px;line-height: 35px;}.grid th {background-color: #F3DCAB;}.grid .book {padding-bottom: 10px;padding-top: 5px;background-color: #F3DCAB;}.grid .total {height: 30px;line-height: 30px;background-color: #F3DCAB;border-top: 1px solid #C2D89A;}/style
/headbodydiv idappdiv classgriddivh1图书管理/h1div classbookdivlabel forid编号/labelinput typetext idid v-modelid :disabledflag v-focuslabel forname名称/labelinput typetext idname v-modelnamebutton clickhandle :disabledsubmitFlag提交/button/div/div/divdiv classtotalspan图书总数/spanspan{{total}}/span/divtabletheadtrth编号/thth名称/thth时间/thth操作/th/tr/theadtbodytr :keyitem.id v-foritem in bookstd{{item.id}}/tdtd{{item.name}}/tdtd{{item.date | format(yyyy-MM-dd hh:mm:ss)}}/tdtda href click.preventtoEdit(item.id)修改/aspan|/spana href click.preventdeleteBook(item.id)删除/a/td/tr/tbody/table/div/divscript typetext/javascript srcjs/vue.js/scriptscript typetext/javascript/*图书管理-添加图书*/Vue.directive(focus, {inserted: function (el) {el.focus();}});Vue.filter(format, function (value, arg) {function dateFormat(date, format) {if (typeof date string) {var mts date.match(/(\/Date\((\d)\)\/)/);if (mts mts.length 3) {date parseInt(mts[2]);}}date new Date(date);if (!date || date.toUTCString() Invalid Date) {return ;}var map {M: date.getMonth() 1, //月份 d: date.getDate(), //日 h: date.getHours(), //小时 m: date.getMinutes(), //分 s: date.getSeconds(), //秒 q: Math.floor((date.getMonth() 3) / 3), //季度 S: date.getMilliseconds() //毫秒 };format format.replace(/([yMdhmsqS])/g, function (all, t) {var v map[t];if (v ! undefined) {if (all.length 1) {v 0 v;v v.substr(v.length - 2);}return v;} else if (t y) {return (date.getFullYear() ).substr(4 - all.length);}return all;});return format;}return dateFormat(value, arg);})var vm new Vue({el: #app,data: {flag: false,submitFlag: false,id: ,name: ,books: []},methods: {handle: function () {if (this.flag) {// 编辑图书// 就是根据当前的ID去更新数组中对应的数据this.books.some((item) {if (item.id this.id) {item.name this.name;// 完成更新操作之后需要终止循环return true;}});this.flag false;} else {// 添加图书var book {};book.id this.id;book.name this.name;book.date 2525609975000;this.books.push(book);// 清空表单this.id ;this.name ;}// 清空表单this.id ;this.name ;},toEdit: function (id) {// 禁止修改IDthis.flag true;console.log(id)// 根据ID查询出要编辑的数据var book this.books.filter(function (item) {return item.id id;});console.log(book)// 把获取到的信息填充到表单this.id book[0].id;this.name book[0].name;},deleteBook: function (id) {// 删除图书// 根据id从数组中查找元素的索引// var index this.books.findIndex(function(item){// return item.id id;// });// 根据索引删除数组元素// this.books.splice(index, 1);// -------------------------// 方法二通过filter方法进行删除this.books this.books.filter(function (item) {return item.id ! id;});}},computed: {total: function () {// 计算图书的总数return this.books.length;}},watch: {name: function (val) {// 验证图书名称是否已经存在var flag this.books.some(function (item) {return item.name val;});if (flag) {// 图书名称存在this.submitFlag true;} else {// 图书名称不存在this.submitFlag false;}}},mounted: function () {// 该生命周期钩子函数被触发的时候模板已经可以使用// 一般此时用于获取后台数据然后把数据填充到模板var data [{id: 1,name: 三国演义,date: 2525609975000}, {id: 2,name: 水浒传,date: 2525609975000}, {id: 3,name: 红楼梦,date: 2525609975000}, {id: 4,name: 西游记,date: 2525609975000}];this.books data;}});/script
/body/html