我正在撰写自定义BaseAdapter
(由Set
支持),我需要通过CharSequence
以外的其他内容过滤数据(价格范围,颜色等) 。
我查看了Filterable
界面和Filter
类,但Filter
中的所有方法都使用CharSequence
s。
那么,该怎么做?我应该将过滤器参数编码为CharSequence
(可能是JSON吗?),还是有更好的方法?
此外,convertResultToString
方法的优点是什么?因为我不希望结果为String
,而Object
来自Set
,因为我显示的信息更多,只有String
。< / p>
答案 0 :(得分:1)
您可以根据需要进行过滤,但需要编写一些代码。
在适配器中,为您的集创建另一个字段。它将是您实际显示的集合。这意味着在您的所有getCount
,getView
,getItemId
,getItem
方法中,您应该使用第二个集合(实际上是在适配器中的evrywhere)。默认情况下,它应与您的主要数据集相同。您的主要数据集将是mSet
和展示mDisplaySet
。
创建自定义过滤器方法。此方法将过滤放入第二组(实际显示的那个)第一组中与给定条件匹配的元素:
public void filter(Object condition) {
mDisplaySet = new Set<>();
for (Object object : mSet) {
if (object.match(condition) {
mDisplaySet.add(object);
}
}
notifyDataSetChanged();
}
答案 1 :(得分:1)
如果您实现了Filterable
和Filter
,并且由于您的适配器由一组元素支持,您可以忽略CharSequences
方法中的public FilterResults performFiltering(CharSequence prefix)
。在适配器内部,复制一组元素,这些元素将用于填充ListView
或您正在使用的任何元素。
之后,在performFiltering(...)
方法中,只需按您选择的条件删除元素:
private class ClientsFilter extends Filter {
@Override
public FilterResults performFiltering(CharSequence prefix) {
// Thats the result of our filtering process
FilterResults results = new FilterResults();
synchronized (mLock) {
// It's a good idea to work with a copy of the original set of elements, so we can reuse it every time we want to filter
ArrayList<Client> filteredClients = new ArrayList<>(originalClients);
for (int i = 0; i < filteredClient.size(); i++) {
if (// !fit my criteria) {
// We remove the clients that doesn`t fit the criteria, so only the good ones stay here
filteredClients.remove(i);
i--;
}
}
results.values = filteredClients;
results.count = filteredClients.size();
}
return results;
}
@Override
protected void publishResults(CharSequence prefix, FilterResults results) {
// And we use the filtered clients in our ListView, GridView or whatever
listViewClients= (ArrayList<Client>) results.values;
adapter.notifyDataSetChanged();
}
}
一些提示:
synchronized
内容,否则您会遇到一些有趣的错误(NPE没有任何明显原因造成的竞争条件)Filterable
过滤进程在后台进行,因此用户界面保持响应adapter.getFilter().filter()
方法,例如在EditText
答案 2 :(得分:1)
我仔细查看了你的问题,我将逐一回答。
1。那么,该怎么做?我应该将过滤器参数编码为CharSequence(可能是JSON吗?),还是有更好的方法?
我认为你不应该对它进行编码,只需按以下方式进行编码:
public class YourFilterObject {
String test1;
int test2;
}
private YourFilterObject yourFilterObject;
public TestAdapter setFilterObject(YourFilterObject object) {
this.yourFilterObject = object;
return this;
}
@Override
public Filter getFilter() {
return new Filter() {
@Override
protected FilterResults performFiltering(CharSequence charSequence) {
// use yourFilterObject here to filter your adapter
return null;
}
@Override
protected void publishResults(CharSequence charSequence, FilterResults filterResults) {
}
};
}
每当您想使用自定义参数(不仅仅是字符串)过滤适配器时,您都可以拨打电话YourAdapter.setFilterObject(object).getFilter().filter(null);
2。什么是convertResultToString方法适用于
实际上这个方法我只用于AutocompleteTextView
。当您在AutocompleteTextView
中输入内容(例如:name ...)时,它会显示filterResults
中要选择的对象列表。当您选择结果对象时,将调用convertResultToString
函数以在Text
中设置(显示)AutocompleteTextView
。如果您不重写此方法,则在选择对象后,AutocompleteTextView
将不会显示任何内容。
希望这有帮助。