CymChad / BaseRecyclerViewAdapterHelper

BRVAH:Powerful and flexible RecyclerAdapter
http://www.recyclerview.org/
MIT License
24.19k stars 5.14k forks source link

调用notifyDataSetChanged时,adapter.stateView的任何改变都不会生效 #3822

Closed liyuhaolol closed 6 months ago

liyuhaolol commented 7 months ago

代码如下

        b.btn3.setOnClickListener {
            mList.clear()
            adapter.stateView = errorView.root//无论先调用还是后调用,均不生效
            adapter.notifyDataSetChanged()
            //adapter.stateView = errorView.root
        }

使用的是最新的4.0.3版本,场景模拟,当list在加载中,有个默认的loadingView占位,或已有一些item数据。比如出现了错误,需要显示报错占位图时,也就是errorView,需要将list中的默认数据清除掉,也就是

mList.clear()
adapter.notifyDataSetChanged()

这时候将stateView替换为errorView是无论如何都无法实现的。Logcat也没有任何异常日志的输出。

请问这是一个BUG么?还是说我对这个默认占位图的功能理解出了问题。看demo也没看出个所以然来,因为demo并没有模拟原有数据,但后续刷新出错清除数据显示报错页面的范例。

lsiuhen commented 7 months ago

请问你有解决吗,我也遇见这个问题

liyuhaolol commented 7 months ago

请问你有解决吗,我也遇见这个问题

我要是知道怎么解决我还来问么,因为最近项目工作太忙,实在没空扒源码,看底层到底如何操作的。只是个人认为不应该如此,所以来提问。如果你着急非要短期解决这个需求,stateView使用loadingView,其他布局请使用多Type解决。

limuyang2 commented 7 months ago

“模拟原有数据,但后续刷新出错清除数据显示报错页面” 这个范例,在demo中有的,查看demo EmptyViewUseActivityreset() 方法。

总体来说,就是如下:

mAdapter.stateView = errorView.root  //设置状态布局
mAdapter.submitList(null) // 清空数据
liyuhaolol commented 7 months ago

“模拟原有数据,但后续刷新出错清除数据显示报错页面” 这个范例,在demo中有的,查看demo EmptyViewUseActivityreset() 方法。

总体来说,就是如下:

mAdapter.stateView = errorView.root  //设置状态布局
mAdapter.submitList(null) // 清空数据

感谢,已经找到对应的代码逻辑,并且在自己的demo里测试成功,但是依然没有解决我的疑惑。因为demo里使用的是adapter.notifyItemRangeRemoved(0,mList.size)这个方法来进行的UI更新,使用adapter.notifyDataSetChanged()则stateView将无法被修改。我再明确一下这个问题的复现流程,1楼说的不完整。

虽然后续无意义的adapter.notifyDataSetChanged()可以通过整理代码逐一去除(但很痛苦),但是就算代码重复调用通知一个RecyclerView进行无意义的操作,我认为也不应该会影响到本项目的stateView的刷新操作。毕竟无意义的调用adapter.notifyItemRangeRemoved(0,mList.size)时,stateView就可以正常刷新。我目前依然会认为调用adapter.notifyDataSetChanged()后无法修改stateView是个BUG

limuyang2 commented 6 months ago

已找到问题,notifyDataSetChanged()只会触发onBindViewHolder()方法

limuyang2 commented 6 months ago

请更新 4.1.3