Error using notifyDataSetChanged in android array adapter

前端 未结 2 392

11-06 19:52:25.958: E/AndroidRuntime(29609): java.lang.IllegalStateException: The content of the adapter has changed but ListView did not receive a notifi

相关标签:
2条回答
  • 2020-12-30 04:04

    Try this (just a guess):

    @Override
        public Filter getFilter() {
            Filter filter = new Filter() {
                @Override
                protected FilterResults performFiltering(CharSequence constraint) {
                    FilterResults filterResults = new FilterResults();
                    if (constraint != null) {
                        ArrayList list = autocomplete(constraint.toString());
                        if (list != null) {
                            filterResults.values = list;
                            filterResults.count = list.size();
                        }
                    }
                    return filterResults;
                }
    
                @Override
                protected void publishResults(CharSequence constraint, FilterResults results) {
                    if (results != null && results.count > 0) {
                        //change the underlying data immediately before notifying UI                        
                        resultList = (ArrayList)results.values; 
                        notifyDataSetChanged();
                    }
                    else {
                        notifyDataSetInvalidated();
                    }
                }};
            return filter;
        }
    
    0 讨论(0)
  • 2020-12-30 04:24

    The Filter's performFiltering() method runs on a background thread and from that method you're changing the resultList on which your adapter is based. If you change that list of data and in that time the ListView access the adapter it will see that something has changed without its knowledge(and it will not be happy). You should avoid using the resultList in the performFiltering method and simply create a new temporary list:

    // in the performFiltering method which runs on a background thread:
    @Override
    protected FilterResults performFiltering(CharSequence constraint) {
         FilterResults filterResults = new FilterResults();
         ArrayList<String> queryResults;
         if (constraint != null && constraint.length() > 0) {
             queryResults = autocomplete(constraint);
         } else {
             queryResults = new ArrayList<String>(); // empty list/no suggestions showing if there's no valid constraint
         }
         filterResults.values = queryResults;
         filterResults.count = queryResults.size();
         return filterResults; // ## Heading ##
    }
    
    private List<String> autocomplete(String input) {
       // don't use the here the resultList List on which the adapter is based!
       // some custom code to get items from http connection
         ArrayList<String> queryResults = new ArrayList<String>(); // new list
         queryResults.add("Some String");
         return queryResults;
    }
    
    @Override
    protected void publishResults(CharSequence constraint, FilterResults results) {
         // update the data with the new set of suggestions
         resultList = (ArrayList<String>)results.values;
         if (results.count > 0) {
             notifyDataSetChanged();
         } else {
             notifyDataSetInvalidated();
         }
    }
    
    0 讨论(0)
提交回复
热议问题