Reputation: 81
So, I know how to do this in just vanilla JS, where if I have a list of things and want one item to be active at a time, I'd remove the class from all of the items listed and add it to the one that was clicked. Unfortunately, I cannot seem to figure it out in Vue.js, as I am still learning it. I am wanting to trigger a variable named 'activeComp' as true just for the clicked element, and make it false for all the other clicked elements, so only one item is active at a time. As of right now, it will allow me to select one at a time, but the class remains on the others. Here is my code:
<div v-if="companions.length > 0" v-for="companion in companions">
<comp-item :companionData="companion"></comp-item>
</div>
<template>
<div class='companion-item' @click="toggleActive" :class="{ active: activeComp }">
<h3>{{ companionData.name }} <span class='desc'>({{ companionData.desc }})</span></h3>
</div>
</template>
<script>
export default {
props: ['companionData'],
data() {
return {
activeComp: false
};
},
methods: {
toggleActive() {
this.activeComp = !this.activeComp;
}
}
}
</script>
Any help on this is much appreciated.
Upvotes: 0
Views: 6037
Reputation: 22393
Since there is only 1 active item at a moment, you should keep track of current active item in parent component:
<div
v-if="companions.length > 0"
v-for="(companion, index) in companions"
:key="index">
<comp-item :companionData="companion"
:isActive="activeIndex === index"
@onToggle="onToggle(index)">
</comp-item>
</div>
<script>
...
data() {
return {
activeIndex: null
};
},
methods: {
onToggle(index) {
if (this.activeIndex === index) {
this.activeIndex = null;
} else {
this.activeIndex = index;
}
}
}
...
</script>
Then in child component, you can emit click event to parent:
<template>
<div class='companion-item' @click="toggleActive" :class="{ active: isActive }">
<h3>{{ companionData.name }} <span class='desc'>({{ companionData.desc }})</span></h3>
</div>
</template>
<script>
export default {
props: ['companionData', 'isActive'],
data() {
return {
};
},
methods: {
toggleActive() {
this.$emit('onToggle')
}
}
}
</script>
When user clicks on an item, event will be emit to parent and handled in onToggle
method.
Upvotes: 2