Vue3 条件渲染与列表渲染
v-if
v-if
指令用于条件性地渲染一块内容。这块内容只会在指令的表达式返回 truthy 值的时候被渲染。
也可以用 v-else
添加一个“else 块”:
1 | <h1 v-if="awesome">Vue is awesome!</h1> |
在 <template>
元素上使用 v-if
条件渲染分组
因为 v-if
是一个指令,所以必须将它添加到一个元素上。但是如果想切换多个元素呢?此时可以把一个 <template>
元素当做不可见的包裹元素,并在上面使用 v-if
。最终的渲染结果将不包含 <template>
元素。
1 | <template v-if="ok"> |
v-else
可以使用 v-else
指令来表示 v-if
的“else 块”
1 | <div v-if="Math.random() > 0.5"> |
v-else
元素必须紧跟在带 v-if
或者 v-else-if
的元素的后面
v-else-if
v-else-if
,顾名思义,充当 v-if
的“else-if 块”,并且可以连续使用
1 | <div v-if="type === 'A'"> |
与 v-else
的用法类似,v-else-if
也必须紧跟在带 v-if
或者 v-else-if
的元素之后。
v-show
1 | <h1 v-show="ok">Hello!</h1> |
带有 v-show
的元素始终会被渲染并保留在 DOM 中。v-show
只是简单地切换元素的 display
CSS property。
v-show
不支持 <template>
元素,也不支持 v-else
。
v-if
vs v-show
v-if
是“真正”的条件渲染,因为它会确保在切换过程中,条件块内的事件监听器和子组件适当地被销毁和重建。
v-if
也是惰性的:如果在初始渲染时条件为假,则什么也不做——直到条件第一次变为真时,才会开始渲染条件块。
相比之下,v-show
就简单得多——不管初始条件是什么,元素总是会被渲染,并且只是简单地基于 CSS 进行切换。
一般来说,v-if
有更高的切换开销,而 v-show
有更高的初始渲染开销。因此,如果需要非常频繁地切换,则使用 v-show
较好;如果在运行时条件很少改变,则使用 v-if
较好。
v-for
我们可以用 v-for
指令基于一个数组来渲染一个列表。v-for
指令需要使用 item in items
形式的特殊语法,其中 items 是源数据数组,而 item
则是被迭代的数组元素的别名。
1 | <ul id="array-rendering"> |
v-for
还支持一个可选的第二个参数,即当前项的索引。
1 | <ul id="array-with-index"> |
也可以用 v-for
来遍历一个对象的 property。
1 | <ul id="v-for-object" class="demo"> |
维护状态
为了给 Vue 一个提示,以便它能跟踪每个节点的身份,从而重用和重新排序现有元素,你需要为每项提供一个唯一的 key
attribute:
1 | <div v-for="item in items" :key="item.id"> |
建议尽可能在使用 v-for
时提供 key
attribute,除非遍历输出的 DOM 内容非常简单,或者是刻意依赖默认行为以获取性能上的提升。
变更方法
Vue 将被侦听的数组的变更方法进行了包裹,所以它们也将会触发视图更新。
push()
pop()
shift()
unshift()
splice()
sort()
reverse()
替换数组
变更方法,顾名思义,会变更调用了这些方法的原始数组。相比之下,也有非变更方法,例如 filter()
、concat()
和 slice()
。它们不会变更原始数组,而总是返回一个新数组。
1 | example1.items = example1.items.filter(item => item.message.match(/Foo/)) |
你可能认为这将导致 Vue 丢弃现有 DOM 并重新渲染整个列表。幸运的是,事实并非如此。
显示过滤/排序后的结果
有时,我们想要显示一个数组经过过滤或排序后的版本,而不实际变更或重置原始数据。在这种情况下,可以创建一个计算属性,来返回过滤或排序后的数组。
1 | <li v-for="n in evenNumbers" :key="n">{{ n }}</li> |
1 | data() { |
v-for
与 v-if
一同使用
不推荐在同一元素上使用 v-if
和 v-for