CellForRowAtIndexPath: не называется
Мое приложение имеет два состояния: вход в систему и не вход в систему, и у меня есть следующая архитектура (значительно упрощенная):
- ViewController A, который содержит окно поиска и вид таблицы.
- ViewController B, который используется для входа в приложение.
Поток следующий:
- пользователь не вошел в систему;
- A вставляется в стек. В viewWillAppear
я проверяю, вошел ли пользователь в систему, и если да, выполняется асинхронный сетевой запрос и, как только это будет сделано, таблица будет загружена данными из сети. Однако, поскольку пользователь не входит в систему в этот момент, вид таблицы пуст,
- пользователь удаляет окно поиска; потому что он не вошел в систему, B нажали (после подтверждения),
- он успешно записывается в B, затем нажимает кнопку, которая появляется B и снова показывает A,
- на данный момент, потому что он вошел в систему, от viewWillAppear
я выполняю запрос async,
- когда это будет завершено, я вызываю reloadData
в виде таблицы.
Я замечаю, что вызывается numberOfRowsInSection:
, и он возвращает правильный результат, однако cellForRowAtIndexPath:
НЕ вызывается впоследствии, и таблица остается пустой.
Я проверил и reloadData
вызывается в основном потоке.
Любая идея, что это может быть? Потому что это сводит меня с ума!
Спасибо,
S.
EDIT: Здесь асинхронный бит кода из viewWillAppear
в A.
if ([User isLoggedIn]) {
[self.asyncRequest fetchDataWithCompletionHandler:^(id response, NSError *error) {
[UIApplication sharedApplication].networkActivityIndicatorVisible = NO;
if (error) {
[Utils displayError:error];
} else {
self.array = response;
self.isLoaded = YES;
[self.tableView reloadData];
[self.tableView setContentOffset:CGPointMake(0.0f, 0.0f) animated:NO];
}
}];
}
Я проверил, что асинхронный запрос завершен успешно и что response
содержит правильные данные (это массив, используемый для возврата UITableView
).
После reloadData
, я поставил точку останова в tableView:numberOfRowsInSection:
, и она останавливается там, и она возвращает правильное количество элементов в array
. Однако после этого точка останова в tableView:cellForRowAtIndexPath:
никогда не попадает.
Ответы
Ответ 1
Один правильный сценарий, по которому будет вызван numberOfRowsInSection
, но cellForRowAtIndexPath
не будет вызываться, - это когда размер или позиционирование таблицы не требуют отображения строк.
Например, скажем, у вас была таблица высотой 20 пикселей, но заголовок для первого раздела был 30 высоким, и вы вернули nil для заголовка (или не реализовали viewForHeaderInSection
). В этом случае никакие строки не будут отображаться, и это будет выглядеть так, как будто таблицы нет.
Я вижу, что вы используете IB. Размер таблицы может быть обманчивым в IB, поскольку он предполагает размеры заголовка и нижнего колонтитула. Я бы запустил фрейм для таблицы, чтобы вы понимали, где это происходит, когда выполняется приложение (в отличие от того, где оно появляется в IB). Я также был бы уверен, что размер и расположение таблицы таблицы вручную будут отображаться перед вызовом reloadData. Это разрешит этот действительный случай, когда cellForRowAtIndexPath
не вызывается.
Ответ 2
Убедитесь, что numberOfSectionsInTableView
не возвращает 0.
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
Ответ 3
У меня была такая же проблема, и проблема заключалась в том, что я пытался вызвать reloadData: из другого потока. Решение:
dispatch_async(dispatch_get_main_queue(), ^{
[self.tableView reloadData];
});
Ответ 4
Если вы используете другой источник данных, как и я, убедитесь, что вы сохраняете dataSource. Простое создание экземпляра класса, который будет источником данных и назначением его через tableView.dataSource = myDataClass
, будет недостаточным, поскольку свойство dataSource таблицыView будет слабым и будет выпущено при завершении viewDidLoad. Все другие методы вызывались для меня - даже, что удивительно, heightForRowAtIndexPath
- поэтому мне потребовалось некоторое время для отладки.
Ответ 5
// For others showing up on this questions via Google, etc.
// Check and make sure you've set the table view data source and delegate.
self.tableView.dataSource = self;
self.tableView.delegate = self;
Ответ 6
Если представление таблицы внутри представления, которое конфликтует с чем-то вроде Scrool View, оно не вызывается. Вы должны отделить представления в своем файле раскадровки или *.xib.
// True
▼ View
► Table View
► Scrool View
► Constraints
// False
▼ View
► Scrool View
► Table View
► Constraints
Ответ 7
Все говорят о высоте, но мой TableView
в StackView
с ведущим выравниванием заканчивается шириной 0.
Убедитесь, что ваш TableView
правильный размер, используя Debug View Hierarchy
.
Ответ 8
Я решил проблему, потому что мое Subview, в котором я добавил UITableView
не было выделено, поэтому он возвращал nill, а tableview не вызывал cellForRowAtIndexPath
а numberOfRowsInSection
cellForRowAtIndexPath
numberOfRowsInSection
Ответ 9
Это смущает и озадачивает, но здесь мое решение.
Мой код:
_scanResultTable.delegate = self;
_scanResultTable.dataSource = self; // self lifecycle was fine, wasn't getting released
[_scanResultTable reloadData];
Итак, странная часть: идентификатор _scanResultTable никогда не был объявлен в моем коде, нигде в проекте. Я понятия не имею, как это скомпилировано (и я перекомпилировал несколько раз).
Моей основной причиной было то, что я связал вывод своей таблицы со scanResultTable
в моем ViewController, но ссылался на него как _scanResultTable. Как только я начал использовать scanResultTable
как я должен был, все прояснилось. Это заставляет меня задуматься, есть ли у target-c что-то особенное в ведущих подчеркиваниях в идентификаторах...
Изменение: это делает ! Господи, я не могу дождаться, чтобы никогда больше не трогать этот язык.
Ответ 10
Я использую ReactiveCocoa. Итак, я создал модель для табличного представления. Данные были подготовлены для отображения, поэтому был вызван numberOfRows
и так далее. Но я не добавил табличное представление как подпредставление, поэтому cellForRowAtIndexPath
не был вызван)))
Ответ 11
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Make sure self.data isn't nil!
// If it is, you'll always return 0 and therefore
// cellForRowAtIndexPath will never get called.
return [self.data count];
}
Ответ 12
Я использую источник данных для клиентов, и он был выпущен. Потому что это слабая ссылка на таблицу.
Ответ 13
Если вы используете автоматическое расположение, как я, и добавляете просмотр таблицы в представление контроллера представления, убедитесь, что вы добавили эту строку при выделении представления таблицы.
tableView?.translatesAutoresizingMaskIntoConstraints = false
Глупая ошибка с моей стороны.
Ответ 14
Вы уверены, что после того, как пользователь вошел в систему и B выскочил, метод viewWillAppear
в будет вызван для выполнения обновления?
Если вы показываете B как модальный контроллер, при его отклонении вы не будете вызывать метод viewWillAppear
.
Насколько я знаю, viewWillAppear/viewDidAppear
(и другие подобные ему) являются событиями, генерируемыми UINavigationController в случае событий навигации (push/pop viewcontrollers).
Поэтому, возможно, именно поэтому вы в конечном итоге получаете свое обновление, когда вы покидаете A и возвращаетесь... все зависит от способа отображения следующего диспетчера представлений.
Ответ 15
Попробуйте вставить новые строки вручную вместо [self.tableView reloadData]
:
[self.tableView beginUpdates];
for (int i = 0; i < responseArray.count; i++) {
_rowsNumber += 1;
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:i inSection:0];
[self.tableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationBottom];
}
[self.tableView endUpdates];
В методе dataSource return incremented int _rowsNumber
:
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return _rowsNumber;
}
Ответ 16
Я решил такую же проблему, проверив идентификатор tableViewCell. Перейдите к атрибутам İnspector и посмотрите раздел идентификатора. Наверное, отсутствует. Поэтому напишите идентификатор ячейки.
Ответ 17
В этом же случае, но это была ошибка:
Я включил Scrollview с двумя таблицами внутри ViewController (требования к дизайну), в контроллере scrollview я создал программный пакет ViewControllers (который содержит TableViews), и я использовал слабый var для его хранения, Плохая идея, потому что они были выпущены в конце метода viewDidLoad.
Если вы не видите свой контент в таблице, пожалуйста, проверьте, был ли он выпущен.
Моя ошибка была очень болезненной для меня, потому что были вызваны все методы (delegate & datasource), кроме viewForCell...
Ответ 18
У меня такая же проблема
я использую Table View внутри StackView и прокрутки таблицы view отключить и установить ограничение высоты, но после этого
tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell
Не работает. Прекратите вызывать этот метод для всех Data Source
и Delegate
.
если у вас есть такая же проблема, чем у решения установлено Table View bottom, leading, trailing constrain
![введите описание изображения здесь]()
Ответ 19
Ни один из ответов здесь не помог мне.
Я использовал программные ограничения, но забыл написать:
myTableView.translatesAutoresizingMaskIntoConstraints = false
Ответ 20
Убедитесь, что ваши ограничения верны, и ни одно из них не будет удалено во время сборки.
Ответ 21
В моем случае у меня был TableView
внутри StackView
. Ru enter code here
ru Я поместил его вне StackView, он работал.
Ответ 22
check numberOfRowsInSection не 0.
иногда это 0, и никто его не узнает.