Из документов Apple (https://developer.apple.com/documentation/uikit/uitableviewdelegate/1614998-tableview):
Перед отображением на экране табличное представление вызывает этот метод для элементов в видимой части таблицы. По мере прокрутки пользователь вызывает табличное представлениеметод для элементов, только когда они перемещаются на экране. Он вызывает метод каждый раз, когда элемент появляется на экране, независимо от того, был ли он ранее отображен на экране.
Во время макета начнется заполнение табличного представления. процесс, размеры для элементов определяются.В зависимости от начальной высоты вашей ячейки и высоты табличного представления, сначала может быть вызван heightForRowAt
для строк, которые могут появиться , затем для строк, которые вероятно появится, затем для строк, которые появится (и строк, которые могут быть просто за кадром).
Добавьте оператор print()
к вашему heightForRowAt
func следующим образом:
func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
// add this line
print(indexPath)
return myTable.frame.size.height / 3.0
}
В моем быстром тесте, если 7 высота по умолчанию строки будут соответствовать в зависимости от высоты моего представления таблицы, я вижу это в выходных данных отладки:
[0, 0]
[0, 0]
[0, 0]
[0, 1]
[0, 1]
[0, 1]
[0, 2]
[0, 2]
[0, 2]
[0, 3]
[0, 3]
[0, 3]
[0, 4]
[0, 4]
[0, 4]
[0, 5]
[0, 5]
[0, 5]
[0, 6]
[0, 6]
[0, 6]
Как видите, 7 ячеек инициализируются, heightForRowAt
вызывается 3 раза для каждой ячейки.
Редактировать: тьфу ... на основе нуля ... изменено неправильно 6 исправить 7
Дополнительные примечания ...
Если вы установите .estimatedRowHeight
, например:
myTable.estimatedRowHeight = 150
, вы увидите меньше инициализируемых ячеек и с:
myTable.estimatedRowHeight = 10
вы увидите еще инициализируемых ячеек, так как автоматическое расположение будет использовать это значение в качестве начальной высоты строки, а не высоты строки по умолчанию.
Также, если вы хотите немного больше узнать о том, как ячейки используются повторно , добавьте это в ваш обработчик didSelectRowAt
(это всего лишь функция отладки / разработки, вероятно, не полезная для производственного кода):
let reusableCells = tableView.value(forKey: "_reusableTableCells")
print(reusableCells as Any)
В моем случае (без настройки .estimatedRowHeight
) я получаю:
Optional({
ContactCell = (
"<MyTest.ContactCell: 0x7fd0ccc295b0; baseClass = UITableViewCell; frame = (0 300; 295 100); text = 'Superhero'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x6000010fecc0>>",
"<MyTest.ContactCell: 0x7fd0ccc2a2a0; baseClass = UITableViewCell; frame = (0 400; 295 100); text = 'Superhero'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x6000010ff0c0>>",
"<MyTest.ContactCell: 0x7fd0ccc2ad90; baseClass = UITableViewCell; frame = (0 500; 295 100); text = 'Superhero'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x6000010ff4a0>>",
"<MyTest.ContactCell: 0x7fd0ccc2ba80; baseClass = UITableViewCell; frame = (0 600; 295 100); text = 'Superhero'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x6000010ff8a0>>"
);
})
Обратите внимание, что количество ячеек в «пуле многократного использования» будет меняться при прокрутке вверхи вниз.
Другое Редактирование:
Также стоит поэкспериментировать с ... измените эту строку в cellForRowAt
, с:
cell.textLabel?.text = "Superhero"
на:
cell.textLabel?.text = "Superhero \(indexPath.row)"
Теперь, когда вы выбираете строку и распечатываете «reusableCells», вы можете видеть, какие ячейки действительно находятся в «пуле». Мой результат меняется на:
Optional({
ContactCell = (
"<MyTest.ContactCell: 0x7fef77608330; baseClass = UITableViewCell; frame = (0 300; 295 100); text = 'Superhero 3'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x600003d36d20>>",
"<MyTest.ContactCell: 0x7fef776091b0; baseClass = UITableViewCell; frame = (0 400; 295 100); text = 'Superhero 4'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x600003d37120>>",
"<MyTest.ContactCell: 0x7fef7760a030; baseClass = UITableViewCell; frame = (0 500; 295 100); text = 'Superhero 5'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x600003d37500>>",
"<MyTest.ContactCell: 0x7fef7760aeb0; baseClass = UITableViewCell; frame = (0 600; 295 100); text = 'Superhero 6'; clipsToBounds = YES; hidden = YES; autoresize = W; layer = <CALayer: 0x600003d37920>>"
);
})
Показывает, что ячейки для строк 4, 5, 6 и 7 (как показано в свойстве text =
- опять же, начиная с нуля) были инициализированы и находятся в «пуле повторного использования».