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

Angular Material嵌套树是否支持同级节点?如何基于现有代码实现

Angular Material 嵌套树完全支持同级节点,mat-tree的节点层级完全由传入的数据源结构决定,同一父节点下children数组内的所有元素都会被自动渲染为同级节点,你现有的HTML代码基础无需做大量修改,只需要补全对应的功能逻辑即可,具体实现步骤如下:

1. 调整右键菜单配置

你现有代码中叶子节点和嵌套节点两处的mat-menu都需要新增「添加同级节点」的按钮,修改后代码如下:

<mat-menu #contextMenu="matMenu">
  <button mat-menu-item (click)="addChild(node)">添加子节点</button>
  <!-- 根节点没有父节点,隐藏新增同级按钮 -->
  <button mat-menu-item (click)="addSibling(node)" *ngIf="node.parentId !== null">添加同级节点</button>
  <button mat-menu-item *ngIf="selectednode?.id !==0" (click)="remove(node)">移除</button>
</mat-menu>

2. 定义节点数据结构

确保你的TS文件中节点接口包含父节点ID字段,方便查找同级节点所属的父级:

// 节点接口定义示例
interface TreeNode {
  id: number;
  name: string;
  parentId: number | null; // 根节点的parentId设为null
  children?: TreeNode[];
}

3. 新增同级节点操作逻辑

在TS文件中添加新增同级节点的相关方法:

// 新增同级节点方法
addSibling(currentNode: TreeNode) {
  // 替换为你自己的ID生成逻辑
  const newId = Date.now();
  const newNode: TreeNode = {
    id: newId,
    name: `新节点${newId}`,
    parentId: currentNode.parentId,
    children: []
  };

  if (currentNode.parentId === null) {
    // 根节点的同级直接插入根数据源
    this.dataSource.data.push(newNode);
  } else {
    // 查找当前节点的父节点,插入到父节点的children数组
    const parentNode = this.findNodeById(this.dataSource.data, currentNode.parentId);
    if (parentNode) {
      if (!parentNode.children) parentNode.children = [];
      parentNode.children.push(newNode);
    }
  }

  // 刷新数据源触发树重渲染
  this.dataSource.data = [...this.dataSource.data];
}

// 辅助方法:根据ID递归查找节点
findNodeById(nodes: TreeNode[], id: number): TreeNode | undefined {
  for (const node of nodes) {
    if (node.id === id) return node;
    if (node.children?.length) {
      const matched = this.findNodeById(node.children, id);
      if (matched) return matched;
    }
  }
  return undefined;
}

// 原有添加子节点方法调整为addChild,逻辑不变
addChild(parentNode: TreeNode) {
  const newId = Date.now();
  const newNode: TreeNode = {
    id: newId,
    name: `新子节点${newId}`,
    parentId: parentNode.id,
    children: []
  };
  if (!parentNode.children) parentNode.children = [];
  parentNode.children.push(newNode);
  this.dataSource.data = [...this.dataSource.data];
  // 可选:自动展开父节点显示新增的子节点
  this.treeControl.expand(parentNode);
}

4. 确认原有hasChild逻辑正常

你原有的hasChild判断方法无需修改,只要能正确识别节点是否存在子节点即可:

hasChild = (_: number, node: TreeNode) => !!node.children && node.children.length > 0;

所有修改完成后,右键点击任意非根节点即可看到新增同级节点的选项,新增的节点会自动和当前节点渲染为同级。

内容的提问来源于stack exchange,提问作者Ajay K

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.30 08:15:04