如何从 UITableViewCell 中加载 UITableView?

How to load an UITableView from inside UITableViewCell?

显示一些代码之前的快速解释:

我想创建一个架构,其中包含帖子、对这些 post 的回复以及对这些回复的回复等(我可以定义一个限制)。

每个回复都可以展开。

我不知道我是否采取了正确的方式,但我正在考虑添加一个 UITableView 作为我的 UITableViewCell 的子级来显示回复,然后再做一次以回复回复等。

我现在只有一个 UITableView,所有 posts 作为 xib 中的可重用单元格。由于我无法向此 xib 添加 UITableView 和单元格,所以我被卡住了。

这是一些代码:

帖子 UITableView 函数:

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = argumentList.dequeueReusableCell(withIdentifier: "postBox", for: indexPath) as! PostBox
        let currentPost = postListItems[indexPath.row]
        cell.postBoxView.message = currentPost
        return cell
    }

邮箱文件:

import UIKit

class PostBox: UITableViewCell {
    let apiClient = APIClient.sharedInstance
    @IBOutlet weak var postBoxView: PostBoxView!
}

PostBoxView 文件:

class PostBoxView: UIView {
    var apiClient = APIClient.sharedInstance
    var repliesOpen: Bool = false
    @IBOutlet var contentView: UIView!
    // Bunch of outlets here
    
    var message: Message! {
        didSet {
            // initializing design stuff here
        }
    }
    
    override init(frame: CGRect){
        super.init(frame: frame)
        self.commonInit()
    }
    
    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        self.commonInit()
    }
    
    func commonInit(){
        let bundle = Bundle(for: Self.self)
        let nib = UINib(nibName: String(describing: type(of: self)), bundle: bundle)
        nib.instantiate(withOwner: self, options: nil)

        addSubview(contentView)
        contentView.translatesAutoresizingMaskIntoConstraints = false
        NSLayoutConstraint.activate([
            contentView.topAnchor.constraint(equalTo: topAnchor),
            contentView.bottomAnchor.constraint(equalTo: bottomAnchor),
            contentView.leadingAnchor.constraint(equalTo: leadingAnchor),
            contentView.trailingAnchor.constraint(equalTo: trailingAnchor)
        ])
    }
    
    @IBAction func showPostReplies(_ sender: Any) {
        self.toggleReplies(show: true)
    }
    
    func getReplies() {
        apiClient.getReplies(postId: String(self.message.id), sort: "-created_at", perPage: 5, page: 1, completion: { replies in
            print(replies)
        })
    }
    
    func toggleReplies(show: Bool) {
        self.repliesOpen = show
        switch repliesOpen {
        case true:
            self.getReplies()
        case false:
            print("close")
        }
    }
}

所以我想知道如何向我的 post 添加回复,然后向我的回复添加回复。 也许我理解错了,所以能提供一点帮助就好了。

伙计,将 table 视图添加到 table 视图单元格是一个非常糟糕的主意(太离谱了,我不得不打开这个问题)。

相对于UI来说,是相对的straight-forward。 您可以将 post 设为 header 部分或只是一个单元格。无论哪种方式,所有回复也将是相同 table 中的单元格——为它们创建一个不同的 UITableViewCell 子类并使用缩进来实现层次结构。 (UITableviewCell 的 indentationLevel 和 indentationWidth 属性) expand - collapse (getReplies) 的动作不应在单元格中调用,而应通过委托在 viewController(或 viewModel / presenter,具体取决于您使用的是什么)中调用。

您真正关心的应该是为 table 提供一个 top-notch 数据结构,它将存储 posts + 回复 + 回复展开状态 + 回复层次结构级别。

我希望这会让您走上正确的道路。 (不要在 table 视图单元格内添加 table 视图,如果您的回复足够深入,您实际上可能会导致堆栈溢出)

这是我很快想出的数据结构(不包括数据字段,但您需要获取它的所有其他内容 运行。)

protocol Repliable {
    var replies: [Repliable] {get}
    var replyLevel: Int {get}
    var isPost: Bool {get}
}

struct Post: Repliable {
    //data fields
    
    let isPost = true
    let replyLevel = 0
    var replies: [Repliable]
}

struct Reply: Repliable {
    //data fields
    
    let isPost = false
    var replyLevel: Int
    var replies: [Repliable]
}

要使用它,您的 tableview 应该使用 Repliable 数组。每次展开(获取)回复时,您只需将它们添加到数组中的正确位置并将行添加到 table。您现在的挑战只是让它们在数组中正确排序。像这样-> Post 1,回复 1,回复 1 到回复 1,回复 2,Post 2 ...