Страницы

Поиск по вопросам

четверг, 21 марта 2019 г.

Получение только измененной части LiveData

Активно изучаю LiveData в андроид и хотел бы разобраться со следующим вопросом. Андроид устройство - клиент, через сокет цепляется к серверу. Сервер периодически присылает какие-то сообщения, среди них есть события, которые необходимо отрисовывать на вьюшке. Я использую mvvm паттерн. На события, пришедшие от сокета, подписывается репозиторий:
class EventRepository : IEventRepositoty {
private companion object { val MAX_EVENT = 20 } private val mEventList = MutableLiveData>() val eventList : LiveData> = mEventList ..... }
В репозитории хранится mEventList, в который я складываю события, пришедшие от сервера. Вопрос в том, что если ViewModel подпишется на eventList, то при записи нового события во ViewModel сработает observer, аргументом которого будет весь новый список. Но на вьюшке уже большая часть списка отрисована, и мне надо только вставить новый item. Решение, которое пришло в голову: события записывать не в LiveData, а в обычный list, а в LiveData держать только один EventModel Но что-то мне не нравится данный вариант, ибо при старте я запрашиваю последние события с сервера, и их придет список. Есть вариант держать LiveData>, но писать туда только список новых элементов (если событие одно, то, соответственно, список размера 1).
Может, есть какой-то более удобный способ получить только измененную часть списка?


Ответ

Если речь идет о RecyclerView, рекомендую вам обратить внимание на новый адаптер ListAdapter из библиотеки поддержки v7. Он обязывает реализовать механизм DiffUtil, который позаботится о вычислении изменений между новыми данными и уже имеющимися в адаптере и автоматически произведет нужные манипуляции (добавит, удалит, изменит соответствующие айтемы). Таким образом вы отдаете адаптеру актуальный список целиком (а не в ручную отбираете новые элементы), он же позаботится о остальном.
При этом работать будет все полностью автоматически - при изменении данных в репозитории они будут изменяться и в виджете без каких либо действий с вашей стороны.
Пример

Комментариев нет:

Отправить комментарий