Time: 20190911
到本篇文章为止,我们在前面的文章中学习了如何将JS中的数据传到HTML模板中,最终转化为DOM在浏览器显示。
Vue在这个过程中扮演了怎样的角色呢?
Vue会时刻监视着data
对象的变化。下面看一个例子:
<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>Documenttitle>
<script src="https://cdn.jsdelivr.net/npm/vue">script>
head>
<body>
<div id="app">
<p>自从打开网页,已经过去{{ seconds }}秒。p>
div>
<script>
var app = new Vue(
{
el: '#app',
data: {
seconds: 0
},
created() {
// 应用启动时执行
console.log("应用启动...")
setInterval(() => {
this.seconds++
}, 1000)
}
}
)
script>
body>
html>
执行效果
就是个网页计数器,每一秒数字变化一次。
这里用到了created
生命周期钩子函数,这也是Vue框架的核心内容,会在后面继续展开。this.seconds
会指向data
对象中的变量,改变这个变量,相应的模板也会变化。
非常简洁的语法。
到目前为止,写Vue的代码都给人一种非常灵活的感觉。
上面这个例子展示的是Vue的响应式能力,用的是数值,也可以对v-bind
的属性进行操作:
<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>Documenttitle>
<script src="https://cdn.jsdelivr.net/npm/vue">script>
head>
<body>
<div id="app">
<p>自从打开网页,已经过去{{ seconds }}秒。p>
<button :disabled="buttonDisabled">测试按钮button>
div>
<script>
var app = new Vue(
{
el: '#app',
data: {
seconds: 0,
buttonDisabled: true
},
created() {
// 应用启动时执行
console.log("应用启动...")
setInterval(() => {
this.seconds++,
this.buttonDisabled = !this.buttonDisabled
}, 1000)
}
}
)
script>
body>
html>
效果如下:
到这里为止,应该可以感受到响应式的能力。响应式的实现原理是怎样的呢?后续会发一篇深入理解响应式实现原理的文章,先留空。
const vm = new Vue({
data: {
formData: {
username: 'xxx'
}
}
})
vm.formData.name = 'new user'
原先定义的username
是响应式的,即该属性的变化会触发模板更新。
新定义的不是响应式的。
有什么解决办法呢?主要有三种:
name
留个位置,就像我上面为要写的文章留个空一样,设置为undefined
,等到后面想用的时候,直接修改即可,反正它一直都是响应式的。但往未来预先定义一步,并不是那么冗余的,这牵涉到预测未来了。
Object.assign()
创建新的对象以覆盖原来的对象。vm.formData = Object.assign({}, vm.formData, {name: 'new user'})
Vue.set()
方法,可以将属性值设置为响应式的Vue.set(vm.formData, 'name', 'new user')
直接按照下标索引修改是不可行的(??)。
const vm = new Vue({
data: {
dogs: ['Rex', 'Rover', 'Alan'
}
})
vm.dogs[2] = 'Bob' // 错误
改进的方式有两种:
.splice()
函数, vm.dogs.splice(2,1, 'Bob')
Vue.set()
函数,Vue.set(vm.dogs, 2, 'Bob')
两种方法效果相同。
也是用.splice()
函数,不过这个方法只能用于缩短长度,不能扩展长度。
END.