当前位置:首页 > JavaScript

js实现无穷树形菜单

2026-03-01 16:40:17JavaScript

实现思路

使用递归组件实现无穷树形菜单,核心在于组件能够调用自身,并动态渲染子节点。数据结构通常采用嵌套的children数组形式。

js实现无穷树形菜单

数据结构示例

const treeData = [
  {
    id: 1,
    label: '节点1',
    children: [
      {
        id: 2,
        label: '节点1.1',
        children: [
          { id: 3, label: '节点1.1.1' }
        ]
      }
    ]
  },
  {
    id: 4,
    label: '节点2'
  }
]

递归组件实现

function TreeNode({ node }) {
  const [isExpanded, setIsExpanded] = useState(false)

  return (
    <div className="tree-node">
      <div 
        className="node-label" 
        onClick={() => setIsExpanded(!isExpanded)}
      >
        {node.children && (
          <span className="toggle-icon">
            {isExpanded ? '−' : '+'}
          </span>
        )}
        {node.label}
      </div>

      {isExpanded && node.children && (
        <div className="children">
          {node.children.map(child => (
            <TreeNode key={child.id} node={child} />
          ))}
        </div>
      )}
    </div>
  )
}

// 使用方式
function TreeMenu() {
  return (
    <div className="tree-menu">
      {treeData.map(node => (
        <TreeNode key={node.id} node={node} />
      ))}
    </div>
  )
}

样式建议

.tree-node {
  margin-left: 20px;
  cursor: pointer;
}

.node-label {
  padding: 5px;
}

.node-label:hover {
  background-color: #f0f0f0;
}

.toggle-icon {
  display: inline-block;
  width: 20px;
  text-align: center;
}

性能优化

对于大型树结构,可采用虚拟滚动技术。以下为简化版实现思路:

js实现无穷树形菜单

function useVirtualScroll(items, itemHeight, containerRef) {
  const [startIndex, setStartIndex] = useState(0)
  const visibleCount = Math.ceil(containerRef.current?.clientHeight / itemHeight)

  useEffect(() => {
    const handleScroll = () => {
      const newStart = Math.floor(containerRef.current.scrollTop / itemHeight)
      setStartIndex(newStart)
    }
    containerRef.current.addEventListener('scroll', handleScroll)
    return () => containerRef.current.removeEventListener('scroll', handleScroll)
  }, [])

  return items.slice(startIndex, startIndex + visibleCount)
}

动态加载方案

当数据量极大时,可采用懒加载方式:

async function loadChildren(parentId) {
  const response = await fetch(`/api/nodes?parent=${parentId}`)
  return response.json()
}

// 在TreeNode组件中
useEffect(() => {
  if (isExpanded && !node.children) {
    loadChildren(node.id).then(children => {
      // 更新数据逻辑
    })
  }
}, [isExpanded])

交互增强

添加复选框支持:

function TreeNode({ node, onCheck }) {
  const handleCheck = (e) => {
    e.stopPropagation()
    onCheck(node.id, e.target.checked)
  }

  return (
    <div className="tree-node">
      <input 
        type="checkbox" 
        checked={node.checked} 
        onChange={handleCheck}
      />
      {/* 其余代码 */}
    </div>
  )
}

注意事项

  1. 确保每个节点有唯一标识符(如id
  2. 深层嵌套时考虑使用不可变数据更新
  3. 对于超大数据量建议结合后端分页加载
  4. 可添加动画效果提升用户体验

标签: 菜单js
分享给朋友:

相关文章

js 实现vue模板

js 实现vue模板

实现 Vue 模板的 JavaScript 方法 通过原生 JavaScript 可以实现类似 Vue 的模板渲染功能,主要包括数据绑定、指令处理和模板解析。以下是核心实现思路: 数据绑定与响应式…

原生js实现轮播图

原生js实现轮播图

基本结构搭建 HTML部分需要包含轮播图容器、图片列表及导航按钮。结构示例如下: <div class="slider-container"> <div class="slid…

js实现交换

js实现交换

交换变量的方法 在JavaScript中,交换两个变量的值有多种方法。以下是常见的几种实现方式: 使用临时变量 通过引入一个临时变量来存储其中一个变量的值,实现交换: let a = 1; le…

vue elementui实现菜单

vue elementui实现菜单

使用 Vue 和 Element UI 实现菜单 Element UI 提供了 el-menu 组件,可以轻松实现导航菜单功能。以下是一个完整的实现示例: 安装 Element UI 确保项目已安装…

css制作二级菜单

css制作二级菜单

CSS制作二级菜单的方法 通过纯CSS实现二级菜单主要依赖HTML结构嵌套和CSS的:hover伪类选择器。以下是具体实现方式: HTML结构 <ul class="main-menu"&g…

js节流实现

js节流实现

节流的概念 节流(Throttle)是一种限制函数执行频率的技术,确保函数在一定时间间隔内只执行一次。常用于滚动事件、窗口调整等高频触发的场景。 基础实现方法 使用时间戳判断是否执行函数:…