UITableViewAutomaticDimension работает не так, как ожидалось. стриж - PullRequest
0 голосов
/ 29 августа 2018

После прочтения Рэя Вендерлиха руководства для "Ячейки представления таблицы с саморазмерением", а также этого вопроса и ответов на него я решил попросить всех вас помощь.

Иметь программно созданную ячейку:

import UIKit

class NotesCell: UITableViewCell {
lazy private var cellCaption: UILabel = {
    let label = UILabel()

    label.translatesAutoresizingMaskIntoConstraints = false
    label.font = UIFont.systemFont(ofSize: 20, weight: UIFont.Weight.medium)
    label.numberOfLines = 0
    label.lineBreakMode = .byWordWrapping

    return label
}()

func configure(with note: NotesModel) {
    cellCaption.text = note.name

    contentView.addSubview(cellCaption)
}

override func layoutSubviews() {
    super.layoutSubviews()

    NSLayoutConstraint.activate([
        cellCaption.topAnchor.constraint(equalTo: contentView.topAnchor, constant: 8),
        cellCaption.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8),
        cellCaption.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -8),
//            cellCaption.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -8),
cellCaption.bottomAnchor.constraint(greaterThanOrEqualTo: contentView.bottomAnchor, constant: -8)
            ])

//        cellCaption.sizeToFit()
//        cellCaption.layoutIfNeeded()
}
}

Контроллер табличного представления использует UITableViewAutomaticDimension в методах делегата:

extension NotesTableViewController {
override func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
    return UITableViewAutomaticDimension
}

override func tableView(_ tableView: UITableView, estimatedHeightForRowAt indexPath: IndexPath) -> CGFloat {
    return UITableViewAutomaticDimension
}

}

В результате самый длинный заголовок указывается полностью, но ячейка в любом случае имеет такую ​​же высоту, как и все остальные.

enter image description here

Некоторое обновление!

Я уже пытался вставить в viewDidLoad () следующий код:

tableView.rowHeight = 44
tableView.estimatedRowHeight = UITableViewAutomaticDimension

с включением методов делегатов и их отключением. Результат тот же: (

Ответы [ 5 ]

0 голосов
/ 24 мая 2019

В Swift 5:

func configureTableView() {
        myTableView.rowHeight =  UITableView.automaticDimension
        myTableView.estimatedRowHeight = 44
    }

Имейте в виду, что если .estimatedRowHeight не правильно, Свифт сделает за вас математику. Наконец, вызовите этот метод в viewDidLoad()

0 голосов
/ 29 августа 2018

Вы делаете несколько вещей неправильно, но main point - это использование greaterThanOrEqualTo:.

Вместо этого должно быть:

cellCaption.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -8),

Кроме того, ваш текущий код добавляет новую метку в качестве подпредставления каждый раз, когда вы устанавливаете текст. Ячейки используются повторно, поэтому добавить метку нужно только при создании ячейки.

Далее правильные свойства таблицы:

    tableView.rowHeight = UITableViewAutomaticDimension
    tableView.estimatedRowHeight = 44

Поместите эти две строки в viewDidLoad() вашего контроллера табличного представления, и не не реализуют функции heightForRowAt или estimatedHeightForRowAt. Вы можете полностью удалить extension.

И, наконец, вам нужно установить ограничения только один раз. Определенно НЕ в layoutSubviews().

Вот полный пример:

//
//  NotesTableViewController.swift
//
//  Created by Don Mag on 8/29/18.
//

import UIKit

class NotesModel: NSObject {
    var name: String = ""
}

class NotesCell: UITableViewCell {
    lazy private var cellCaption: UILabel = {
        let label = UILabel()

        label.translatesAutoresizingMaskIntoConstraints = false
        label.font = UIFont.systemFont(ofSize: 20, weight: UIFont.Weight.medium)
        label.numberOfLines = 0
        label.lineBreakMode = .byWordWrapping

        return label
    }()

    func configure(with note: NotesModel) {
        cellCaption.text = note.name
    }

    override init(style: UITableViewCellStyle, reuseIdentifier: String?) {
        super.init(style: style, reuseIdentifier: reuseIdentifier)
        commonInit()
    }

    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        commonInit()
    }

    func commonInit() -> Void {

        contentView.addSubview(cellCaption)

        NSLayoutConstraint.activate([
            cellCaption.topAnchor.constraint(equalTo: contentView.topAnchor, constant: 8),
            cellCaption.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: 8),
            cellCaption.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -8),
            cellCaption.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -8),
            ])

    }

}

class NotesTableViewController: UITableViewController {

    override func viewDidLoad() {
        super.viewDidLoad()

        tableView.rowHeight = UITableViewAutomaticDimension
        tableView.estimatedRowHeight = 44
    }

    // MARK: - Table view data source

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

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

    override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "NotesCell", for: indexPath) as! NotesCell

        let m = NotesModel()

        if indexPath.row == 3 {
            m.name = "This is a very long caption. It will demonstrate how the cell height is auto-sized when the text is long enough to wrap to multiple lines."
        } else {
            m.name = "Caption \(indexPath.row)"
        }

        cell.configure(with: m)

        return cell
    }

}

Результат:

enter image description here

0 голосов
/ 29 августа 2018

Обновить следующую строку:

cellCaption.bottomAnchor.constraint(greaterThanOrEqualTo: contentView.bottomAnchor, constant: -8)
            ])

до:

cellCaption.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -8)
            ])

и добавьте следующее в viewDidLoad:

self.tableView.rowHeight = UITableViewAutomaticDimension;
self.tableView.estimatedRowHeight = 44.0;
0 голосов
/ 29 августа 2018

Следующие шаги могут решить вашу проблему:

1) установите верхнюю, нижнюю, начальную и конечную ограничения для UILabel в ячейке, как показано ниже: enter image description here

2) настроить просмотр таблицы:

self.tableView.rowHeight = UITableViewAutomaticDimension;
self.tableView.estimatedRowHeight = 44.0;
0 голосов
/ 29 августа 2018

Я бы рекомендовал не использовать методы делегатов для ваших нужд.

Просто попробуйте установить это в вашем viewDidLoad:

self.tableView.rowHeight = UITableViewAutomaticDimension;
// set estimatedRowHeight to whatever is the fallBack rowHeight
self.tableView.estimatedRowHeight = 44.0;

Это всегда работает для меня. Дайте мне знать, если это поможет :)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...