Trying to implement an accordion using Vue.js has been a bit challenging for me.
While I came across some examples online, my requirements are slightly different. In order to maintain SEO compatibility, I need to use "is" and "inline-template", which makes the accordion relatively static rather than fully powered by Vue.js.
I have encountered two main issues/questions:
1) The need to dynamically add the class "is-active" to the component based on user interactions (clicks), leading to the following error message.
The property or method "contentVisible" is not defined within the instance but referenced during rendering. It's essential to declare reactive data properties within the data option.
This issue arises because setting it at the instance level requires having a value (true or false) specific to each component for "contentVisible".
To tackle this, I thought of utilizing an array of "contentVisible" at the instance level along with props being passed through instances and custom events on children to update the values at the instance level.
2) While this approach could work, managing a static array poses limitations. How can I create a dynamic array without knowing the number of item components?
<div class="accordion">
<div>
<div class="accordion-item" is="item" inline-template :class="{ 'is-active': contentVisible}" >
<div>
<a @click="toggle" class="accordion-title"> Title A1</a>
<div v-show="contentVisible" class="accordion-content">albatros</div>
</div>
</div>
<div class="accordion-item" is="item" inline-template :class="{ 'is-active': contentVisible}" >
<div>
<a @click="toggle" class="accordion-title"> Title A2</a>
<div v-show="contentVisible" class="accordion-content">lorem ipsum</div>
</div>
</div>
</div>
var item = {
data: function() {
return {
contentVisible: true
}
},
methods: {
toggle: function(){
this.contentVisible = !this.contentVisible
}
}
}
new Vue({
el:'.accordion',
components: {
'item': item
}
})
Update I implemented the code below, however, the custom event that is supposed to send modifications from the component to the instance isn't functioning properly as tabsactive remains unchanged.
var item = {
props: ['active'],
data: function() {
return {
contentVisible: false
}
},
methods: {
toggle: function(index){
this.contentVisible = !this.contentVisible;
this.active[index] = this.contentVisible;
**this.$emit('tabisactive', this.active);**
console.log(this.active);
}
}
}
new Vue({
el:'.accordion',
data: {
tabsactive: [false, false]
},
components: {
'item': item
}
})
<div class="accordion" **@tabisactive="tabsactive = $event"**>
<div class="accordion-item" is="item" inline-template :active="tabsactive" :class="{'is-active': tabsactive[0]}">
<div>
<a @click="toggle(0)" class="accordion-title"> Title A1</a>
<div v-show="contentVisible" class="accordion-content">albatros</div>
</div>
</div>
<div class="accordion-item" is="item" inline-template :active="tabsactive" :class="{'is-active': tabsactive[1]}">
<div>
<a @click="toggle(1)" class="accordion-title" > Title A2</a>
<div v-show="contentVisible" class="accordion-content">lorem ipsum</div>
</div>
</div>
</div>