HarmonyOS 鸿蒙next list组件嵌套展开折叠及跳转功能

发布于 1周前 作者 phonegap100 最后一次编辑是 5天前 来自 鸿蒙OS

HarmonyOS 鸿蒙Next list组件嵌套展开折叠及跳转功能实现

帮忙提供list组件嵌套的样例,每一级可以展开和折叠

2 回复
import { NodeController, FrameNode, UIContext } from "@kit.ArkUI"
import { typeNode } from '@ohos.arkui.node';

class TextNodeController extends NodeController {
  public rootNode: FrameNode | null = null;
  public listFrameNode: FrameNode | null = null;
  private uiContext: UIContext | null = null;
  private data: Array<Tree> = [
    { "id": 1, "name": "用户中心", "pid": 0 },
    {
      "id": 2,
      "name": "订单中心",
      "pid": 0,
      "children": [
        { "id": 12, "name": "所有订单", "pid": 2 },
        { "id": 14, "name": "待发货", "pid": 2 },
        { "id": 15, "name": "订单导出", "pid": 2 }
      ]
    },
    {
      "id": 3,
      "name": "系统管理",
      "pid": 0,
      "children": [
        { "id": 18, "name": "菜单设置", "pid": 3 },
        {
          "id": 19,
          "name": "权限管理",
          "pid": 3,
          "children": [
            { "id": 21, "name": "系统权限", "pid": 19 },
            { "id": 22, "name": "角色设置", "pid": 19 }
          ]
        }
      ]
    }
  ]

  makeNode(uiContext: UIContext): FrameNode | null {
    this.uiContext = uiContext
    if (this.rootNode == null) {
      this.rootNode = new FrameNode(uiContext);
      this.rootNode.commonAttribute
        .width('100%')
        .height('100%')
        .backgroundColor('#F5F1E5')
    }

    if (this.listFrameNode == null) {
      let listNode = typeNode.createNode(uiContext, 'List')
      listNode.initialize()
        .divider({
          strokeWidth: 0.5,
          color: Color.Gray
        })
      this.data.forEach((item) => {
        let listItemNode = typeNode.createNode(uiContext, 'ListItem')
        let columnNode = typeNode.createNode(uiContext, 'Column')
        let textNode = typeNode.createNode(uiContext, 'Text')
        textNode.initialize(item.name)
          .width('100%')
          .height(45)
          .padding({ left: 15 })
          .onClick(() => {
            uiContext.getPromptAction().showToast({
              message: 'parent',
              duration: 2000
            })
            const level = this.findLevel(this.data, item.id)
            const nodeType = textNode.getNextSibling()?.getNodeType()
            if (item.children && (nodeType === 'Text' || nodeType === undefined)) {
              this.addChild(textNode, item.children, level)
            } else if (nodeType === 'Column') {
              textNode.getNextSibling()?.disposeTree()
            }
          })
        columnNode.appendChild(textNode)
        listItemNode.appendChild(columnNode)
        listNode.appendChild(listItemNode)
      })
      this.rootNode.appendChild(listNode)
    }
    return this.rootNode
  }

  // 递归添加子节点
  addChild(currentNode: FrameNode, children: Tree[], level: number | undefined) {
    const parentNode = currentNode.getParent()
    let columnNode = typeNode.createNode(this.uiContext, 'Column')
    children.forEach((item) => {
      let textNode = typeNode.createNode(this.uiContext, 'Text')
      if (level) {
        textNode.initialize(item.name)
          .width('100%')
          .height(45)
          .padding({ left: 15 * (1 + level) })
          .onClick(() => {
            this.uiContext?.getPromptAction().showToast({
              message: `add child,level:${level}`,
              duration: 2000
            })
            const nextLevel = this.findLevel(this.data, item.id)
            const nodeType = textNode.getNextSibling()?.getNodeType()
            if (item.children && (nodeType === 'Text' || nodeType === undefined)) {
              this.addChild(textNode, item.children, nextLevel)
            } else if (nodeType === 'Column') {
              textNode.getNextSibling()?.disposeTree()
            }
          })
      }
      columnNode.appendChild(textNode)
    })
    parentNode?.insertChildAfter(columnNode, currentNode)
  }

  // 获取当前组件层级
  findLevel(tree: Tree[], id: number, level: number = 1): number | undefined {
    for (let node of tree) {
      if (node.id === id) {
        return level;
      }
      if (node.children) {
        const childLevel: number | undefined = this.findLevel(node.children, id, level + 1);
        if (childLevel !== undefined) {
          return childLevel;
        }
      }
    }
    return undefined;
  }
}

let textNodeController: TextNodeController = new TextNodeController();

@Entry
@Component
export struct TreePage {
  build() {
    Column() {
      NodeContainer(textNodeController)
    }
    .width('100%')
    .height('100%')
  }
}

interface Tree {
  id: number,
  name: string,
  pid: number,
  children?: Array<Tree>
}

更多关于HarmonyOS 鸿蒙next list组件嵌套展开折叠及跳转功能的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


在HarmonyOS鸿蒙系统中实现Next list组件的嵌套展开折叠及跳转功能,可以通过以下步骤进行:

  1. 组件布局:

    • 使用List组件作为外层列表。
    • 在每个列表项中嵌套一个可展开折叠的布局,如StackLayout或自定义布局。
    • 嵌套布局中包含用于显示和隐藏的详细内容以及触发展开折叠的按钮或图标。
  2. 数据绑定:

    • 为列表项绑定数据模型,模型中包含一个用于控制展开折叠状态的布尔值。
    • 通过数据绑定,将展开折叠按钮的点击事件与状态切换逻辑关联。
  3. 跳转功能:

    • 在嵌套布局中添加跳转目标页面的按钮或链接。
    • 为按钮设置点击事件监听器,在事件处理函数中实现页面跳转逻辑,如使用Intent进行页面跳转。
  4. 动画效果:

    • 可为展开折叠添加动画效果,提升用户体验。
    • 使用鸿蒙提供的动画API,如Animator类,实现展开折叠时的渐变效果。

请注意,以上步骤为大致实现流程,具体实现需根据实际需求调整。若在实现过程中遇到问题,可参考鸿蒙官方文档或示例代码。如果问题依旧没法解决请联系官网客服,官网地址是 https://www.itying.com/category-93-b0.html

回到顶部