1. 指令-动态参数
在指令参数中使用 JavaScript 表达式,方法是用方括号括起来:
<a v-bind:[attributeName]="url"> ... </a>
可以使用动态参数为一个动态的事件名绑定处理函数:
<a v-on:[eventName]="doSomething"> ... </a>
动态参数的缩写:
<a :[key]="url"> ... </a>
<a @[event]="doSomething"> ... </a>
对动态参数表达式约定:某些字符,如空格和引号,放在 HTML attribute 名里是无效的
<!-- 这会触发一个编译警告 -->
<a v-bind:['foo' + bar]="value"> ... </a>
浏览器会把 attribute 名全部强制转为小写:
<!-- 在 DOM 中使用模板时这段代码会被转换为 `v-bind:[someattr]`。-->
<a v-bind:[someAttr]="value"> ... </a>
2. 计算属性
一般只包含getter:
computed: {
// 计算属性的 getter
publishedBooksMessage() {
// `this` 指向 vm 实例
return this.author.books.length > 0 ? 'Yes' : 'No'
}
}
自定义setter:
computed: {
fullName: {
// getter
get() {
return this.firstName + ' ' + this.lastName
},
// setter
set(newValue) {
const names = newValue.split(' ')
this.firstName = names[0]
this.lastName = names[names.length - 1]
}
}
}
计算属性缓存 vs 方法
不同的是计算属性是基于它们的响应依赖关系缓存的。计算属性只在相关响应式依赖发生改变时它们才会重新求值。
计算属性缓存 vs 侦听器
当你有一些数据需要随着其它数据变动而变动时,通常更好的做法是使用计算属性而不是命令式的 watch 回调。
3. Class 与 Style 绑定
对象语法
<div :class="{ active: isActive }"></div>
绑定对象的计算属性(返回一个对象):
<div :class="classObject"></div>
data() {
return {
isActive: true,
error: null
}
},
computed: {
classObject() {
return {
active: this.isActive && !this.error,
'text-danger': this.error && this.error.type === 'fatal'
}
}
}
数组语法
<div :class="[activeClass, errorClass]"></div>
数组中可以使用三元表达式或对象:
<div :class="[isActive ? activeClass : '', errorClass]"></div>
<div :class="[{ active: isActive }, errorClass]"></div>
4. 条件渲染
v-if vs v-show
v-if 是“真正”的条件渲染,因为它会确保在切换过程中,条件块内的事件监听器和子组件适当地被销毁和重建。
v-if 也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
相比之下,v-show 就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
一般来说,v-if 有更高的切换开销,而 v-show 有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用 v-show 较好;如果在运行时条件很少改变,则使用 v-if 较好。
5. 列表渲染
在 v-for 里使用数组:
<div v-for="(item, index) in arr"></div>
在 v-for 中使用对象:
<div v-for="(value, key, index) in obj"></div>
v-for 中设置 key 的必要性
当 Vue 正在更新使用 v-for 渲染的元素列表时,它默认使用“就地更新”的策略。如果数据项的顺序被改变,Vue 将不会移动 DOM 元素来匹配数据项的顺序,而是就地更新每个元素,并且确保它们在每个索引位置正确渲染。
这个默认的模式是高效的,但是只适用于不依赖子组件状态或临时 DOM 状态 (例如:表单输入值) 的列表渲染输出。
为了给 Vue 一个提示,以便它能跟踪每个节点的身份,从而重用和重新排序现有元素,你需要为每项提供一个唯一 key。
6. 事件处理
若需要在内联语句处理器中访问原始的 DOM 事件。可以用特殊变量 $event 把它传入方法中。
事件处理程序中可以有多个方法,这些方法由逗号运算符分隔:
<button @click="one($event), two($event)">
Submit
</button>
事件修饰符
.stop防止事件冒泡,等同于JavaScript中的event.stopPropagation()
<!-- 阻止单击事件继续传播 -->
<a @click.stop="doThis"></a>
.prevent等同于JavaScript中的event.preventDefault(),防止执行预设的行为(如果事件可取消,则取消该事件,而不停止事件的进一步传播)
<!-- 提交事件不再重载页面 -->
<form @submit.prevent="onSubmit"></form>
.capture内部元素触发的事件先在此处理,然后才交由内部元素进行处理.self只在当前元素自身触发事件时处理函数.once事件只出发一次.passive.passive会告诉浏览器你不想阻止事件的默认行为。若.passive与.prevent一起使用,.prevent将会被忽略。
为什么在 HTML 中监听事件?
所有的 Vue.js 事件处理方法和表达式都严格绑定在当前视图的 ViewModel 上,它不会导致任何维护上的困难。使用 v-on 或 @ 有几个好处:
- 扫一眼 HTML 模板便能轻松定位在 JavaScript 代码里对应的方法。
- 无须在 JavaScript 里手动绑定事件,所以ViewModel 代码可以是非常纯粹的逻辑,和 DOM 完全解耦,更易于测试。
- 当一个 ViewModel 被销毁时,所有的事件处理器都会自动被删除。无须担心如何清理它们。
7. 表单输入修饰符
.lazy
<!-- 在“change”时而非“input”时更新 -->
<input v-model.lazy="msg" />
.number
<!-- 自动将用户的输入值转为数值类型 -->
<input v-model.number="age" type="number" />
.trim
<!-- 自动过滤用户输入的首尾空白字符 -->
<input v-model.trim="msg" />
8. 组件基础
动态组件
<!-- 组件会在 `currentTabComponent` 改变时改变 -->
<component :is="currentTabComponent"></component>
在上述示例中,currentTabComponent 可以包括
- 已注册组件的名字,或
- 一个组件的选项对象
解析 DOM 模板时的注意事项
有些 HTML 元素,诸如 <ul>、<ol>、<table> 和 <select>,对于哪些元素可以出现在其内部是有严格限制的。而有些元素,诸如 <li>、<tr> 和 <option>,只能出现在其它某些特定的元素内部。变通办法:
<table>
<tr is="vue:blog-post-row"></tr>
</table>
is 的值必须以 vue: 开头,才可以被解释为 Vue 组件。