如何解决在 RecyclerView 中移动项目会使视图中的项目翻倍
我正在使用 RecyclerView 在消息应用中构建联系人列表 (ArrayList)。
当联系人更新时,我想将该用户移动到列表顶部,而列表中的所有其他项目向下移动一级。
我正在使用 Firestore 获取用户列表。
DocumentChange.Type.MODIFIED -> {
val matchThatChanged = dc.newIndex
matchesArrayList[matchThatChanged] = ChatMatchListMatch(
matchUserID)
adapter.notifyItemChanged(matchThatChanged) //Ensures change is visible immediately
val fromPosition = matchesArrayList.indexOfFirst {
it!!.matchUserID == matchUserID
}
Log.d(TAG,"From position A: $matchThatChanged")
if (fromPosition != 0) {
adapter.moveMatchToTop(
fromPosition,ChatMatchListMatch(
matchUserID
)
)
}
}
在此处的日志中,当我迈出第一步时,它会正确输出 1。但是,此后当我尝试更新其他用户时它输出 0?这是不正确的。被推下的用户应该不再是 0,它应该是 1。因为它现在错误地在 0,它没有运行代码(这不是问题。问题是不应该是 0第一名)。
这是我的适配器中的代码:
override fun onCreateViewHolder(parent: ViewGroup,viewType: Int): RecyclerView.ViewHolder {
val view: View = LayoutInflater.from(parent.context)
.inflate(R.layout.chat_matchlist_item,parent,false)
return CustomViewHolder(view)
}
// Passes the ContactListMatch object to a ViewHolder so that the contents can be bound to UI.
override fun onBindViewHolder(holder: RecyclerView.ViewHolder,position: Int) {
val contactListMatch = mMatchesArrayList[position]
(holder as CustomViewHolder).bind(contactListMatch)
}
fun moveMatchToTop(fromPosition: Int,chatMatchListMatch: ChatMatchListMatch) {
mMatchesArrayList.removeAt(fromPosition)
notifyItemChanged(fromPosition)
notifyItemRemoved(fromPosition)
mMatchesArrayList.add(0,chatMatchListMatch)
notifyItemInserted(0)
notifyItemChanged(0)
notifyItemChanged(1)
}
我必须开始的清单是:
当我只更新底部用户 (2) 时,它显示正确(将用户 2 移动到顶部,将另一个用户向下移动):
我现在尝试再次更新原始用户 1,我希望它再次出现在顶部,如下所示:
但我得到了这个:
解决方法
我想出了解决办法。我不得不进行一些更改,但我会尽力让这些更改对可能遇到类似问题的其他人有所帮助:
我在 Firestore 中使用了一个索引,并使用了两个“orderby”查询来按照我想要的顺序获取列表:
myCollectionRef
.orderBy("unread",Query.Direction.DESCENDING)
.orderBy("timeStamp",Query.Direction.DESCENDING)
.addSnapshotListener
然后在 case 下修改:
DocumentChange.Type.MODIFIED -> {
我必须获取旧索引并更改项目的新索引。当我获得旧索引时(通过遍历我的列表以使用 for 循环查找它),我确保从列表中删除该项目并通知我的适配器我删除了该项目:
val newIndex = dc.newIndex
var oldIndex = -1
for (i in myList.indices.reversed()) {
if (myList[i]!!.IDnumber == userID) {
oldIndex = i
myList.removeAt(oldIndex)
adapter.notifyItemRemoved(oldIndex)
}
}
然后我必须将更改后的项目重新添加到我的列表中的正确位置。由于我有新索引,这很容易。我还将更改通知我的适配器:
myList.add(
newIndex,MySpecialItem(
userID!!,userImageOrWhatever!!
)
)
adapter.notifyItemInserted(newIndex)
就是这样。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。