I have a notification list displayed through paging. When I delete or change the status of an item, I want to refresh the page so as not to lose the item when scrolling to another page. I have used a placeholder to hold the place when refreshing and do not want to show it when loading another page, but I have encountered a problem where after refreshing one page, the pages loaded in append or prepend have errors and a series of placeholders that I do not want will appear, even though only one page has been loaded.
class NotificationListPagingSource(
...
) : RxPagingSource<Int, NotificationItem>() {
override fun getRefreshKey(state: PagingState<Int, NotificationItem>): Int? {
return state.anchorPosition?.let { anchorPosition ->
val anchorPage = state.closestPageToPosition(anchorPosition)
anchorPage?.prevKey?.plus(1) ?: anchorPage?.nextKey?.minus(1) ?: 0
}
}
override fun loadSingle(params: LoadParams<Int>): Single<LoadResult<Int, NotificationItem>> {
val position = params.key ?: 0
val isStateRefresh = params is LoadParams.Refresh
return api.getNotificationList(status, position, pageSize)
.subscribeOn(Schedulers.io())
.map {
toLoadResult(it, position, isStateRefresh)
}
.onErrorReturn {
LoadResult.Error(it)
}
}
private fun toLoadResult(
data: ApiResponse<NotificationListResponse>,
position: Int,
isStateRefresh: Boolean = false
): LoadResult<Int, NotificationItem> {
val itemsBefore = if (isStateRefresh) { position * pageSize } else { 0 }
val itemsAfter = if (isStateRefresh) { (data.result?.count ?: 0) - (itemsBefore + (data.result?.data?.size ?: 0)) } else { 0 }
return LoadResult.Page(
data = data.result?.data.orEmpty(),
prevKey = if (position == 0) null else position - 1,
nextKey = if (data.result?.count == null || data.result.count == 0 || position >= ceil(data.result.count.toFloat() / pageSize).roundToInt() -1) null else position + 1 ,
itemsBefore,
itemsAfter
)
}
}
override fun getNotificationList(
status: String?,
pageSize: Int
): Flowable<PagingData<NotificationItem>> {
return Pager(
config = PagingConfig(
pageSize = pageSize,
prefetchDistance = pageSize/2,
enablePlaceholders = true,
), pagingSourceFactory = {
NotificationListPagingSource(authorizationMapApiService, status = status, pageSize = pageSize)
}
).flowable
}
and when update or delete notifcation call:
adapterNotificationList.refresh()
I am trying to refresh a page while keeping the scroll position of an item. I have tried using RemoteMediator, but when calling adapter.refresh, it deletes all the data and loses the current scroll position.