推荐教程 :
Vue.js官网
Vue.js视频教程
8.计算属性和侦听器
模板内的表达式非常便利,但是设计它们的初衷是用于简单运算的。在模板中放入太多的逻辑会让模板过重且难以维护。所以,对于任何复杂逻辑,你都应当使用计算属性。
<1>.官方基础例子
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<!-- HTML的案例代码 Start-->
<div id="example">
<p>Original message: "{{ message }}"</p>
<p>Computed reversed message: "{{ reversedMessage }}"</p>
</div>
<!-- HTML的案例代码 END -->
<!-- JS的案例代码 -->
<script>
var vm = new Vue({
el: '#example',
data: {
message: 'Hello'
},
computed: {
// 计算属性的 getter
reversedMessage: function() {
// `this` 指向 vm 实例
return this.message.split('').reverse().join('')
}
}
})
</script>
</body>
</body>
</html>
传送门: 了解更多-计算属性
<2>.侦听器
虽然计算属性在大多数情况下更合适,但有时也需要一个自定义的侦听器。这就是为什么 Vue 通过 watch 选项提供了一个更通用的方法,来响应数据的变化。当需要在数据变化时执行异步或开销较大的操作时,这个方式是最有用的。
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<!-- HTML的案例代码 Start-->
<div id="watch-example">
<p>
问一个 是/不是 的问题:
<input v-model="question">
</p>
<p>{{ answer }}</p>
</div>
<!-- HTML的案例代码 END -->
<!-- JS的案例代码 -->
<!-- 因为 AJAX 库和通用工具的生态已经相当丰富,Vue 核心代码没有重复 -->
<!-- 提供这些功能以保持精简。这也可以让你自由选择自己更熟悉的工具。 -->
<script src="https://cdn.jsdelivr.net/npm/axios@0.12.0/dist/axios.min.js"></script>
<script src="https://cdn.jsdelivr.net/npm/lodash@4.13.1/lodash.min.js"></script>
<script>
var watchExampleVM = new Vue({
el: '#watch-example',
data: {
question: '',
answer: '除非你问问题,否则我不能给你答案!'
},
watch: {
// 如果 `question` 发生改变,这个函数就会运行
question: function (newQuestion, oldQuestion) {
this.answer = '等待你停止打字...'
this.debouncedGetAnswer()
}
},
created: function () {
// `_.debounce` 是一个通过 Lodash 限制操作频率的函数。
// 在这个例子中,我们希望限制访问 yesno.wtf/api 的频率
// AJAX 请求直到用户输入完毕才会发出。想要了解更多关于
// `_.debounce` 函数 (及其近亲 `_.throttle`) 的知识,
// 请参考:https://lodash.com/docs#debounce
this.debouncedGetAnswer = _.debounce(this.getAnswer, 500)
},
methods: {
getAnswer: function () {
if (this.question.indexOf('?') === -1) {
this.answer = '问题通常包含一个问号. ;-)'
return
}
this.answer = '思考中...'
var vm = this
axios.get('https://yesno.wtf/api')
.then(function (response) {
vm.answer = _.capitalize(response.data.answer)
})
.catch(function (error) {
vm.answer = 'Error! Could not reach the API. ' + error
})
}
}
})
</script>
</body>
</body>
</html>
9.Class 与 Style 绑定
<1>.绑定 HTML Class
[1].对象语法
通过对象的方式绑定 HTML Class,从而通过css实现Class 与 Style 绑定
<div id='app'>
<div v-bind:class="{ active: isActive }">
Hello Vue
</div>
</div>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<div v-bind:class="{ active: isActive }">
Hello Vue
</div>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
isActive: true,
}
})
</script>
<style>
.active {
color: #FF0000;
}
</style>
</body>
</html>
[2].数组语法
我们可以把一个数组传给 v-bind:class,以应用一个 class 列表:
<div v-bind:class="[activeClass, errorClass]"></div>
data: {
activeClass: 'active',
errorClass: 'text-danger'
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<div v-bind:class="[activeClass, errorClass]">
Hello Vue
</div>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
activeClass: 'active',
errorClass: 'text-danger'
}
})
</script>
<style>
.active {
color: #FF0000;
}
</style>
</body>
</html>
- 如果你也想根据条件切换列表中的 class,可以用三元表达式
<div v-bind:class="[isActive ? activeClass : '', errorClass]"></div>
[3].用在组件上
这个章节假设你已经对 Vue 组件有一定的了解。当然你也可以先跳过这里,稍后再回过头来看
<2>.绑定内联样式
[1].对象语法
<div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }">
Hello Vue
</div>
data: {
activeColor: 'red',
fontSize: 30
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<div v-bind:style="{ color: activeColor, fontSize: fontSize + 'px' }">
Hello Vue
</div>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
activeColor: 'red',
fontSize: 30
}
})
</script>
<style>
.active {
color: #FF0000;
}
</style>
</body>
</html>
直接绑定到一个样式对象通常更好,这会让模板更清晰:
<div v-bind:style="styleObject">
Hello Vue
</div>
data: {
styleObject: {
color: 'red',
fontSize: '13px'
}
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<div v-bind:style="styleObject">
Hello Vue
</div>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
styleObject: {
color: 'red',
fontSize: '24px'
}
}
})
</script>
</body>
</html>
同样的,对象语法常常结合返回对象的计算属性使用。
[2].数组语法
v-bind:style
的数组语法可以将多个样式对象应用到同一个元素上:
<div v-bind:style="[baseStyles, overridingStyles]"></div>
data: {
baseStyles: {
color: 'red',
fontSize: '24px'
},
overridingStyles: {
margin: '50px',
}
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<div v-bind:style="[baseStyles,overridingStyles]">
Hello Vue
</div>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
baseStyles: {
color: 'red',
fontSize: '24px'
},
overridingStyles:{
margin: '50px',
}
}
})
</script>
</body>
</html>
10.条件渲染
<1>.v-if
[1].使用v-if
v-if 指令用于条件性地渲染一块内容。这块内容只会在指令的表达式返回 truthy 值的时候被渲染。
<h1 v-if="awesome">Vue is awesome!</h1>
也可以用 v-else 添加一个“else 块”:
<h1 v-if="awesome">Vue is awesome!</h1>
<h1 v-else>Oh no 😢</h1>
还可以使用v-else-if
<h1 v-if="awesome">Vue is awesome!</h1>
<h1 v-else-if="usable">Vue is usable!</h1>
<h1 v-else>Oh no 😢</h1>
data: {
awesome: true,
usable:true
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<h1 v-if="awesome">Vue is awesome!</h1>
<h1 v-else-if="usable">Vue is usable!</h1>
<h1 v-else>Oh no 😢</h1>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
awesome: true,
usable:true
}
})
</script>
</body>
</html>
data: {
awesome: false,
usable: true
}
data: {
awesome: false,
usable: false
}
[2].在 元素上使用 v-if 条件渲染分组
因为 v-if 是一个指令,所以必须将它添加到一个元素上。但是如果想切换多个元素呢?此时可以把一个 元素当做不可见的包裹元素,并在上面使用 v-if。最终的渲染结果将不包含 元素。
<template v-if="awesome">
<h1>Title</h1>
<p>Paragraph 1</p>
<p>Paragraph 2</p>
</template>
data: {
awesome: true
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<template v-if="awesome">
<h1>Title</h1>
<p>Paragraph 1</p>
<p>Paragraph 2</p>
</template>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
awesome : true
}
})
</script>
</body>
</html>
[3].用 key 管理可复用的元素
Vue 会尽可能高效地渲染元素,通常会复用已有元素而不是从头开始渲染。这么做除了使 Vue 变得非常快之外,还有其它一些好处。
例如,如果你允许用户在不同的登录方式之间切换(输入框内容不变):
<template v-if="loginType === 'username'">
<label>Username</label>
<input placeholder="Enter your username">
</template>
<template v-else>
<label>Email</label>
<input placeholder="Enter your email address">
</template>
<script>
var vm = new Vue({
el: "#app",
data: {
loginType: 'username'
},
methods: {
btSwitch: function() {
if (this.$data.loginType === 'username') {
this.$data.loginType = "email"
} else {
this.$data.loginType = "username"
}
console.log(this.$data.loginType)
},
}
})
</script>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Hello Vue</title>
<script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>
<body>
<body>
<div id='app'>
<template v-if="loginType === 'username'">
<label>Username</label>
<input placeholder="Enter your username">
</template>
<template v-else>
<label>Email</label>
<input placeholder="Enter your email address">
</template>
<br />
<button @click="btSwitch">切换登录方式</button>
</div>
</body>
<script>
var vm = new Vue({
el: "#app",
data: {
loginType: 'username'
},
methods: {
btSwitch: function() {
if(this.$data.loginType === 'username'){
this.$data.loginType = "email"
}else{
this.$data.loginType = "username"
}
console.log(this.$data.loginType)
},
}
})
</script>
</body>
</html>
这样也不总是符合实际需求,所以 Vue 为你提供了一种方式来表达“这两个元素是完全独立的,不要复用它们”。只需添加一个具有唯一值的 key attribute
即可:
例如,如果你允许用户在不同的登录方式之间切换(输入框内容改变):
<template v-if="loginType === 'username'">
<label>Username</label>
<input placeholder="Enter your username" key="username-input">
</template>
<template v-else>
<label>Email</label>
<input placeholder="Enter your email address" key="email-input">
</template>
<2>.v-show
另一个用于根据条件展示元素的选项是 v-show 指令。用法大致一样:
<h1 v-show="isShow">Hello!</h1>
data: {
isShow: true
}
注意,v-show 不支持 <template> 元素,也不支持 v-else。
<3>.v-if
vs v-show
官方:
v-if
是“真正”的条件渲染,因为它会确保在切换过程中条件块内的事件监听器和子组件适当地被销毁和重建。
v-if
也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
相比之下,v-show
就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
一般来说,v-if
有更高的切换开销,而 v-show
有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用 v-show
较好;如果在运行时条件很少改变,则使用 v-if
较好。总
总结:
v-if | v-show | |
---|---|---|
开销 | 更高的切换开销 | 更高的初始渲染开销 |
使用场景 | 运行时条件很少改变 | 非常频繁地切换 |
不推荐同时使用 v-if
和 v-for
。
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。
文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/92686.html