1

In the below code snippet, the PagedList LiveData observed only once. It successfully loads the next page to the recyclerView. As we know it internally use an asynchronous call to submit the result to the adapter.

Question is how to observe PagedList LiveData for every new data inserted to the list?

val callback = PostListAdapter.PagerCallback()

viewModel.posts.observe(viewLifecycleOwner, Observer<PagedList<PostData>> { pagedList ->
  adapter.submitList(pagedList) // 
  adapter.updatePostList(pagedList) // I want to update this list on new data

  pagedList.addWeakCallback(null, callback) // callback working fine.
}

I also tried PagedList.Callback() and it's working fine but LiveData is not observed.

class PagedCallback() : PagedList.Callback() {
    override fun onChanged(position: Int, count: Int) {}

    override fun onInserted(position: Int, count: Int) {
        println("count: $count")
    }
    override fun onRemoved(position: Int, count: Int) {}
})
sandpat
  • 1,478
  • 12
  • 30
Praful Ranjan
  • 117
  • 1
  • 2
  • 13

1 Answers1

2

I found the solution for my scenario and sharing the same.

We can't observe PagedList LiveData after first call as it submit result asynchronously to the adapter that why live data won't trigger.

Solution: I have added new LiveData and updating it in DataSource class after getting response from server.

ViewModel

viewModel.posts.observe(viewLifecycleOwner, Observer { pagedList ->
    adapter.submitList(pagedList)
})

// Added new LiveData to observer my list and pass it to detail screen
viewModel.postList.observe(viewLifecycleOwner, Observer {
    adapter.updatePostList(it)
})

Repository

class MyRepository(private val api: ApiService) : {
val sourceFactory = MyDataSourceFactory(api) // create MyDataSource
val postList = Transformations.switchMap( // this is new live data to observe list
       sourceFactory.sourceLiveData) { it.postList }

val data = LivePagedListBuilder(sourceFactory, PAGE_SIZE).build() 

return Result(data, postList)
}

DataSourceFactory

class MyDataSourceFactory(private val api: ApiService) : 
    DataSource.Factory<String, PostData>() {

val sourceLiveData = MutableLiveData<MyDataSource>()

override fun create(): DataSource<String, PostData> {
   val source = MyDataSource(api)
   sourceLiveData.postValue(source)
   return source
 }
}

DataSource

class MyDataSource(private val api: ApiService)
    :PageKeyedDataSource<String, PostData>() {

 val postList = MutableLiveData<List<PostData>>()

 override fun loadInitial(
     params: LoadInitialParams<String>,
     callback: LoadInitialCallback<String, PostData>) {
     //Api call here
     val list = response.body()?.data
     callback.onResult( // this line submit list to PagedList asynchronously
       list,
       response.body()?.data?.before,
       response.body()?.data?.after) 

     postList.value = response.body().data // your LiveData to observe list
}

 override fun loadAfter(
     params: LoadParams<String>,
     callback: LoadCallback<String, PostData>) {
     //Api call here
     val list = response.body()?.data?
     callback.onResult( // this line submit list to PagedList asynchronously
       list,
       response.body()?.data?.before,
       response.body()?.data?.after) 

     postList.value = response.body().data // your LiveData to observe list
}
Praful Ranjan
  • 117
  • 1
  • 2
  • 13