在取消隐藏stackview的一部分时,stackview不会扩展的单元格

时间:2017-01-20 14:08:22

标签: swift uitableview autolayout uistackview

我有一个带有tableview的viewcontroller,其rowHeight属性设置为UITableViewAutomaticDimension:

class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {

    private var items: [String] = []

    @IBOutlet weak var tableView: UITableView!

    // MARK: - UITableViewDataSource, UITableViewDelegate

    func numberOfSections(in tableView: UITableView) -> Int {
        return 1
    }

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return self.items.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "CustomTableViewCell") as! CustomTableViewCell
        cell.expandButton.setTitle(self.items[indexPath.row], for: .normal)
        return cell
    }

    // MARK: - View cycle

    override func viewDidLoad() {
        super.viewDidLoad()

        items = [
            "Allen","Upton","Hu","Yuli","Tiger","Flynn","Lev","Kyle","Sylvester","Mohammad",
            "Harlan","Julian","Sebastian","Porter","Preston","Palmer","Jakeem","Micah","Stephen","Tucker"
        ]

        self.tableView.estimatedRowHeight = 150
        self.tableView.rowHeight = UITableViewAutomaticDimension
    }

}

接口在IB中定义如下。它有一个自定义单元格。单元格包含stackview。在该堆栈视图的顶部,有一个按钮,在底部,有一个文本字段。文本字段最初设置为隐藏。

UITableView with prototype cell containing stackview

点击按钮将取消隐藏文本字段。但是,细胞不会膨胀:

Screenshot of iOS Simulator

预计单元格会展开以显示整个堆栈视图。为什么这不起作用?

(我已经通过重新加载单元格来使其工作,但这是一个丑陋的解决方法,需要在viewcontroller中使用代码。)

Github上的项目: https://github.com/bvankuik/TestResizingCell

2 个答案:

答案 0 :(得分:1)

我已经“修复”了如下问题。在viewcontroller中,我维护一行是否隐藏或显示其文本字段。我删除了按钮,然后使用didSelectRowAt。重新加载单元格:

struct NameCellData {
    var name: String
    var isTextFieldHidden: Bool
}

class ViewController: UIViewController, UITableViewDelegate, UITableViewDataSource {

    private var items: [NameCellData] = []

    @IBOutlet weak var tableView: UITableView!

    // MARK: - UITableViewDataSource, UITableViewDelegate

    func numberOfSections(in tableView: UITableView) -> Int {
        return 1
    }

    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return self.items.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "CustomTableViewCell") as! CustomTableViewCell
        cell.nameLabel.text = self.items[indexPath.row].name
        cell.nameCorrectionTextField.isHidden = self.items[indexPath.row].isTextFieldHidden
        return cell
    }

    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        self.items[indexPath.row].isTextFieldHidden = !self.items[indexPath.row].isTextFieldHidden
        tableView.reloadRows(at: [indexPath], with: .automatic)
    }

    // MARK: - View cycle

    override func viewDidLoad() {
        super.viewDidLoad()

        let names = [
            "Allen","Upton","Hu","Yuli","Tiger","Flynn","Lev","Kyle","Sylvester","Mohammad",
            "Harlan","Julian","Sebastian","Porter","Preston","Palmer","Jakeem","Micah","Stephen","Tucker"
        ]
        for name in names {
            let nameCellData = NameCellData(name: name, isTextFieldHidden: true)
            items.append(nameCellData)
        }

        self.tableView.estimatedRowHeight = 150
        self.tableView.rowHeight = UITableViewAutomaticDimension
    }

}

有关完整代码,请参阅Github上原始测试项目的分支: https://github.com/bvankuik/TestResizingCell/tree/withReload

答案 1 :(得分:0)

不幸的是,当您更改其中的约束时,自定义单元格高度不会自动更改。 当您生成tableView时,代理的方法是:numberOfSectionsnumberOfRowsInSectioncellForRowAt等...

tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath)也属于这种情况。这意味着如果您在更改单元格中的约束后没有重新加载tableView,则不会调用这些委托方法,并且不会通过自动布局再次计算行高。

我可以拥有的最佳建议是在显示文本字段后立即调用cell.layoutIfNeeded(),而不是重新加载tableView。