1、条件渲染
1.1、v-if和v-show
1、使用官网的话来说:
v-if
是“真正”的条件渲染,因为它会确保在切换过程中条件块内的事件监听器和子组件适当地被销毁和重建。
v-if
也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
相比之下,v-show
就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
一般来说,v-if
有更高的切换开销,而 v-show
有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用 v-show
较好;如果在运行时条件很少改变,则使用 v-if
较好。
2、就是说v-if对应的值为true,在DOM上这个元素就真实存在了,而v-if对应的值为false,这个元素就镇的被从DOM中撤销和删除了。而v-show对应的值不管是true还是false,这个元素始终在DOM中真实存在,只不过使用display这个CSS属性来切换出现和隐藏,来满足v-show对应的true和false的值。
3、很明显,v-show的性能更高一些,不会去频繁的操作DOM
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>条件渲染</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="vm">
<button @click="handleBtnSwitch">switch</button>
<div v-if="show">hello world</div>
<div v-show="show">hello world</div>
</div>
<script>
var vm = new Vue({
el: '#vm',
data: {
show: false,
},
methods: {
handleBtnSwitch: function() {
this.show = !this.show;
}
}
})
</script>
</body>
</html>
1.2、v-if和v-else
1、v-if和v-else要紧贴着一起使用,不然不起作用。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>条件渲染</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="vm">
<button @click="handleBtnSwitch">switch</button>
<div v-if="show === 'a'">hello world</div><!--v-if,v-else-if,v-else都要紧贴一起使用-->
<div v-else-if="show === 'b'">hello Vue</div>
<div v-else-if="show === 'c'">hello JS</div>
<div v-else>Bye Bye</div>
</div>
<script>
var vm = new Vue({
el: '#vm',
data: {
show: "a",
},
methods: {
handleBtnSwitch: function() {
this.show = this.show === 'a'?'b':this.show === 'b'?'c':this.show === 'c'?'':this.show ===''? 'a':'';
}
}
})
</script>
</body>
</html>
1.3、key值的应用
1、Vue 会尽可能高效地渲染元素,通常会复用已有元素而不是从头开始渲染,所以我们下面的例子中我们在输入框中输入值后,去改变show的值,你会发现输入框中的东西没有清空,所以我们需要给input来添加key值,表示input框是唯一独特的,上一个input和下一个input不能复用。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>key</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="app">
<div v-if="show">
用户名:<input type="" key="username">
</div>
<div v-else>
邮箱:<input type="text " key="mail">
</div>
<button @click="submit">submit</button>
</div>
<script>
var app = new Vue({
el: "#app",
data: {
show: false,
},
methods: {
submit: function() {
this.show = true;
}
}
})
</script>
</body>
</html>
2、列表渲染(数组的循环和元素修改,对象的循环和元素修改)
2.1、数组的更新检测
1、关于列表渲染比较重要的一点就是要使用key值,使用key值来表明数据的唯一性,在diff算法中能够极大的提高渲染性能,这个特殊的属性相当于 Vue 1.x 的 track-by
,但它的工作方式类似于一个属性,所以你需要用 v-bind
来绑定动态值。所以循环中的key是需要加冒号的。
2、因为我们从数据库拿到数据,一般都有一个数据库中数据唯一标识id值,我们一般拿这个作为key。
3、我们修改列表不能通过下标的形式去改变列表中的数据,只能通过Vue提供的几个(1)变异方法去改变数组中的数据,或者通过(2)非变异的方式,或者通过(3)set方法。如下所示
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>list渲染</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="app">
<div v-for="(item,index) in list"
:key="item.id"
>{{item.text}}----{{index}}</div>
<button @click="Btnsplice">使用方法改变原引用中的数据</button>
<button @click="BtnChangeObj">改变变量的引用来改变数据</button>
<button @click="BtnUserVueSet">Vue.set</button>
<button @click="BtnUserEmpleSet">实例.set</button>
</div>
<script>
//pop:删除数组的最后一项
//push:往数组中增加一条
//shift:删除数组中的第一项
//unshift:往数组的第一项中加点内容
//splice:数组的截取
//sort:数组进行排序
//reverse:数组取反
var list2=[{id:"020151501",text:"hello",},
{id:"020151502",text:"Vue2",},
{id:"020151503",text:"JS",},];
var app = new Vue({
el: '#app',
data: {
list:[
{id:"020151501",text:"hello",},
{id:"020151502",text:"Vue",},
{id:"020151503",text:"JS",},
]
},
methods: {
Btnsplice: function() {
//1、使用方法去改变数据:删除list中下标为1的元素,并在此处添加新的元素
this.list.splice(1,1,{id:"020151599",text:"Vue1"})
},
BtnChangeObj: function() {
//2.1、通过该变list的引用
this.list=list2;
//2.2、相比之下,也有非变异 (non-mutating method) 方法,例如:filter(), concat() 和 slice() 。这些不会改变原始数组,但总是返回一个新数组。当使用非变异方法时,可以用新数组替换旧数组:
example1.items = example1.items.filter(function (item) {
return item.message.match(/Foo/)
})
},
BtnUserVueSet: function() {
//3.1、通过使用Vue.set方法(修改下标为1的元素)
Vue.set(this.list,1,{id:"020151505",text:"subOnechanged"});
},
BtnUserEmpleSet: function() {
//3.2、通过使用实例.set方法(修改下标为2的元素)
this.$set(this.list,2,{id:"020151504",text:"subTwochanged"});
}
}
})
</script>
</body>
</html>
4、template占位符:帮助我们包裹一些元素,但是在渲染的时候并不会真的渲染出来。
<template v-for="(item,index) in list"
:key="item.id"
>
<div>
{{item.text}}-----{{index}}
</div>
<span>
{{item.text}}
</span>
</template>
2.2、显示过滤/排序结果
1、有时,我们想要显示一个数组的过滤或排序副本,而不实际改变或重置原始数据。在这种情况下,可以创建返回过滤或排序数组的计算属性。
<li v-for="n in evenNumbers">{{ n }}</li>
....
data: {
numbers: [ 1, 2, 3, 4, 5 ]
},
computed: {
evenNumbers: function () {
return this.numbers.filter(function (number) {
return number % 2 === 0
})
}
}
2、在计算属性不适用的情况下 (例如,在嵌套 v-for
循环中) 你可以使用一个 method 方法:
<li v-for="n in even(numbers)">{{ n }}</li>
....
data: {
numbers: [ 1, 2, 3, 4, 5 ]
},
methods: {
even: function (numbers) {
return numbers.filter(function (number) {
return number % 2 === 0
})
}
}
3、对象循环
1、我们再项目当中经常需要把对象中的所有属性循环展示出来,我们要这样做。
2、给对象添加或者删除属性,不能通过直接添加的方法,我们可以通过修改对象的引用,让引用指向一个新的对象:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>对象循环</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="app">
<!--使用item of 对象名的语法,和数组不一样的地方就是对象使用of,数组使用in-->
<!--item就是属性值,key就是属性名,index就是下标-->
<div v-for="(item,key,index) of userInfo">
{{index}}----{{key}}----{{item}}
</div>
<button @click="changeValue">直接修改对象中属性值</button>
<button @click="changObj">改变引用</button>
</div>
<script>
var app = new Vue({
el: "#app",
data: {
userInfo: {
name: "Dell",
age: 28,
gender: "male",
salary: "secret",
}
},
methods: {
//1、直接去修改属性值
changeValue: function() {
this.userInfo.name="taopoppy";
},
//2、通过改变引用,变向的给对象添加或者删除属性
changObj: function() {
this.userInfo={name: "Dell",age: 28,gender: "male",salary: "secret",address:"xinhuastreat"}
}
}
})
</script>
</body>
</html>
3、当然通过set方法也可以,set方法有两种,如下代码:
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>对象循环</title>
<script src="./vue.js"></script>
</head>
<body>
<div id="app">
<div v-for="(item,key,index) of userInfo">
{{index}}----{{key}}----{{item}}
</div>
<button @click="useVueSet">使用Vue.set</button>
<button @click="useEmpleSet">使用实例.set</button>
</div>
<script>
var app = new Vue({
el: "#app",
data: {
userInfo: {name: "Dell",age: 28,gender: "male",salary: "secret",}
},
methods: {
//使用set方法向对象添加属性
useVueSet: function() {
Vue.set(this.userInfo,"address","beijing");
},
//使用实例.$set方法向对象添加属性
useEmpleSet: function() {
this.$set(this.userInfo,"address","shanghai");
},
}
})
</script>
</body>
</html>
4、v-for的专题
1、一段范围取值的v-for
<!--v-for 也可以取整数。在这种情况下,它将重复多次模板。-->
<div>
<span v-for="n in 10">{{ n }} </span>
</div>
2、在template上面使用v-for
<ul>
<template v-for="item in items">
<li>{{ item.msg }}</li>
<li class="divider" role="presentation"></li>
</template>
</ul>
3、v-for与v-if
(1)当它们处于同一节点,v-for
的优先级比 v-if
更高,这意味着 v-if
将分别重复运行于每个 v-for
循环中。当你想为仅有的一些项渲染节点时,这种优先级的机制会十分有用,如下:
<li v-for="todo in todos" v-if="!todo.isComplete">
{{ todo }}
</li>
(2)而如果你的目的是有条件地跳过循环的执行,那么可以将 v-if
置于外层元素 (或 <template>
)上。如:
<ul v-if="todos.length">
<li v-for="todo in todos">
{{ todo }}
</li>
</ul>
<p v-else>No todos left!</p>