记录一次树形分级列表的实现

栏目: IOS · 发布时间: 7年前

内容简介:项目需求需要对用户根据推荐人的不同进行树形结构显示.使用 tableView 实现这一需求.使用 tableView 实现先树形结构(不同的 cell 样式显示不同的等级),当点击 cell 时,判断当前点击的 cell 是否存在下一级,是否已经是打开状态.如果存在下一级,关闭状态,则通过插入 cell 实现点击展开树形图的效果.如果存在下一级且已经展开则通过删除 cell的方式实现树形图的关闭效果.

项目需求需要对用户根据推荐人的不同进行树形结构显示.使用 tableView 实现这一需求.

实现思路

使用 tableView 实现先树形结构(不同的 cell 样式显示不同的等级),当点击 cell 时,判断当前点击的 cell 是否存在下一级,是否已经是打开状态.如果存在下一级,关闭状态,则通过插入 cell 实现点击展开树形图的效果.如果存在下一级且已经展开则通过删除 cell的方式实现树形图的关闭效果.

具体实现

  1. 定义数据结构类型,如下:
class YTTTreeListModel: NSObject {
    
    /**
        你所需要的属性
        var name: String = ""
        var address: String = ""
        var age: Int = -1
        ...
    **/
    
    // 当前节点是否有下一级
    var isShow: Bool = false
    // 当前节点是否展开
    var isOpen: Bool = false
    // 当前的等级
    var level: Int = 0
    // 当前节点的子节点
    var child: [QWMyTeamModel] = []
}
复制代码
  1. 定义主要的方法(递归算法)
/// 获取 cell 的行数
///
/// - Parameter items: 数据源
/// - Returns: cell 行数
private func getRowsNum(_ items: [YTTTreeListModel]) -> Int {
    var num = 0
    items.forEach { (model) in
        num += 1
        if model.isShow && model.isOpen && model.child.count > 0 {
            num += getRowsNum(model.child)
        }
    }
    return num
}

/// 获取当前 cell 的数据模型
///
/// - Parameters:
///   - items: 数据源
///   - index: 当前位置
/// - Returns: 数据模型
private func getItem(_ items: [YTTTreeListModel], index: inout Int) -> YTTTreeListModel? {

    for item in items {
        if index == 0 {
            return item
        }
        index -= 1
        if item.isShow && item.isOpen && item.child.count > 0 {
            if let model = getItem(item.child, index: &index) {
                return model
            }
        }
    }
    return nil
}

/// 获取需要添加或删除的 cell
///
/// - Parameters:
///   - item: 当前数据模型(点击的 cell)
///   - index: 当前位置
/// - Returns: 需要删除或添加位置
private func getIndexPath(_ item: YTTTreeListModel, index: inout Int) -> [IndexPath] {
    var indexPaths: [IndexPath] = []
    for item in item.child {
        index += 1
        indexPaths.append(IndexPath(row: index, section: 0))
        if item.isShow && item.isOpen && item.child.count > 0 {
            indexPaths.append(contentsOf: getIndexPath(item, index: &index))
        }
    }
    return indexPaths
}
复制代码
  1. 实现代理方法
// dataArr     private var dataArr: [YTTTreeListModel] = []

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return getRowsNum(dataArr) 
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

    var index = indexPath.row
    if let model = getItem(dataArr, index: &index) {
        if model.level == 1 {
            // 返回第一级样式
        } else if model.level == 2 {
            // 返回第二级样式
        }else if model.level == 3 {
            // 返回第三级样式
        }
        ...
    }
    return UITableViewCell()
}

func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    var index = indexPath.row
    if let model = getItem(dataArr, index: &index) {

        if model.isOpen {
            tableView.beginUpdates()
            model.isOpen = false
            var ind = indexPath.row
            tableView.reloadRows(at: [indexPath], with: .none)
            tableView.deleteRows(at: getIndexPath(model, index: &ind), with: .none)
            tableView.endUpdates()
        }else {
            if !model.isShow {
                return
            }
            
            // 存在下一级且子级已经加载直接展开
            if model.isShow == 1 && model.child.count > 0 {
                tableView.beginUpdates()
                model.isOpen = true
                var ind = indexPath.row
                tableView.reloadRows(at: [indexPath], with: .none)
                tableView.insertRows(at: getIndexPath(model, index: &ind), with: .none)
                tableView.endUpdates()
            }else {
            // 存在下一级,但数据未请 求网络请求
            http.globalPOST(url: **, parameters: ["": ""], success: { [weak self] (result) in
                if let models = YTTTreeListModel(dictArray: result) as? [YTTTreeListModel] {
                    model.child = models.compactMap({ (item) -> YTTTreeListModel in
                        item.level = model.level + 1 // 设置等级
                        return item
                    })
                    tableView.beginUpdates()
                    model.isOpen = true
                    var ind = indexPath.row
                    tableView.reloadRows(at: [indexPath], with: .none)
                    if let indexs = self?.getIndexPath(model, index: &ind) {
                        tableView.insertRows(at: indexs, with: .none)
                    }
                    tableView.endUpdates()
                }

            }, fail: {(error) in

            }, isHUD: true)
            }
        }
    }
}
复制代码

以上所述就是小编给大家介绍的《记录一次树形分级列表的实现》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

阿里巴巴

阿里巴巴

邓肯·克拉克 (Duncan Clark) / 中信出版社 / 2016-8-22 / CNY 58.00

阿里巴巴的故事在中国已是家喻户晓,马云的个人魅力和非凡的商业头脑也早已声名远扬。而一千个人眼中会有一千个不一样的马云, 一个外国投资人、咨询顾问眼中的马云和阿里巴巴会是什么样的?1994年就来到中国,阿里巴巴创业早期的咨询顾问克拉克先生将阿里巴巴帝国崛起过程中他的见闻、感触和思考结合深入的访谈、研究写成了这本书。 书中既可以读到阿里巴巴艰辛的创业历程、惊心动魄的商业对垒,也不乏有趣好玩儿的背......一起来看看 《阿里巴巴》 这本书的介绍吧!

HTML 编码/解码
HTML 编码/解码

HTML 编码/解码

html转js在线工具
html转js在线工具

html转js在线工具