Vue Conditionals and Lists
Vue has directives that decide whether an element appears and that repeat an element for each item in a list.
v-if, v-else-if and v-else
v-if adds the element to the page only when its condition is true.
Example
<script setup>
import { ref } from "vue";
const marks = ref(72);
</script>
<template>
<p v-if="marks >= 80">Grade A, excellent!</p>
<p v-else-if="marks >= 60">Grade B, well done.</p>
<p v-else>Keep practising.</p>
</template>Grade B, well done.
v-else-if and v-else must come straight after a v-if or v-else-if element.
To control several elements at once without adding an extra <div>, put v-if on a <template> tag:
Example
<template v-if="isLoggedIn">
<h2>Dashboard</h2>
<p>Your next class is on Monday.</p>
</template>v-show
v-show also hides and shows an element, but in a different way.
Example
<p v-show="showOffer">Eid sale: 20% off all courses!</p>v-if | v-show | |
|---|---|---|
| How it hides | Removes the element from the page | Sets display: none |
| Cost to toggle | Higher | Very low |
| Cost at start | Low if false | Always renders once |
Works with v-else | Yes | No |
| Best for | Rarely changing conditions | Things toggled often, like a menu |
v-for with an Array
v-for repeats an element for each item. Always add a unique :key.
Example
<script setup>
import { ref } from "vue";
const courses = ref([
{ id: 1, name: "Web Development", months: 6 },
{ id: 2, name: "Graphic Designing", months: 3 },
{ id: 3, name: "Digital Marketing", months: 3 },
]);
</script>
<template>
<ul>
<li v-for="course in courses" :key="course.id">
{{ course.name }} ({{ course.months }} months)
</li>
</ul>
</template>• Web Development (6 months) • Graphic Designing (3 months) • Digital Marketing (3 months)
The key helps Vue track each item when the list changes. Use an id from your data, not a random number.
Getting the Index
v-for can also give you the position of each item:
Example
<li v-for="(course, index) in courses" :key="course.id">
{{ index + 1 }}. {{ course.name }}
</li>1. Web Development 2. Graphic Designing 3. Digital Marketing
Other Things You Can Loop Over
Example
<!-- A range of numbers: 1 to 5 -->
<span v-for="n in 5" :key="n">{{ n }} </span>
<!-- An object's values and keys -->
<p v-for="(value, key) in { city: 'Karachi', area: 'Orangi Town' }" :key="key">
{{ key }}: {{ value }}
</p>1 2 3 4 5 city: Karachi area: Orangi Town
Changing the List
Because courses is a ref, normal array methods update the page automatically:
Example
<script setup>
import { ref } from "vue";
const tasks = ref(["Revise HTML"]);
function addTask() {
tasks.value.push("Practise Vue");
}
function removeFirst() {
tasks.value.shift();
}
</script>
<template>
<button @click="addTask">Add</button>
<button @click="removeFirst">Remove first</button>
<p v-if="tasks.length === 0">No tasks left!</p>
<ul v-else>
<li v-for="task in tasks" :key="task">{{ task }}</li>
</ul>
</template>Unlike React, Vue lets you use push, splice and other mutating methods on reactive arrays.
Filtering with computed
To show only some items, use a computed value instead of putting v-if inside v-for:
Example
const shortCourses = computed(() => courses.value.filter((c) => c.months <= 3));Do not use v-if and v-for on the same element. It is confusing and Vue warns against it. Filter the list with computed, or wrap the element in a <template>.
Exercise
Exercise
Which directive is better for a menu that the user opens and closes many times?
