SearchView过滤和设置建议 [英] SearchView Filtering and Set Suggestions

查看:111
本文介绍了SearchView过滤和设置建议的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对使用SearchView非常陌生.我需要具有ActionBar且具有Search的功能.当我单击搜索"时,建议应显示在搜索"字段下方的列表中.

I am very new to using SearchView. I need a functionality where I have an ActionBar for which I have Search. When I click on Search, the Suggestions should be displayed in a List below the Search field.

我到目前为止所做的事情: 在menu.xml中添加了搜索,并在onCreateOptionsMenu()中编写了代码,在此我初始化了SearchView,并且setSuggestionsAdapter也实现了setOnQueryTextListener.

What I have done so far : Added search in menu.xml and wrote the code in onCreateOptionsMenu() where I initialize the SearchView and setSuggestionsAdapter also implement setOnQueryTextListener.

结果:我进入应用程序,单击搜索"图标,它会显示建议.我输入一个字母,以找出匹配的字母.我输入第二个字母,它没有显示任何建议.另外,我关闭了搜索视图,然后再次打开它,打开了键盘,但是未显示列表中的建议".

Result: I enter the app, click on search Icon, it shows the suggestions. I type a letter it sorts out the matched ones. I type 2nd letter it shows no suggestions. Also I close the searchview and open it again, the Keyboard is opened, but the Suggestions in List is not shown.

我需要什么:根据用户输入的字符进行过滤.即使是多个字符也是如此. 始终显示建议,即默认包含所有列表项的建议,或者显示用户键入时排序的建议.

What I need : Filter according to user entered characters. Even if it's more than one character. Always show suggestions either default one with all list items or the ones that's sorted when user type.

我已经在Android的SearchView类中看到过,他们将文本设置为空,并且还忽略了建议".但是我不要这个.

I have seen in the SearchView class of Android, they are setting the text to empty and also dismissing the Suggestions. But I don't want this.

我被困在这里,不知道如何进行.请帮我. 这是我的适配器代码:

I am stuck here and don't know how to proceed. Please help me. Here is my Adapter Code:

public class ExampleAdapter extends CursorAdapter implements Filterable {

    private ArrayList<String> items;
    private ArrayList<String> orig;

    public ExampleAdapter(Context context, Cursor cursor,
            ArrayList<String> items) {
        super(context, cursor, false);
        this.items = new ArrayList<String>();
        this.items = items;
        orig = new ArrayList<String>();
        orig.addAll(items);
    }

    @Override
    public int getCount() {
        return items.size();
    }

    @Override
    public Filter getFilter() {
        return new Filter() {

            @Override
            protected FilterResults performFiltering(CharSequence constraint) {
                constraint = constraint.toString().toLowerCase();
                FilterResults result = new FilterResults();

                if (constraint != null
                        && constraint.toString().length() > 0) {
                    List<String> founded = new ArrayList<String>();
                    for (int i = 0, l = orig.size(); i < l; i++) {
                        if (orig.get(i)
                                .toString()
                                .toLowerCase()
                                .startsWith(
                                        constraint.toString().toLowerCase()))
                            founded.add(orig.get(i));
                    }

                    result.values = founded;
                    result.count = founded.size();
                } else {
                    synchronized (this) {
                        result.values = orig;
                        result.count = orig.size();
                    }

                }
                return result;

            }

            @Override
            protected void publishResults(CharSequence constraint,
                    FilterResults results) {

                items.clear();
                items = new ArrayList<String>();
                items = (ArrayList<String>) results.values;
                notifyDataSetChanged();

            }

        };
    }

    @Override
    public void bindView(View view, Context context, Cursor cursor) {
        ViewHolder holder = (ViewHolder) view.getTag();
        holder.textView.setText(items.get(cursor.getPosition()));
    }

    public class ViewHolder {
        public TextView textView;
    }

    @Override
    public View newView(Context context, Cursor cursor, ViewGroup parent) {
        ViewHolder holder = new ViewHolder();
        View v = null;

        LayoutInflater inflater = (LayoutInflater) context
                .getSystemService(Context.LAYOUT_INFLATER_SERVICE);

        v = inflater.inflate(R.layout.item, parent, false);
        holder.textView = (TextView) v.findViewById(R.id.text);

        v.setTag(holder);
        return v;

    }
}

活动中与我具有searchview的菜单相关的代码:

Code in my Activity related to Menu where I have searchview :

private String[] columns = new String[] { "_id", "text" };
    private SearchView searchView;
    private SearchManager manager;
    private ExampleAdapter aptr;

@Override
    protected void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_home);

    manager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);

}

@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.main, menu);
        MenuItem searchItem = menu.findItem(R.id.action_search);
        searchView = (SearchView) MenuItemCompat.getActionView(searchItem);
        setSearchTextColour(searchView);
        setSearchIcons(searchView);
        searchView.setQueryHint(Html.fromHtml("<font color = #ffffff>"
                + getResources().getString(R.string.search_store) + "</font>"));
        searchView.setSearchableInfo(manager
                .getSearchableInfo(getComponentName()));
        Object[] temp = new Object[] { 0, "default" };
        final MatrixCursor cursor = new MatrixCursor(columns);
        for (int i = 0; i < alStoreNames.size(); i++) {
            temp[0] = i;
            temp[1] = alStoreNames.get(i);
            cursor.addRow(temp);
        }
        aptr = new ExampleAdapter(MainActivity.this, cursor, alStoreNames);
        searchView.setSuggestionsAdapter(aptr);

    searchView.setOnQueryTextListener(new OnQueryTextListener() {

        @Override
        public boolean onQueryTextSubmit(String arg0) {
            if (!TextUtils.isEmpty(arg0)) {
                aptr.getFilter().filter(arg0.toString());
            }
            return true;
        }

        @Override
        public boolean onQueryTextChange(String arg0) {
            return false;
        }
    });

    searchView.setOnSuggestionListener(new OnSuggestionListener() {

            @Override
            public boolean onSuggestionSelect(int arg0) {
                return false;
            }

            @Override
            public boolean onSuggestionClick(int position) {
                String suggestion = getSuggestion(position);
                db.openDatabase();
                String studentId = db.getStudentIdFromName(suggestion);
                String studentImg = db.getStudentImgFromName(suggestion);
                db.closeDatabase();
                Log.e("Sp", " On Click name -> " + aptr.getItem(position).toString() + " : "
                         + aptr.getCursor().getString(0) + " : " + suggestion);
                Intent i = new Intent(MainActivity.this,
                        ExampleActivity.class);
                i.putExtra("studentId", studentId);
                i.putExtra("studentName", suggestion);
                i.putExtra("studentImg", studentImg);
                startActivity(i);
                return true;
            }
        });

    return true;
}

private String getSuggestion(int position) {
    Cursor cursor = (Cursor) searchView.getSuggestionsAdapter().getItem(
            position);
    String suggest1 = cursor.getString(cursor.getColumnIndex("text"));
    return suggest1;
}

private void setSearchTextColour(SearchView searchView) {
        Field qTextField;
        try {
            qTextField = SearchView.class.getDeclaredField("mQueryTextView");
            qTextField.setAccessible(true);
            SearchAutoComplete searchPlate = (SearchAutoComplete) qTextField
                    .get(searchView);
            searchPlate.setTextColor(getResources().getColor(R.color.white));
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        }
        catch (IllegalArgumentException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
    }

private void setSearchIcons(SearchView searchView) {
    try {
        Field searchField = SearchView.class
                .getDeclaredField("mCloseButton");
        searchField.setAccessible(true);
        ImageView closeBtn = (ImageView) searchField.get(searchView);
        closeBtn.setImageResource(R.drawable.close);

        Field searchField1 = SearchView.class
                .getDeclaredField("mSearchButton");
        searchField1.setAccessible(true);
        ImageView searchButton = (ImageView) searchField1.get(searchView);
        searchButton.setImageResource(R.drawable.ic_action_search);

    } catch (NoSuchFieldException e) {
        Log.e("SearchView", e.getMessage(), e);
    } catch (IllegalAccessException e) {
        Log.e("SearchView", e.getMessage(), e);
    }
}

推荐答案

在我看来,部分问题在于缺少getItem()方法.

It seems to me that part of the problem is in the absence of the getItem() method.

如果您查看游标适配器源代码,则getItem()将从游标而不是从筛选列表中获取数据,您希望它从筛选列表中获取数据!

If you look at the cursor adapter source code the getItem() will get the data from the cursor, and not from your filtered list, you want it to get the data from your filtered list!

尝试一下:

@Override
 public Object getItem(int position) {
    if (position < items.size()) {            
        return items.get(position);
    } else {
        return null;
    }
}

我忘了添加,您还需要更改此内容:

i forgot to add, you also need to change this:

private String getSuggestion(int position) {
    String suggest1 = (String) searchView.getSuggestionsAdapter().getItem(position);    
    return suggest1;
}

要关闭所有内容,请首先将其添加到createOptions菜单:

And to close everything,first add this to createOptions menu:

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    getMenuInflater().inflate(R.menu.main, menu);
    MenuItem searchItem = menu.findItem(R.id.action_search);
    searchView = (SearchView) MenuItemCompat.getActionView(searchItem);

    searchView.setIconifiedByDefault(true); //this line

    ...

然后将其添加到onSuggestionClick:

then add this to onSuggestionClick:

 @Override
 public boolean onSuggestionClick(int position) {
   String suggestion = getSuggestion(position);
   db.openDatabase();
   String studentId = db.getStudentIdFromName(suggestion);
   String studentImg = db.getStudentImgFromName(suggestion);
   db.closeDatabase();
   Log.e("Sp", " On Click name -> " + aptr.getItem(position).toString() + " : "
        + aptr.getCursor().getString(0) + " : " + suggestion);

   searchView.setIconified(true);//this line


   Intent i = new Intent(MainActivity.this,ExampleActivity.class);
   i.putExtra("studentId", studentId);
   i.putExtra("studentName", suggestion);
   i.putExtra("studentImg", studentImg);
   startActivity(i);
   return true;
}

一些解释.调用setIconified时,它会清除searchView的文本或将其折叠(取决于默认状态).在那里,我们将默认状态设置为图标化,因此,当我们调用setIconified方法时,它将清除文本并折叠视图!

A bit of an explanation. When you call setIconified it will either clear the text of your searchView or collapse it, depending on the default state. What we did there was set the default state to iconified so when we call the setIconified method it will clear the text and collapse the view!

这篇关于SearchView过滤和设置建议的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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