在Kotlin中就要用companion object和@JvmStatic
class ImageViewBindingAdapter {
//里面的BindingAdapter方法必须是静态方法,否则会编译会报错
//DataBinding调用必须是静态方法
companion object {
@JvmStatic
@BindingAdapter("image")
fun setImage(imageView:ImageView, url: String){
if (!TextUtils.isEmpty(url)){
//加载网络图片
} else{
imageView.setBackgroundColor(Color.GRAY)
}
}
}
}
在计算paging的prevKey和nextKey,也就是上一页,下一页的时候,需要考虑PagingConfig中的initialLoadSize参数
fun loadMovie(): Flow<PagingData<Movie>> {
return Pager(
config = PagingConfig(
pageSize = 8,
//第一次加载的数量,16也就是2页,默认是3*pageSize
initialLoadSize = 16
),
pagingSourceFactory = { MoviePagingSource() }
).flow
}
class MoviePagingSource: PagingSource<Int, Movie>() {
override fun getRefreshKey(state: PagingState<Int, Movie>): Int? {
//第一次加载
return 1
}
override suspend fun load(params: LoadParams<Int>): LoadResult<Int, Movie> {
val currentPage = params.key ?: 1
val pageSize = params.loadSize
val movies = RetrofitClient.createApi(MoviesApi::class.java).getMovies(currentPage, pageSize)
var prevKey: Int? = null
var nextKey: Int? = null
//PagingConfig中的2个参数
val realPageSize = 8
val initialLoadSize = 16
if (currentPage == 1){
prevKey = null
nextKey = initialLoadSize / realPageSize + 1
}else{
prevKey = currentPage - 1
nextKey = if (movies.hasMore) currentPage + 1 else null
}
//下面这样计算,在initialLoadSize不等于realPageSize的时候会有数据错乱
//prevKey = if (currentPage == 1) null else currentPage - 1
//nextKey = if (movies.hasMore) currentPage + 1 else null
return try {
LoadResult.Page(
data = movies.movieList,
prevKey = prevKey,
nextKey = nextKey
)
}catch (e: Exception){
e.printStackTrace()
return LoadResult.Error(e)
}
}
}
recycleView.adapter = movieAdapter.withLoadStateFooter(MovieLoadMoreAdapter(this@MainActivity))
只需要加个适配器就可以
class MovieLoadMoreAdapter(private val context: Context): LoadStateAdapter<BindViewHolder>() {
override fun onBindViewHolder(holder: BindViewHolder, loadState: LoadState) {
}
override fun onCreateViewHolder(parent: ViewGroup, loadState: LoadState): BindViewHolder {
val binding = MovieLoadmoreBinding.inflate(LayoutInflater.from(context), null, false)
return BindViewHolder(binding)
}
}
<androidx.swiperefreshlayout.widget.SwipeRefreshLayout
android\:id="@+id/swipeRefreshLayout"
android\:layout\_width="match\_parent"
android\:layout\_height="match\_parent">
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recycleView"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager" />
</androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
swipeRefreshLayout.setOnRefreshListener {
movieAdapter.refresh()
}
lifecycleScope.launchWhenCreated {
movieAdapter.loadStateFlow.collectLatest { state ->
mBinding.swipeRefreshLayout.isRefreshing = state.refresh is LoadState.Loading
}
}
class MovieViewModel: ViewModel() {
private val movies by lazy {
Pager(
config = PagingConfig(
pageSize = 8,
//第一次加载的数量,16也就是2页
initialLoadSize = 16,
//预刷新的距离,距离最后一个item多远时加载数据,默认为pageSize
prefetchDistance = 8
),
pagingSourceFactory = { MoviePagingSource() }
).flow.cachedIn(viewModelScope)
}
fun loadMovie(): Flow<PagingData<Movie>> = movies
}
码字不易,求转发,求点在看,求关注,感谢!