首页 > 解决方案 > 添加一个项目会破坏 getFilter() 方法

问题描述

问题:添加列表项会阻止过滤方法工作。否则过滤器正常工作。

预期:项目和数据库已从添加项目和筛选方法正确更新。

测试:

  1. 当前列表上的过滤器有效并应用布局。
  2. 过滤列表上的过滤器有效并应用布局。
  3. 没有约束的过滤器会加载完整列表并应用布局。
  4. 在过滤器工作之前添加项目并应用布局。
  5. 在过滤器之后添加项目并应用布局。
  6. 添加项目后过滤无法过滤结果并且不会对布局应用任何更改。没有提供运行时错误。

可能的解决方案:我以为我错过了对项目列表的分配以获取列表的更新版本。检查后似乎 add item 和 filter 方法都在获取更新的列表。我开始认为我不了解过滤器方法的工作原理,并且我缺少过滤器需要刷新的方法或行。将不胜感激有关如何找到我所缺少的建议。

private void addProjectItem() {
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        View view = getLayoutInflater().inflate(R.layout.project_add_layout, null);

        final EditText title = view.findViewById(R.id.addProjectTitle);
        final EditText description = view.findViewById(R.id.addProjectDescription);

        builder.setNegativeButton(
                android.R.string.cancel,
                (dialog, which) -> dialog.cancel()
        );

        builder.setPositiveButton(
                android.R.string.ok,
                (dialog, which) -> {
                    if (!title.getText().toString().isEmpty() && !description.getText().toString().isEmpty()) {
                        ProjectItem item = new ProjectItem(
                                title.getText().toString(),
                                description.getText().toString(),
                                appDataManager.getUid(),
                                false
                        );

                        projectListManager.addItem(item);
                        adapter.updateItems(projectListManager.getList());
                    } else {
                        Toast.makeText(SecondActivity.this, projectAddError, Toast.LENGTH_SHORT).show();
                    }
                }
        );

        builder.setView(view);
        builder.show();
    }

    private class ProjectItemAdapter extends ArrayAdapter<ProjectItem> implements Filterable {
        private Context context;
        private List<ProjectItem> items;

        private ImageButton projectCompleteButton;
        private ImageButton projectDescriptionButton;
        private TextView itemTitle;
        private ImageButton projectJoinButton;

        private ProjectItemAdapter( Context context, List<ProjectItem> items) {
            super(context, -1, items);

            this.context = context;
            this.items = items;
        }

        @NonNull
        @Override
        public Filter getFilter() {
            return projectFilter;
        }

        private final Filter projectFilter = new Filter() {

            @Override
            protected FilterResults performFiltering(CharSequence constraint) {
                FilterResults results = new FilterResults();

                List<ProjectItem> found = new ArrayList<>();

                if(constraint == null || constraint.length() == 0) {
                    found.addAll(projectListManager.getList());
                } else {
                    String filterPattern = constraint.toString().toLowerCase().trim();

                    for(ProjectItem item : items){
                        if(item.getTitle().toLowerCase().contains(filterPattern)) {
                            found.add(item);
                        }
                    }
                }

                results.values = found;
                results.count = found.size();
                return results;
            }

            @Override
            protected void publishResults(CharSequence constraint, FilterResults results) {
                clear();
                addAll((List)results.values);
                notifyDataSetChanged();
            }
        };

        public void updateItems(List<ProjectItem> items) {
            this.items = items;
            notifyDataSetChanged();
        }
        
        @Override
        public int getCount() {
            return items.size();
        }

        @NonNull
        @Override
        public View getView(int position, View convertView, @NonNull ViewGroup parent) {
            // Removed as there is nothing that manipulates the list item.
            return convertView;
        }
    }
}

标签: javaandroidlistviewfilteradapter

解决方案


问题在于发布结果没有引用项目列表并将结果正确转换为集合。

解决方案:

@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
    items.clear();

    items.addAll((Collection<? extends ProjectItem>) results.values);

    notifyDataSetChanged();
}

推荐阅读