簡體   English   中英

當recyclerView已在底部並添加新項時,將其保留在底部

[英]Keep recyclerView at bottom when already at bottom and new item is added

我正在創建一個聊天應用程序。 我試圖使所有新消息都顯示在屏幕上可見列表中當前最低的項目時,而不是當用戶向上滾動時(如大多數聊天應用程序),出現在聊天應用程序的底部。 截至目前,當屏幕上仍然有未使用的空間時,我已經可以使用此功能,但是當RecyclerView的視圖太多而無法容納時,它將開始在屏幕底部顯示新消息。 這是我創建RecyclerView的方法:

private void initRecyclerView() {


    mRecyclerView = findViewById(R.id.chatRecyclerView);
    mAdapter = new ChatRecyclerViewAdapter(this, mMessages, mUsernames, mRoomID, mDatabaseReference);
    mRecyclerView.setAdapter(mAdapter);
    final LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this);
    linearLayoutManager.setStackFromEnd(true);
    RecyclerView.AdapterDataObserver observer = new RecyclerView.AdapterDataObserver() {
        @Override
        public void onChanged() {
            super.onChanged();

            if(linearLayoutManager.findLastVisibleItemPosition()==(mAdapter.getItemCount()-1)){
                mRecyclerView.smoothScrollToPosition(mAdapter.getItemCount()-1);
            }
        }
    };
    mAdapter.registerAdapterDataObserver(observer);
    mRecyclerView.setLayoutManager(linearLayoutManager);

最后,我添加了一個檢查以查看RecyclerView是否在底部,並將該布爾值插入AdapterDataObserver。 我還犯了一個錯誤,即使用觀察者的onChanged方法而不是onItemRangeInserted,這顯然是對RecyclerViewAdapter中的notifyItemInserted的補充。

這是我的RecyclerView的工作代碼,如果用戶位於底部,它將自動在底部放置新消息:

 private void initRecyclerView() {


    //initializes and sets adapter 


    mRecyclerView = findViewById(R.id.chatRecyclerView);
    mAdapter = new ChatRecyclerViewAdapter(this, mMessages, mUsernames, mRoomID, mDatabaseReference);
    mRecyclerView.setAdapter(mAdapter);

    //Creates layout manager and makes it feed new RecyclerView views from the bottom


    final LinearLayoutManager linearLayoutManager = new LinearLayoutManager(this);
    linearLayoutManager.setStackFromEnd(true);

    //Makes RecyclerView scroll to bottom when notifyItemInserted is called from adapter and RecyclerView is already at bottom

    RecyclerView.AdapterDataObserver observer = new RecyclerView.AdapterDataObserver() {
        @Override
        public void onItemRangeInserted(int positionStart, int itemCount) {
            super.onItemRangeInserted(positionStart, itemCount);


            if (isAtBottom) {
                mRecyclerView.smoothScrollToPosition(mAdapter.getItemCount() - 1);
            } else {
            }
        }
    };

    //Adds logic to see if RecyclerView is at bottom or not

    mRecyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
        @Override
        public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
            super.onScrollStateChanged(recyclerView, newState);

            if (!recyclerView.canScrollVertically(1)) {
                isAtBottom = true;
            } else {
                isAtBottom = false;
            }
        }
    });

    //Assigns observer to adapter and LayoutManager to RecyclerView

    mAdapter.registerAdapterDataObserver(observer);
    mRecyclerView.setLayoutManager(linearLayoutManager);

}

mRecyclerView.smoothScrollToPosition(mAdapter.getItemCount()-1); //刪除此行。

並使用此:

mAdapter.notifyItemRangeInserted(mAdapter.getItemCount(), list.size() - 1);

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM