onScrolled вызывается без прокрутки пользователем в recyclerView. - PullRequest
0 голосов
/ 21 апреля 2020

Я пытаюсь создать нумерацию страниц. Для этого я использую вызовы дооснащения к MovieDb API с запросом страницы в моей viewModel:

fun getMovies(page: Int = 1) {
        launch {
            if (page == 1) {
                liveData.value =
                    State.ShowLoading
            }
            val list = withContext(Dispatchers.IO) {
                try {
                    val api: MovieApi? = RetrofitService.getClient()?.create(MovieApi::class.java)
                    val response =
                        api?.getPopularMoviesListCoroutine(BuildConfig.THE_MOVIE_DB_API_TOKEN, page)
                    if (response?.isSuccessful!!) {
                        val result = response.body()
                        val list = response?.body()?.results ?: emptyList()
                        val totalPage = response?.body()?.totalPages ?: 0
                        if (!result?.results.isNullOrEmpty()) {
                            movieDao.insertAll(result?.results!!)
                        }


                        Pair(totalPage, list)
                    } else {
                        Pair(
                            1, movieDao.getAll() ?: emptyList<Movie>()
                        )

                    }
                } catch (e: Exception) {
                    Log.e("Moviedatabase", e.toString())
                    Pair(
                        1, movieDao.getAll() ?: emptyList<Movie>()
                    )
                }
            }

            liveData.postValue(
                State.Result(
                    totalPage = list.first,
                    list = list.second
                )
            )
            liveData.value = State.HideLoading
        }
    }

, а в своем фрагменте я использую эту viewModel:

override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
        val viewModelProviderFactory = ViewModelProviderFactory(requireContext())
        movieListViewModel =
            ViewModelProvider(this, viewModelProviderFactory).get(MoviesListViewModel::class.java)
        return inflater.inflate(R.layout.fragment_movie_list, container, false)
    }

Затем в привязке я вызываю getMovies в recyclerView srolling:

recyclerView.addOnScrollListener(object :PaginationListener(layoutManager){
            override fun loadMoreItems() {
                Log.d("load_more", "true --"+currentPage )
                isLoading = true
                currentPage++
                // mocking network delay for API call
                Handler().postDelayed({
                    movieListViewModel.getMovies(page = currentPage)
                }, 3000)            }

PaginationListener:


    override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
        super.onScrolled(recyclerView, dx, dy)

        val visibleItemCount = layoutManager.childCount
        val totalItemCount = layoutManager.itemCount
        val firstVisibleItemPosition = layoutManager.findFirstVisibleItemPosition()

        if (!isLoading() && !isLastPage()) {
            if (visibleItemCount + firstVisibleItemPosition >= totalItemCount &&
                firstVisibleItemPosition >= 0 &&
                totalItemCount >= PAGE_SIZE) {
                loadMoreItems()
            }
        }
    }

Также при настройке данных я использую объекты закрытого класса:

is MoviesListViewModel.State.Result -> {
                        itemCount = result.list.size
                        if (currentPage != PaginationListener.PAGE_START) {
                            movieListAdapter?.removeLoading()
                            Log.d("load_more", "remove loading")

                        }
                        movieListAdapter?.addItems(result.list)
                        if (currentPage < result.totalPage) {
                            movieListAdapter?.addLoading()
                            Log.d("load_more", "add loading")

                        } else {
                            isLastPage = true
                        }
                        isLoading = false

Итак, loadMoreItems вызывается всегда. Пожалуйста, дайте мне решение

1 Ответ

0 голосов
/ 21 апреля 2020

ты прав. OnScroll вызывает каждый раз, когда создается действие. вот часть моего фрагмента, которая обрабатывает нумерацию страниц. Я надеюсь, что это поможет:

//define out of method blocks (globaly):
boolean loaded = false;  
int page = 2;
.
.
.

//in onCreate method:
list.setOnScrollListener(new AbsListView.OnScrollListener() {

    public void onScrollStateChanged(AbsListView view, int scrollState) {
    }

    public void onScroll(AbsListView view, int firstVisibleItem, int visibleItemCount, int totalItemCount) {

        if (firstVisibleItem + visibleItemCount == totalItemCount && totalItemCount != 0) {

            if (!loaded) {
                loadMore(nextPage++);
                loaded = true;
            }

        }
    }
});

.
.
.
.
.
//after list filled (onResponse):
int index = list.getFirstVisiblePosition();
View v = list.getChildAt(0);
int top = (v == null) ? 0 : v.getTop();
list.setSelectionFromTop(index, top);
loaded = false;

, если вы не поняли, скажите мне объяснить больше и предоставить целые классы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...