В моем приложении для iPad есть UITableView, заполняемый из ленты. Как и большинство программ чтения RSS, он отображает список ссылок на сообщения в блогах в обратном хронологическом порядке с их заголовками и кратким описанием каждого сообщения. Лента обновляется часто и довольно большая, около 500 сообщений. Я' m, используя push-синтаксический анализ libxml2 , чтобы эффективно загружать и анализировать канал в подклассе NSOperation, создавая объекты ввода и обновляя базу данных по мере необходимости. Но затем мне нужно обновить UITableView с помощью изменений.
До сих пор приложение обновляло UITableView для каждого проанализированного сообщения по мере его анализа. Парсер выполняет эту работу в основном потоке. Но это приводит к серьезным задержкам на пару секунд, если нужно обновить много ячеек. Я могу смягчить это, запустив обновление таблицы в фоновом потоке, но кажется, что это не очень хорошая идея . Итак, теперь я пытаюсь выяснить, как более эффективно обновлять таблицу в основном потоке.
Я мог бы просто вызвать reloadData
, когда все сообщения были проанализированы, но это не очень удобно для пользователя: нет анимации, показывающей, что что-то изменилось, только вспышка и новые данные. Я бы предпочел, чтобы он был анимирован, чтобы показать, что новые сообщения добавляются, а старые удаляются. Существующие сообщения, которые не удаляются из ленты, должны перемещаться вниз по таблице новыми сообщениями, появляющимися вверху.
Я знаю, что это возможно. Автор , например, отлично справляется. Каждое сообщение добавляется или удаляется из UITableView по одному, без пропусков, показывающих фон таблицы. И все это без того, чтобы пользовательский интерфейс ни в коей мере не зависал. Как это делается ??
Моя последняя попытка - обновить таблицу только после того, как все сообщения будут проанализированы (анализатор работает довольно быстро, так что это не большая задержка). Затем он загружает существующие сообщения в NSDictionary, сопоставляя их идентификаторы с их индексами в массиве, используемом в качестве источника данных таблицы. Затем он выполняет итерацию по каждому объекту во вновь проанализированном массиве сообщений, добавляя NSIndexPath для каждого из массивов, которые позже передаются в -insertRowsAtIndexPaths: withRowAnimation:
, -deleteRowsAtIndexPaths: withRowAnimation]: [ и
-reloadRowsAtIndexPaths: withRowAnimation:
, в зависимости от ситуации, для вставки, удаления, перемещения или обновления ячеек. Для 500 сообщений обновление занимает около 4 секунд, при этом пользовательский интерфейс полностью не отвечает. Это время используется почти исключительно для анимированных обновлений UITableView; перебор двух массивов сообщений занимает очень мало времени.
Затем я изменил его так, чтобы они обновлялись без анимации , и у меня есть отдельные массивы для вставки / удаления / перезагрузки с анимацией только для позиций строк, соответствующих текущим видимым строкам. Это лучше, но появляются пробелы, когда сообщения удаляются и добавляются новые.
Извините, это так многословно, но вот результат:
Как я могу обновить UITableView, добавляя новые ячейки, нажимая другие выключено, а третьи перемещены из одной позиции в другую, до 500 ячеек в UITableView (6-8 видны одновременно), и каждая анимация происходит последовательно, при этом пользовательский интерфейс остается полностью отзывчивым?