UITableView - загружать большие UIImages из NSBundle, не блокируя основной поток

В UITableViewController пользовательский интерфейс зависает при вызове этого метода: - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

где изображение загружается в UITableViewCell.

cell.imageView.image = [UIImage imageWithContentsOfFile:@"filePath"];

Файлы хранятся локально в папке документов - это не удаленный вызов. Я понимаю, что загрузка изображения во время создания ячейки приводит к зависанию основного потока, если бы это был удаленный вызов, я бы использовал асинхронную загрузку, но как бы вы сделали это для локальных файлов?

* изображения около 500k.

Нужна помощь. Спасибо.


person Yogev Shelly    schedule 28.09.2011    source источник
comment
500 тыс. изображений из пакета для отображения в виде таблицы в ячейках? подумайте о том, чтобы сделать большие пальцы. Это может уменьшить размер в 10 раз.   -  person Valeriy Van    schedule 28.09.2011
comment
подойдет, и он улучшится, но все равно будет небольшая задержка, когда табличное представление перезагрузит ячейки. я хочу использовать 100% бесплатный пользовательский интерфейс — такую ​​же скорость отклика, которую я получил бы, если бы использовал ASIHTTPRequest для удаленных изображений.   -  person Yogev Shelly    schedule 28.09.2011
comment
в вопросе вы пишете, что загружаете изображения из пакета. Если вы загружаете изображения не для всей таблицы, а только те, которые вам сейчас нужны для отображения, загрузка будет почти немедленной, если изображения имеют разумный размер. Но если вы загружаете изображения из Интернета, вам нужен другой подход. Загружать изображения в фоновом режиме и вместо незагруженных изображений отображать заполнитель.   -  person Valeriy Van    schedule 28.09.2011
comment
Изображения загружаются из библиотеки документов, то есть локально с устройства (не NSBundle, но они тоже могут быть) - есть множество ответов о загрузке удаленного изображения, мне интересно знать, когда данные UIImage готовы, поэтому я могу отобразите его из фонового потока в поток пользовательского интерфейса, как я сделал бы для удаленных изображений. Кстати, сейчас я использую большие пальцы, и теперь все работает нормально... но вопрос остается.   -  person Yogev Shelly    schedule 30.09.2011


Ответы (1)


Например, создайте отдельный поток, в который вы будете загружать изображения и сохранять ссылки на них в какой-нибудь array. Когда все изображения будут готовы (или какая-то их часть), вы можете reload cells, которые должны содержать эти сообщения.

В table view controller вы должны проверить, загружен ли уже image для этого cell, и если это просто взять ссылку и установить cell.imageView.image с ней.

person Nekto    schedule 28.09.2011
comment
Как узнать, что локальный файл завершил загрузку? - person Yogev Shelly; 28.09.2011
comment
Когда [UIImage imageWithContentsOfFile:@"filePath"]; вернет ссылку, это будет означать, что локальный файл загружен в память. - person Nekto; 28.09.2011
comment
Итак, вы предлагаете мне добавить интервал, чтобы проверить это? нет ли цели/действия, уведомления или чего-то еще, чего я могу дождаться? - person Yogev Shelly; 28.09.2011
comment
Нет, вам следует просто создать отдельный поток, где вы будете загружать эти изображения по кругу, а когда какая-то часть этих изображений будет загружена, просто перезагрузите соответствующие ячейки представления таблицы, вызвав какой-либо метод в основном потоке. - person Nekto; 28.09.2011
comment
Спасибо, что именно вы подразумеваете под кругом? (в то время как цикл?) - person Yogev Shelly; 28.09.2011
comment
Да, while(count < numberOfImages){[arr addObject:[UIImage imageWithContentsOfFile:@"filePath"]]; count++;} - person Nekto; 28.09.2011