You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在React中实现动态嵌套分类的展开/收起功能

React 嵌套分类展开/隐藏实现方案

下面是实现点击主分类显示/隐藏子分类的完整代码,同时附带悬停触发的CSS方案:

点击触发版本代码

import React, { useState } from "react";

function App(props) {
  const categoriesList = [
    {
      id: "1",
      name: "Accessories",
      slug: "accessories",
      children: [
        { id: "2", name: "Mobiles", slug: "mobiles" },
        { id: "3", name: "TV", slug: "tv" },
        {
          id: "4",
          name: "Laptops",
          slug: "laptops",
          children: [{ id: "5", name: "Dell", slug: "dell" }],
        },
      ],
    },
    { id: "6", name: "Books", slug: "books" },
    {
      id: "7",
      name: "Groceries",
      slug: "groceries",
      children: [{ id: "8", name: "Noodles", slug: "noodles" }],
    },
  ];

  // 记录每个分类的展开状态,键为分类id,值为布尔值
  const [expandedCategories, setExpandedCategories] = useState({});

  // 切换指定分类的展开状态
  const toggleCategory = (categoryId) => {
    setExpandedCategories(prev => ({
      ...prev,
      [categoryId]: !prev[categoryId]
    }));
  };

  // 递归渲染分类
  const renderCategories = (categories) => {
    return categories.map(category => {
      const hasChildren = category?.children?.length > 0;
      const isExpanded = expandedCategories[category.id];

      return (
        <li className="category-list" key={category.id}>
          {/* 有子分类的项添加点击交互 */}
          <span 
            className={hasChildren ? "category-title clickable" : "category-title"}
            onClick={() => hasChildren && toggleCategory(category.id)}
          >
            {category.name}
            {/* 可选:添加展开/折叠图标提示 */}
            {hasChildren && (isExpanded ? " ▼" : " ▶")}
          </span>
          
          {/* 仅在展开状态下渲染子分类 */}
          {hasChildren && isExpanded && (
            <ul className="nested-category">
              {renderCategories(category.children)}
            </ul>
          )}
        </li>
      );
    });
  };

  return (
    <div className="app">
      <ul className="main">{renderCategories(categoriesList)}</ul>
    </div>
  );
}

关键说明

  • 状态管理:通过useState创建expandedCategories对象,独立控制每个分类的展开/折叠状态,适配嵌套层级需求。
  • 交互逻辑:仅给包含子分类的标题添加点击事件,调用toggleCategory切换对应分类的状态。
  • 条件渲染:只有当分类处于展开状态且存在子分类时,才渲染子分类列表,避免不必要的DOM渲染。

悬停触发的CSS方案(无需修改JS)

如果想用鼠标悬停代替点击触发,只需添加以下CSS样式:

/* 默认隐藏子分类 */
.nested-category {
  display: none;
}

/* 鼠标悬停父分类时显示子分类 */
.category-list:hover .nested-category {
  display: block;
}

/* 可选:给可交互标题添加样式提示 */
.category-title.clickable {
  cursor: pointer;
  color: #0066cc;
}

内容的提问来源于stack exchange,提问作者Spurgeon Gnan Prakasham Tara

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 14:10:36