【问题标题】:RecyclerView onScrolled method of addOnScrollListener not called except only onceaddOnScrollListener 的 RecyclerView onScrolled 方法只调用一次
【发布时间】:2020-01-11 12:16:15
【问题描述】:

背景:

我正在通过添加addOnScrollListener 函数来使用RecyclerView 实现分页逻辑。

面临的问题:

onScrolled 方法在 RecyclerView 适配器加载时调用一次,dy 值为 0。但是,当列表在滚动时到达末尾时,onScrolled 方法不会被触发,而onScrollStateChanged 触发正确。

这是我的适配器:

HistoryAdapter(Context context, ArrayList<HistoryItem> items, RecyclerView recyclerView) {
        inflater = LayoutInflater.from(context);
        this.items = items;
        preferences = PreferenceManager.getDefaultSharedPreferences(context);
        this.context = context;
        this.recyclerView = recyclerView;

        final LinearLayoutManager linearLayoutManager = (LinearLayoutManager) recyclerView.getLayoutManager();

        recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
            @Override
            public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
                super.onScrolled(recyclerView, dx, dy);
                Timber.w("onScrolled.. %s", dy);

                if (dy > 0) {
                    totalItemCount = linearLayoutManager.getItemCount();
                    lastVisibleItem = linearLayoutManager.findLastVisibleItemPosition();
                    Timber.e("totalItemCount: %s", totalItemCount);
                    Timber.e("lastVisibleItem: %s", lastVisibleItem);

                    if (!isLoading && totalItemCount <= (lastVisibleItem + 1)) {

                        Timber.i("End reached...");
                        if (onLoadMoreListener != null) {
                            //Log.i(TAG, "Episodes Adapter: onLoadMore calling...");
                            onLoadMoreListener.onLoadMore();
                        }
                        isLoading = true;
                    }
                }
            }

            @Override
            public void onScrollStateChanged(@NonNull RecyclerView recyclerView, int newState) {
                super.onScrollStateChanged(recyclerView, newState);

            }
        });
    }

回收商:

private void setupRecycler() {
        LinearLayoutManager linearLayoutManager = new LinearLayoutManager(getActivity());
        recyclerView.setLayoutManager(linearLayoutManager);
        historyAdapter = new HistoryAdapter(getActivity(), historyItems, recyclerView);
        recyclerView.setAdapter(historyAdapter);
        historyAdapter.setClickListener(this);
        historyAdapter.setOnLoadMoreListener(this);
        historyAdapter.setErrorClickListener(this);
    }

我的回收站 xml:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <LinearLayout
        android:id="@+id/header"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/medium_text_color_blue"
        android:padding="12dp">

        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:gravity="start"
            android:text="#"
            android:textColor="@android:color/white"
            android:textStyle="bold" />

        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="4.5"
            android:gravity="start"
            android:text="CLASS"
            android:textAllCaps="true"
            android:textColor="@android:color/white"
            android:textStyle="bold" />

        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="2"
            android:gravity="center"
            android:text="Date"
            android:textAllCaps="true"
            android:textColor="@android:color/white"
            android:textStyle="bold" />

        <TextView
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="2"
            android:gravity="center"
            android:text="time"
            android:textAllCaps="true"
            android:textColor="@android:color/white"
            android:textStyle="bold" />
    </LinearLayout>

    <FrameLayout
        android:layout_below="@+id/header"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <TextView
            android:id="@+id/no_reflection_text"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:visibility="gone"
            android:layout_gravity="center"
            android:text="No Reflection History found!" />

        <androidx.recyclerview.widget.RecyclerView
            android:id="@+id/history_recycler"
            android:layout_width="match_parent"
            android:layout_height="wrap_content" />
    </FrameLayout>
</RelativeLayout>

我研究过的内容:

StackOverflow 上已经发布了许多此类问题,但其中大多数都指向一个解决方案,即删除 RecyclerView 的父 ScrollView,它正在停止触发 onScrolled 方法,但这似乎不是我面临的问题。

RecyclerView.onScrolled() not getting called

RecyclerView onScrolled not called when use scrollToPosition

RecyclerView onScrolled not being fired at all

RecyclerView not calling onScrolled at the bottom

android RecyclerView onScrolled not call

https://github.com/passsy/ArrayAdapter/issues/4

【问题讨论】:

    标签: android android-recyclerview


    【解决方案1】:

    另一种方法是检查回收器是否可以垂直滚动,如果不能,则表示它已到达底部。

    试试这个

    recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
                @Override
                override fun onScrollStateChanged(recyclerView: RecyclerView, newState: Int) {
                    super.onScrollStateChanged(recyclerView, newState)
    
                    if (!recyclerView.canScrollVertically(1)) {
                        // Load more
                    }
                }
    }
    
    `
    

    【讨论】:

    • 这是一个很好的替代解决方案,而不是依赖onScrolled。我实现了它并且它正在工作。
    • 运行完美。但是当我在 onScrolled 中做同样的事情时,它有时不起作用。那么 onScrolledonScrollStateChanged 有什么区别呢? @itabdullah @christoandrew
    猜你喜欢
    • 2020-09-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-03-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多