Vue.js: 手风琴在 for 循环中不工作
Vue.js: Accordion is not working in for loop
我为单个项目添加了手风琴,它工作正常,但后来我添加了 for 循环,现在当我点击任何项目时,所有项目都会展开。
<template>
<ul class="level-0-wrp" v-if="headerDesktopMenu.menu.menu_items">
<li class="level-0" v-for="(menu, index) in headerDesktopMenu.menu.menu_items" :key="index" :class="accordionClasses" v-if="headerDesktopMenu.menu.menu_items">
<a class="title" @click="toggleAccordion">{{ menu.item_name }}</a>
<ul class="level-1-wrp" v-if="menu.childrens">
<li class="level-1" v-for="(submenuone, indexone) in menu.childrens" :key="indexone" v-if="menu.childrens">
<a class="title">{{ submenuone.item_name }}</a>
</li>
</ul>
</li>
</ul>
</template>
<script>
export default {
data () {
return {
isOpen: false
}
},
methods: {
toggleAccordion () {
this.isOpen = !this.isOpen;
}
},
computed: {
accordionClasses () {
return {
'is-closed': !this.isOpen,
'is-primary': this.isOpen,
'is-dark': !this.isOpen
};
}
}
}
如图所示,如果我点击男士、女士和配饰,就会展开。
像下面的片段一样尝试:
您可以添加另一个数据属性 selected: ''
,然后在模板中切换手风琴v-if="isOpen && menu.item_name === selected"
。在您设置的方法中选择:
toggleAccordion (item) {
item == this.selected ? this.isOpen = !this.isOpen : this.isOpen = true
this.selected = item
}`
new Vue({
el: '#demo',
data () {
return {
isOpen: false,
selected: '',
headerDesktopMenu: {
menu: {
menu_items: [{item_name:11111, childrens: [{item_name: 11}, {item_name: 12}]},{item_name:22222, childrens: [{item_name: 21}, {item_name: 22}]},{item_name:33333, childrens: [{item_name: 31}, {item_name: 32}]},{item_name:44444, childrens: [{item_name: 41}, {item_name: 42}]}]
}
}
}
},
methods: {
toggleAccordion (item) {
item == this.selected ? this.isOpen = !this.isOpen : this.isOpen = true
this.selected = item
}
},
computed: {
accordionClasses () {
return {
'is-closed': !this.isOpen,
'is-primary': this.isOpen,
'is-dark': !this.isOpen
};
}
}
})
Vue.config.productionTip = false
Vue.config.devtools = false
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="demo">
<ul class="level-0-wrp" v-if="headerDesktopMenu.menu.menu_items">
<li class="level-0" v-for="(menu, index) in headerDesktopMenu.menu.menu_items" :key="index" :class="accordionClasses" v-if="headerDesktopMenu.menu.menu_items">
<a class="title" @click="toggleAccordion(menu.item_name)">{{ menu.item_name }}</a>
<ul class="level-1-wrp" v-if="menu.childrens">
<li class="level-1" v-for="(submenuone, indexone) in menu.childrens" :key="indexone" v-if="isOpen && menu.item_name === selected">
<a class="title">{{ submenuone.item_name }}</a>
</li>
</ul>
</li>
</ul>
</div>
您已为所有项目设置 @click="toggleAccordion"
。要解决您的问题,每个项目都需要有自己的状态。例如,可以这样做:
首先,提供您的州 object
:
return {
isOpen: {}
}
因为我不知道你的数据结构,我只是用 objects
的简单 array
做了这个例子,像这样:
testObject: [
{name: "hello1"},
{name: "hello2"},
{name: "hello3"},
{name: "hello4"}
]
只需在 created
中循环执行此操作即可为所有人生成一个状态,如下所示:
for(let itemId in this.testObject) {
Object.assign(this.isOpen, {[itemId]: false})
}
object
isOpen
现在看起来像这样:
{
"0":false,
"1":false,
"2":false,
"3":false
}
现在您可以从循环中使用 index
调用 toggleAccordion
,例如 toggleAccordion(index)
并将函数更改为:
toggleAccordion(index) {
this.isOpen[index] = !this.isOpen[index];
}
你申请的地方 isOpen
现在才申请 isOpen[index]
。
我为单个项目添加了手风琴,它工作正常,但后来我添加了 for 循环,现在当我点击任何项目时,所有项目都会展开。
<template>
<ul class="level-0-wrp" v-if="headerDesktopMenu.menu.menu_items">
<li class="level-0" v-for="(menu, index) in headerDesktopMenu.menu.menu_items" :key="index" :class="accordionClasses" v-if="headerDesktopMenu.menu.menu_items">
<a class="title" @click="toggleAccordion">{{ menu.item_name }}</a>
<ul class="level-1-wrp" v-if="menu.childrens">
<li class="level-1" v-for="(submenuone, indexone) in menu.childrens" :key="indexone" v-if="menu.childrens">
<a class="title">{{ submenuone.item_name }}</a>
</li>
</ul>
</li>
</ul>
</template>
<script>
export default {
data () {
return {
isOpen: false
}
},
methods: {
toggleAccordion () {
this.isOpen = !this.isOpen;
}
},
computed: {
accordionClasses () {
return {
'is-closed': !this.isOpen,
'is-primary': this.isOpen,
'is-dark': !this.isOpen
};
}
}
}
如图所示,如果我点击男士、女士和配饰,就会展开。
像下面的片段一样尝试:
您可以添加另一个数据属性 selected: ''
,然后在模板中切换手风琴v-if="isOpen && menu.item_name === selected"
。在您设置的方法中选择:
toggleAccordion (item) {
item == this.selected ? this.isOpen = !this.isOpen : this.isOpen = true
this.selected = item
}`
new Vue({
el: '#demo',
data () {
return {
isOpen: false,
selected: '',
headerDesktopMenu: {
menu: {
menu_items: [{item_name:11111, childrens: [{item_name: 11}, {item_name: 12}]},{item_name:22222, childrens: [{item_name: 21}, {item_name: 22}]},{item_name:33333, childrens: [{item_name: 31}, {item_name: 32}]},{item_name:44444, childrens: [{item_name: 41}, {item_name: 42}]}]
}
}
}
},
methods: {
toggleAccordion (item) {
item == this.selected ? this.isOpen = !this.isOpen : this.isOpen = true
this.selected = item
}
},
computed: {
accordionClasses () {
return {
'is-closed': !this.isOpen,
'is-primary': this.isOpen,
'is-dark': !this.isOpen
};
}
}
})
Vue.config.productionTip = false
Vue.config.devtools = false
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="demo">
<ul class="level-0-wrp" v-if="headerDesktopMenu.menu.menu_items">
<li class="level-0" v-for="(menu, index) in headerDesktopMenu.menu.menu_items" :key="index" :class="accordionClasses" v-if="headerDesktopMenu.menu.menu_items">
<a class="title" @click="toggleAccordion(menu.item_name)">{{ menu.item_name }}</a>
<ul class="level-1-wrp" v-if="menu.childrens">
<li class="level-1" v-for="(submenuone, indexone) in menu.childrens" :key="indexone" v-if="isOpen && menu.item_name === selected">
<a class="title">{{ submenuone.item_name }}</a>
</li>
</ul>
</li>
</ul>
</div>
您已为所有项目设置 @click="toggleAccordion"
。要解决您的问题,每个项目都需要有自己的状态。例如,可以这样做:
首先,提供您的州 object
:
return {
isOpen: {}
}
因为我不知道你的数据结构,我只是用 objects
的简单 array
做了这个例子,像这样:
testObject: [
{name: "hello1"},
{name: "hello2"},
{name: "hello3"},
{name: "hello4"}
]
只需在 created
中循环执行此操作即可为所有人生成一个状态,如下所示:
for(let itemId in this.testObject) {
Object.assign(this.isOpen, {[itemId]: false})
}
object
isOpen
现在看起来像这样:
{
"0":false,
"1":false,
"2":false,
"3":false
}
现在您可以从循环中使用 index
调用 toggleAccordion
,例如 toggleAccordion(index)
并将函数更改为:
toggleAccordion(index) {
this.isOpen[index] = !this.isOpen[index];
}
你申请的地方 isOpen
现在才申请 isOpen[index]
。