Vue(基础三)_监听器与计算属性
一、前言
本文主要涉及: 1、watch()监听单个属性
二、主要内容
(1)监听简单的数据类型
new Vue({ el:'#app', data(){ return { msg:'' } }, watch:{ //第一个参数为新数据,第二个参数为老数据 msg:function(newV,oldV ){ console.log(newV,oldV) } } })
(2)对于复杂的数据类型(数组,对象)不能用上面的来监听
<body> <div id="app"> <input type="" name="" v-model='msg'> <h4>{{stu[0].name}}</h4> </div> <script type="text/javascript" src="node_modules/vue/dist/vue.js"></script> <script type="text/javascript"> new Vue({ el:'#app', data(){ return { msg:'', stu:[{ name: 'jack'}] } }, watch:{ //第一个参数为新数据,第二个参数为老数据 msg:function(newV,oldV){ console.log(newV,oldV) }, stu:{ deep:true, hander:function(newV, oldV){ console.log(newV[0].name) } } } }) </script> </body>
(1)计算属性:在computed中定义计算属性的方法,在页面中用{{方法名}}来使用计算属性
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>03_计算属性和监视</title> </head> <body> <div id="demo"> 姓:<input type="text" name="" placeholder="First Name" v-model="firstName"><br> 名:<input type="text" name="" placeholder="Last Name" v-model="lastName"><br> 姓名1:<input type="text" name="" placeholder="Last Name" v-model="fullName1"><br> </div> <script type="text/javascript" src="./vue.js"></script> <script> new Vue({ el:"#demo", data:{ firstName: 'A', lastName: 'B', //fullName1:'A B' }, computed:{ //fullName1的值是由前两个属性共同计算得到的 fullName1(){ return this.firstName +" "+this.lastName } } }) </script> </body> </html>
/*computed计算属性*/ computed:{ //fullName1的值是由前两个属性共同计算得到的 fullName1(){ return this.firstName +" "+this.lastName } },
实现效果(单向改变):
(2)监视属性:通过vm对象的$watch()方法或者watch配置来监听指定的属性,当属性变化时,回调函数自动调用,在函数内部进行计算
a:配置监视
//配置监视 watch:{ firstName:function(newvalue, oldvalue){ this.fullName1 = newvalue + " " + this.lastName } }
b:实例方法监视,vue实例中有一个$watch()方法来用于监听
//方法监视 vm.$watch('lastName',function(value){ this.fullName1 = this.firstName + value })
结合watch和$watch()也能实现同样的效果
(3)计算属性的高级
a : 通过计算属性get/set实现对属性数据 的显示和监视(双向监听),每个属性都有一个get()和set()方法,下面在computed中给fullName1属性设置set和get方法
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>03_计算属性和监视</title> </head> <body> <div id="demo"> 姓:<input type="text" name="" placeholder="First Name" v-model="firstName"><br> 名:<input type="text" name="" placeholder="Last Name" v-model="lastName"><br> 姓名1:<input type="text" name="" placeholder="Last Name" v-model="fullName1"><br> </div> <script type="text/javascript" src="./vue.js"></script> <script> const vm = new Vue({ el:"#demo", data:{ firstName: 'A', lastName: 'B' }, computed:{ fullName1:{ //当获取当前属性值的时候自动调用 get(){ return this.firstName + " " +this.lastName }, //当属性值发生改变的时候监听属性值变化, set(value){//value就是fullName1的最新属性值 const names = value.split(' ') this.firstName = names[0] this.lastName = names[1] } } } }) </script> </body> </html>
效果:
b:计算属性存在缓存,当多次调用getter的时候,只执行一次,当执行第一次的时候就将数据存在缓存里面。
下面用一个例子来简单说明
点击列表,切换播放的音乐(这个例子不用计算属性也可实现,用了稍微有点绕,这里只是用他来说明计算属性是如何监听多个属性的)
不用计算属性的代码:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Document</title> <style type="text/css"> *{ margin: 0; padding: 0; } ul li{ height: 100px; background-color: blue; padding: 20px; margin: 10px; border-radius: 5px; } ul li.active { background-color: yellow; } </style> </head> <body> <div id="app"> <div> <audio :src="musicList[this.currentIndex].musicSrc" controls autoplay></audio> <ul> <li v-for="(item, index) in musicList" v-on:click='changeMusic(index)'> <h4>{{item.music}}</h4> <h6>{{item.musicSrc}}</h6> <h1>{{index}}</h1> </li> </ul> </div> </div> <script type="text/javascript" src="node_modules/vue/dist/vue.js"></script> <script type="text/javascript"> var musicList = [ {id:0, music:'Jeol Adams - Please Dont GO.mp3',author:'Jeol', musicSrc:'./static/Joel Adams - Please Dont Go.mp3'}, {id:1, music:'MKJ - Time.mp3',author:'MKJ', musicSrc:'./static/MKJ - Time.mp3'}, {id:2, music:'Russ - Psycho (Pt. 2).mp3',author:'Russ', musicSrc:'./static/Russ - Psycho (Pt. 2).mp3'}, {id:3,music:'于荣光 - 少林英雄.mp3',author:'于荣光', musicSrc:'./static/于荣光 - 少林英雄.mp3'} ] var vm = new Vue({ el:"#app", data(){ return{ musicList:musicList, currentIndex:0 } }, methods:{ changeMusic: function(index){ console.log(index) return this.currentIndex=index; } } }) console.log(vm) </script> </body> </html>
使用计算属性实现音乐列表:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Document</title> <style type="text/css"> *{ margin: 0; padding: 0; } ul li{ height: 100px; background-color: blue; padding: 20px; margin: 10px; border-radius: 5px; } ul li.active { background-color: yellow; } </style> </head> <body> <div id="app"> <div> <audio :src="getCurrentSongSrc" controls autoplay></audio> <ul> <li v-for="(item, index) in musicList" @click="changeMusic(index)"> <h4>{{item.music}}</h4> <h6>{{item.musicSrc}}</h6> </li> </ul> </div> </div> <script type="text/javascript" src="node_modules/vue/dist/vue.js"></script> <script type="text/javascript"> var musicList = [ {music:'Jeol Adams - Please Dont GO.mp3',author:'Jeol', musicSrc:'./static/Joel Adams - Please Dont Go.mp3'}, {music:'MKJ - Time.mp3',author:'MKJ', musicSrc:'./static/MKJ - Time.mp3'}, {music:'Russ - Psycho (Pt. 2).mp3',author:'Russ', musicSrc:'./static/Russ - Psycho (Pt. 2).mp3'}, {music:'于荣光 - 少林英雄.mp3',author:'于荣光', musicSrc:'./static/于荣光 - 少林英雄.mp3'} ] new Vue({ el:"#app", data(){ return{ musicList:musicList, currentIndex:0 } }, template:'', computed:{ // musicList[this.currentIndex].musicSrc getCurrentSongSrc: function(){ return this.musicList[this.currentIndex].musicSrc; } }, methods:{ changeMusic(index){ this.currentIndex = index; } } }) </script> </body> </html>
具体实现:
三、总结
1、点击li标签获取当前li标签的索引:
<ul> <li v-for="(item, index) in musicList" @click="changeMusic(index)"> </li> </ul> methods:{ clickHandler(index){ this.currentIndex = index; } }