Android RecyclerView:notifyDataSetChanged()IllegalStateException [英] Android RecyclerView : notifyDataSetChanged() IllegalStateException

查看:360
本文介绍了Android RecyclerView:notifyDataSetChanged()IllegalStateException的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试使用notifyDataSetChanged()更新recycleview的项目.

I'm trying to update the items of a recycleview using notifyDataSetChanged().

这是我的recycleview适配器中的onBindViewHolder()方法.

This is my onBindViewHolder() method in the recycleview adapter.

@Override
public void onBindViewHolder(ViewHolder viewHolder, int position) {

     //checkbox view listener
    viewHolder.getCheckbox().setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {
        @Override
        public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {

            //update list items
            notifyDataSetChanged();
        }
    });
}

我想要做的是在选中复选框后更新列表项.但是,我得到了一个非法异常:"Cannot call this method while RecyclerView is computing a layout or scrolling"

What I want to do is update the list items, after I check a checkbox. I get an illegal exception though: "Cannot call this method while RecyclerView is computing a layout or scrolling"

java.lang.IllegalStateException: Cannot call this method while RecyclerView is computing a layout or scrolling
    at android.support.v7.widget.RecyclerView.assertNotInLayoutOrScroll(RecyclerView.java:1462)
    at android.support.v7.widget.RecyclerView$RecyclerViewDataObserver.onChanged(RecyclerView.java:2982)
    at android.support.v7.widget.RecyclerView$AdapterDataObservable.notifyChanged(RecyclerView.java:7493)
    at android.support.v7.widget.RecyclerView$Adapter.notifyDataSetChanged(RecyclerView.java:4338)
    at com.app.myapp.screens.RecycleAdapter.onRowSelect(RecycleAdapter.java:111)

我也使用了notifyItemChanged(),同样的例外.有什么秘密方法可以更新以通知适配器某些更改吗?

I also used notifyItemChanged(), same exception. Any secret way to update to notify the adapter that something changed?

推荐答案

您应将方法'setOnCheckedChangeListener()'移至ViewHolder,后者是适配器上的内部类.

You should move method 'setOnCheckedChangeListener()' to ViewHolder which is inner class on your adapter.

onBindViewHolder()不是初始化ViewHolder的方法. 此方法是刷新每个回收站项目的步骤. 呼叫notifyDataSetChanged()时,onBindViewHolder()将被称为每个项目的次数.

onBindViewHolder() is not a method that initialize ViewHolder. This method is step of refresh each recycler item. When you call notifyDataSetChanged(), onBindViewHolder() will be called as the number of each item times.

因此,如果您notifyDataSetChanged()放入onCheckChanged()并在onBindViewHolder()中初始化checkBox,则由于循环方法调用,您将获得IllegalStateException.

So If you notifyDataSetChanged() put into onCheckChanged() and initialize checkBox in onBindViewHolder(), you will get IllegalStateException because of circular method call.

单击复选框-> onCheckedChanged()-> notifyDataSetChanged()-> onBindViewHolder()->设置复选框-> onChecked ...

click checkbox -> onCheckedChanged() -> notifyDataSetChanged() -> onBindViewHolder() -> set checkbox -> onChecked...

简单来说,您可以通过在适配器中放置一个标志来解决此问题.

Simply, you can fix this by put one flag into Adapter.

尝试一下

private boolean onBind;

public ViewHolder(View itemView) {
    super(itemView);
    mCheckBox = (CheckBox) itemView.findViewById(R.id.checkboxId);
    mCheckBox.setOnCheckChangeListener(this);
}

@Override
public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
    if(!onBind) {
        // your process when checkBox changed
        // ...

        notifyDataSetChanged();
    }
}

...

@Override
public void onBindViewHolder(YourAdapter.ViewHolder viewHolder, int position) {
    // process other views 
    // ...

    onBind = true;
    viewHolder.mCheckBox.setChecked(trueOrFalse);
    onBind = false;
}

这篇关于Android RecyclerView:notifyDataSetChanged()IllegalStateException的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆