Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Update Current Page or Update Data in Paging 3 library Android Kotlin

I am new in Paging 3 library in android kotlin. I want unlimited data. So I found Paging 3 library is helpful in my case. I used PagingSource to create a list. I am not using Room. I have nested recyclerView. I am using PagingDataAdapter with diff util for my Recyclerview. I used the recommended tutorial for Paging library from codelab and I succeeded without any problem. I am facing difficult to update the item. I used paging source to create list and inside list i have some data which are coming from sever. I completely all this without any problem. But how to update adapter or notify data has changed in reyclerview. I already mechanism to fetch updated list. I searched how to update the adapter in some place but every where is mention to use invalidate() from DataSource. DataSource is used in paging 2 right?. Now this is inside the Paging 3 as per Documentation in Migrate to Paging 3. I used Flow to retrieve data. This code is inside viewmodel class.

fun createRepo(data: List<String>, repository: RepositoryData): Flow<PagingData<UnlimitData>> {
    return repository.getStreamData(data).cachedIn(viewModelScope)
}

I am passing list, which is coming from sever. getStreamData function return the items with int and string data. My Data class

data class UnlimitData(val id: Int, val name: String)

createRepo is calling in my activity class to send data in adpater.

lifecycleScope.launch {
        viewModel.createRepo(serverData,repository).collectLatest { data ->
            adapter.submitData(data)
        }
}

This is my Adapter code:-

class unlimitedAdapter() :
    PagingDataAdapter<UnlimitData, RecyclerView.ViewHolder>(COMPARATOR) {

override fun onBindViewHolder(holder: RecyclerView.ViewHolder, position: Int) {
    val item = getItem(position)
    if (item != null) {
        (holder as UnlimitedViewHolder).bind(item)
    }
}

override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): RecyclerView.ViewHolder {
    return UnlimitedViewHolder.create(parent)
}

companion object {
    private val COMPARATOR = object : DiffUtil.ItemCallback<UnlimitData>() {
        override fun areItemsTheSame(oldItem: UnlimitData, newItem: UnlimitData): Boolean =
            oldItem.id == newItem.id

        override fun areContentsTheSame(oldItem: UnlimitData, newItem: UnlimitData): Boolean = oldItem == newItem
    }
}

}

I added logic to insert/Update data in list using RetroFit. My list is updated successfully, but i am unable to refresh reyclerview.

Thanks in advance.

like image 855
vivek modi Avatar asked Oct 14 '22 23:10

vivek modi


1 Answers

In order for paging to pick up new items, you will need to call PagingSource.invalidate() to inform Pager that it needs to fetch a new PagingSource and reload pages. You'll want to keep track of all the PagingSources your factory produces and invalidate them anytime you update the backing dataset from network.

EDIT: Something like this, but this is a very rough prototype

abstract class InvalidatingPagingSourceFactory<K,V> : () -> PagingSource<K,V> {
    private val list = mutableListOf()

    abstract fun create()

    override final fun invoke() {
        create().also { list.add(it) }
    }

    fun invalidate() {
        while (list.isNotEmpty()) { list.removeFirst().invalidate() }
    }
}
like image 197
dlam Avatar answered Nov 15 '22 12:11

dlam