Flutter数据结构插件unit_tree_data_structure的使用

Flutter数据结构插件unit_tree_data_structure的使用

特性

unit_tree_data_structure 插件基于计算机目录树的结构设计,有两种类型的节点:目录和文件。一个目录可以包含多个文件和其他目录,而文件是最小的层级,不能包含其他内容。

  • AbsNodeType: 抽象类表示节点的数据类型。一个节点可以是内部节点或叶节点:

    • id: 必须的,动态。
      • title: 必须的,字符串。
      • isInner: 布尔值,默认为 true
      • isUnavailable: 布尔值,默认为 false。默认定义为:如果一个分支不包含任何叶子节点,则该分支不可用(或不可选择)。
      • isChosen: 可空布尔值,默认为 false
      • isExpanded: 布尔值,默认为 false
      • isFavorite: 布尔值,默认为 false
      • isShowedInSearching: 布尔值,默认为 true。也称为 isDisplayable,在UI树具有搜索功能时使用。
    • clone(): 抽象方法,T extends AbsNodeType。允许克隆对象。
  • EasyNodeType: AbsNodeType 的简单实现。

  • TreeType: 树数据结构。

    • TAbsNodeType 的实现类。
      • data: 必须的,T
      • children: 必须的,List<TreeType<T>>
      • parent: 必须的,TreeType<T>?。如果 parent == null,则表示我们位于整个树的根部。
      • isChildrenLoadedLazily: 布尔值,默认为 false。仅在当前树是惰性加载的情况下使用,指示子节点是否已加载。
      • isLeaf: 当前树是否在叶节点?
      • isRoot: 当前树是否在根节点?
      • clone(tree, parent): 静态方法。允许克隆树。

支持函数

遍历函数

enum EChosenValues {
  /// 所有节点都被选中
  chosenAll,

  /// 没有节点被选中
  unchosenAll,

  /// 一些节点被选中
  chosenSome,

  /// 树不可选择/不可用
  notChosenable,
}
  • EChosenValues isChosenAll(tree): 检查树的当前选中状态。
  • TreeType findRoot(tree): 查找根节点。
  • TreeType? findTreeWithId(tree, id): 根据ID查找树。
  • searchAllTreesWithTitleDFS(tree, title, []result): 搜索所有标题包含 title 参数的树。
  • searchLeavesWithTitleDFS(tree, title, []result): 同上,但只针对叶子节点。
  • returnChosenLeaves(tree, []result): 返回被选中的叶子节点 (isChosen == true)。
  • returnChosenNodes(tree, []result): 返回被选中的节点。
  • returnFavoriteNodes(tree, []result): 返回被标记为收藏的节点 (isFavorite == true)。
  • int findLevel(tree): 返回当前节点的层级。

更新函数

  • updateAllUnavailableNodes(tree): 在首次创建新树时,必须调用此函数以更新节点的可用/不可用状态,并避免将来出现的问题。
  • checkAll(tree): 全部选中。
  • uncheckAll(tree): 全部取消选中。
  • updateTreeMultipleChoice(tree, chosenValue, ...): 在多选树中点击节点时更新树。
  • updateTreeSingleChoice(tree, chosenValue): 在单选树中打勾时更新树。
  • updateTreeWithSearchingTitle(tree, searchingText): 应用搜索功能时更新节点的 isShowedInSearching 属性。
  • updateTreeWithSearchingTitle(tree, searchingText): 使用文本搜索时更新节点的可显示状态。
  • insertNode(tree, node): 将节点插入为树的子节点。
  • deleteBranchByID(tree, id): 根据ID删除分支。

完整示例Demo

初始化树结构

import 'package:flutter/material.dart';
import 'package:unit_tree_data_structure/unit_tree_data_structure.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(title: Text('Unit Tree Data Structure Demo')),
        body: UnitTreeView(),
      ),
    );
  }
}

class UnitTreeView extends StatefulWidget {
  @override
  _UnitTreeViewState createState() => _UnitTreeViewState();
}

class _UnitTreeViewState extends State<UnitTreeView> {
  late TreeType<AbsNodeType> root;

  @override
  void initState() {
    super.initState();
    // 初始化根节点
    root = TreeType(
      data: EasyNodeType(
        id: 'root',
        title: '根目录',
        isInner: true,
      ),
      children: [
        TreeType(
          data: EasyNodeType(
            id: 'child1',
            title: '子目录1',
            isInner: true,
          ),
          children: [
            TreeType(
              data: EasyNodeType(
                id: 'leaf1',
                title: '叶子节点1',
                isInner: false,
                isChosen: true,
              ),
              children: [],
            ),
            TreeType(
              data: EasyNodeType(
                id: 'leaf2',
                title: '叶子节点2',
                isInner: false,
                isChosen: false,
              ),
              children: [],
            ),
          ],
        ),
        TreeType(
          data: EasyNodeType(
            id: 'child2',
            title: '子目录2',
            isInner: true,
          ),
          children: [
            TreeType(
              data: EasyNodeType(
                id: 'leaf3',
                title: '叶子节点3',
                isInner: false,
                isChosen: false,
              ),
              children: [],
            ),
          ],
        ),
      ],
    );

    // 更新所有不可用节点的状态
    updateAllUnavailableNodes(root);
  }

  @override
  Widget build(BuildContext context) {
    return Column(
      children: [
        ElevatedButton(
          onPressed: () {
            // 检查所有节点
            checkAll(root);
          },
          child: Text('检查所有'),
        ),
        ElevatedButton(
          onPressed: () {
            // 取消选中所有节点
            uncheckAll(root);
          },
          child: Text('取消选中所有'),
        ),
        Expanded(
          child: ListView(
            children: [
              // 显示树视图
              TreeViewWidget(tree: root),
            ],
          ),
        ),
      ],
    );
  }
}

自定义节点样式

class TreeViewWidget extends StatelessWidget {
  final TreeType<AbsNodeType> tree;

  TreeViewWidget({required this.tree});

  @override
  Widget build(BuildContext context) {
    return ExpansionTile(
      title: Text(tree.data.title),
      initiallyExpanded: tree.data.isExpanded,
      onExpansionChanged: (bool isExpanded) {
        setState(() {
          tree.data.isExpanded = isExpanded;
        });
      },
      children: tree.children.map((child) {
        return TreeViewWidget(tree: child);
      }).toList(),
    );
  }
}

主要依赖

确保在 pubspec.yaml 文件中添加以下依赖:

dependencies:
  flutter:
    sdk: flutter
  unit_tree_data_structure: ^1.0.0

更多关于Flutter数据结构插件unit_tree_data_structure的使用的实战教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter数据结构插件unit_tree_data_structure的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


当然,下面是一个关于如何在Flutter项目中使用unit_tree_data_structure插件的示例代码。假设你已经将该插件添加到了你的pubspec.yaml文件中,并且已经运行了flutter pub get来安装它。

1. 添加依赖

首先,确保你的pubspec.yaml文件中包含了对unit_tree_data_structure的依赖:

dependencies:
  flutter:
    sdk: flutter
  unit_tree_data_structure: ^最新版本号  # 替换为实际的最新版本号

2. 导入插件

在你的Dart文件中导入该插件:

import 'package:unit_tree_data_structure/unit_tree_data_structure.dart';

3. 使用插件

下面是一个简单的例子,展示如何创建和操作一个树数据结构:

import 'package:flutter/material.dart';
import 'package:unit_tree_data_structure/unit_tree_data_structure.dart';

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: MyHomePage(),
    );
  }
}

class MyHomePage extends StatefulWidget {
  @override
  _MyHomePageState createState() => _MyHomePageState();
}

class _MyHomePageState extends State<MyHomePage> {
  // 创建一个树节点数据类(假设插件需要这样的数据类)
  class TreeNodeData {
    String id;
    String name;

    TreeNodeData({required this.id, required this.name});
  }

  late UnitTreeDataStructure<TreeNodeData> tree;

  @override
  void initState() {
    super.initState();

    // 初始化树结构
    tree = UnitTreeDataStructure<TreeNodeData>();

    // 创建根节点
    TreeNodeData rootNode = TreeNodeData(id: '1', name: 'Root');
    tree.addRootNode(rootNode);

    // 创建子节点并添加到根节点
    TreeNodeData childNode1 = TreeNodeData(id: '2', name: 'Child 1');
    TreeNodeData childNode2 = TreeNodeData(id: '3', name: 'Child 2');
    tree.addChildNode(rootNode, childNode1);
    tree.addChildNode(rootNode, childNode2);

    // 你可以继续添加更多的节点和层级
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Flutter Tree Data Structure Demo'),
      ),
      body: Padding(
        padding: const EdgeInsets.all(8.0),
        child: Column(
          crossAxisAlignment: CrossAxisAlignment.start,
          children: <Widget>[
            Text('Root Node:', style: TextStyle(fontSize: 18, fontWeight: FontWeight.bold)),
            Text(tree.getRootNode()?.data?.name ?? 'No root node'),
            SizedBox(height: 16),
            Text('Child Nodes:', style: TextStyle(fontSize: 18, fontWeight: FontWeight.bold)),
            for (var childNode in tree.getChildNodes(tree.getRootNode()!))
              Text('  - ${childNode.data?.name}'),
          ],
        ),
      ),
    );
  }
}

4. 运行应用

确保你的Flutter环境已经配置好,然后运行应用:

flutter run

注意

  • 上述代码假设UnitTreeDataStructure有一个addRootNodeaddChildNodegetRootNodegetChildNodes方法。实际使用时,请查阅unit_tree_data_structure的官方文档,以确认具体的方法和API。
  • 插件的具体实现和API可能会有所不同,因此在实际开发中,务必参考最新的官方文档和示例代码。

希望这个示例对你有所帮助!如果有其他问题,欢迎继续提问。

回到顶部