我正在创建一个聊天应用程序。我试图使所有新消息都显示在屏幕上可见列表中当前最低的项目时,而不是当用户向上滚动时(如大多数聊天应用程序),出现在聊天应用程序的底部。截至目前,当屏幕上仍然有未使用的空间时,我已经可以使用此功能,但是当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);
答案 0 :(得分:4)
我最终添加了一个检查以查看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);
}
答案 1 :(得分:0)
mRecyclerView.smoothScrollToPosition(mAdapter.getItemCount()-1);
//删除此行。
并使用它:
mAdapter.notifyItemRangeInserted(mAdapter.getItemCount(), list.size() - 1);