Vue3多级菜单开发问题:点击分类触发所有子分类展开而非当前分类
Vue3 分类菜单独立展开/收起问题解决
你遇到的问题核心是单个全局状态变量同时控制了所有分类的显示,点击任何分类都会触发所有子分类的状态切换。要实现独立控制,需要为每个分类维护专属的展开状态,以下是具体解决方案:
方案一:用对象记录每个分类的展开状态
修改JS代码
const menu = [ { label: "Category 1", key: "category_1", subcategories: [ { label: "1 - Subcategory 1", key: "1_subcategory_1" }, { label: "1 - Subcategory 2", key: "1_subcategory_2" }, ], }, { label: "Category 2", key: "category_2", // 统一子分类字段为subcategories(原数据是children,需对齐) subcategories: [ { label: "2 - Subcategory 1", key: "2_subcategory_1" }, ], }, ]; // 用对象存储每个分类的展开状态,初始默认隐藏 const expandedKeys = ref({}); // 接收分类key,切换对应状态 const toggleSubcategories = (key) => { expandedKeys.value[key] = !expandedKeys.value[key]; };
修改模板代码
<template> <div v-for="category in menu" :key="category.key"> <!-- 点击时传递当前分类的key --> <div @click="toggleSubcategories(category.key)"> <span>{{ category.label }}</span> <!-- 可选:添加展开/收起图标提示 --> <span style="margin-left: 8px;">{{ expandedKeys[category.key] ? '▼' : '▶' }}</span> </div> <!-- 根据当前分类的key判断是否显示子分类 --> <div v-if="expandedKeys[category.key]"> <div v-for="subcategory in category.subcategories" :key="subcategory.key" > {{ subcategory.label }} </div> </div> </div> </template>
方案二:用Set存储展开的分类key(更简洁)
如果不需要记录每个分类的初始状态,用Set来管理展开的key更高效:
JS代码修改
const expandedKeys = ref(new Set()); const toggleSubcategories = (key) => { const currentSet = expandedKeys.value; if (currentSet.has(key)) { currentSet.delete(key); } else { currentSet.add(key); } // 注意:Set是引用类型,修改后需要触发响应式更新 expandedKeys.value = new Set(currentSet); };
模板判断修改
<div v-if="expandedKeys.has(category.key)"> <!-- 子分类列表 --> </div>
注意事项
- 原数据中第二个分类的子分类字段是
children,和第一个分类的subcategories不一致,建议统一字段名,避免模板中额外判断。如果不能修改数据,模板中可以用category.subcategories || category.children来兼容。 - 之前传递参数无效的原因是没有把状态和对应分类的key绑定,只是单纯切换了全局变量,所以还是会影响所有分类。
内容的提问来源于stack exchange,提问作者paabt
相关产品推荐
相关产品推荐

