如何创建"搜索"上下文操作栏中的字段?

时间:2014-10-16 23:18:30

标签: android android-actionbar contextual-action-bar

我有一个ActionBar的活动。其中一个选项是搜索文档(不一定是本地文档)。我想使用具有以下项目的上下文操作栏(CAB):

  • 编辑字段 - 用户输入要搜索的文本的位置
  • 上一个按钮 - 移至与搜索匹配的上一个项目
  • 下一个按钮 - 移至与搜索匹配的下一个项目

我想使用CAB有几个原因。首先,我希望用户选择一个选项,该选项将调出上面定义的CAB。当用户完成搜索时,他们选择完成按钮,ActionBar返回到先前状态。

这是问题所在。我无法让搜索项在扩展状态下显示在我的CAB中。注意:我尝试修改的活动不是主要活动,而是用户根据特定事件启动的活动。加载此活动后,用户可能会也可能不会决定使用我正在描述的“搜索”功能。我也不希望Android进行搜索。我有一个API,可以搜索我想要的结果,并允许我导航到上一个/下一个搜索结果。

我的CAB代码(正确调用)是:

     protected ActionMode mActionModeSearch;
private ActionMode.Callback mActionModeSearchCallback = new ActionMode.Callback()
{
    @Override
    public boolean onCreateActionMode(ActionMode actionMode, Menu menu)
    {
        actionMode.getMenuInflater().inflate(R.menu.pdf_menu_search, menu);
        // Associate searchable configuration with the SearchView
        SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
        SearchView searchView = (SearchView) menu.findItem(R.id.pdf_menu_search_item).getActionView();
        searchView.setSearchableInfo(searchManager.getSearchableInfo(getComponentName()));
        searchView.setIconifiedByDefault(false);
        searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener()
        {
            @Override
            public boolean onQueryTextSubmit(String s)
            {
                return false;
            }

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

    @Override
    public boolean onPrepareActionMode(ActionMode actionMode, Menu menu)
    {
        return false;
    }

    @Override
    public boolean onActionItemClicked(ActionMode actionMode, MenuItem menuItem)
    {
        switch(menuItem.getItemId())
        {
            case R.id.pdf_menu_search_prev:
                findPrevSearchResult();
                return true;
            case R.id.pdf_menu_search_next:
                findNextSearchResult();
                return true;
            default:
                return false;
        }
    }

    @Override
    public void onDestroyActionMode(ActionMode actionMode)
    {
        //resetHideToolbarsTimer();
    }
};

CAB菜单代码为:

 <?xml version="1.0" encoding="utf-8"?>
 <menu xmlns:android="http://schemas.android.com/apk/res/android"
  xmlns:app="http://schemas.android.com/apk/res-auto">
<group android:id="@+id/group_search_mode">
    <item
        android:id="@+id/pdf_menu_search_item"
        android:title="@string/search"
        android:icon="@drawable/ic_pdf_action_search"
        app:showAsAction="collapseActionView|ifRoom"
        app:actionViewClass="android.support.v7.widget.SearchView"/>
    <item
        android:id="@+id/pdf_menu_search_prev"
        android:title="@string/search_prev"
        android:icon="@drawable/ic_pdf_action_search_prev"
        app:showAsAction="ifRoom" />
    <item
        android:id="@+id/pdf_menu_search_next"
        android:title="@string/search_next"
        android:icon="@drawable/ic_pdf_action_search_next"
        app:showAsAction="ifRoom" />
</group>

我也在AndroidManifest.xml中更改了我的活动定义,虽然我不确定这是否是必需的:

         <activity
        android:name="com.myapp.myActivity"
        android:label="@string/app_name">
        <intent-filter>
            <action android:name="android.intent.action.SEARCH" />
        </intent-filter>
        <meta-data
            android:name="android.app.default_searchable"
            android:value="com.myapp.myActivity" />
        <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchable" />
    </activity>

当我运行应用程序时,活动正确加载。当用户选择搜索选项时,我加载CAB,它似乎运行正常。我已逐步完成代码以确保onCreateActionMode按预期运行。但是,我所看到的只是搜索的图标,下一个和上一个,使用“完成”按钮。当我触摸“搜索”图标时,它什么也没做。在CAB中没有创建文本字段供我输入文本。我究竟做错了什么????

显示CAB即将发布的屏幕截图。如您所见,搜索图标显示但在我按下时没有做任何事情。我真正需要的是默认情况下显示搜索编辑框。

enter image description here

2 个答案:

答案 0 :(得分:9)

首先,我们应为所有菜单项always设置app:showAsAction值:

<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:app="http://schemas.android.com/apk/res-auto">
    <group android:id="@+id/group_search_mode">
        <item
            android:id="@+id/pdf_menu_search_item"
            android:icon="@drawable/ic_pdf_action_search"
            android:title="@string/search"
            app:actionViewClass="android.support.v7.widget.SearchView"
            app:showAsAction="always"/>
        <item
            android:id="@+id/pdf_menu_search_prev"
            android:icon="@drawable/ic_pdf_action_search_prev"
            android:title="@string/search_prev"
            app:showAsAction="always"/>
        <item
            android:id="@+id/pdf_menu_search_next"
            android:icon="@drawable/ic_pdf_action_search_next"
            android:title="@string/search_next"
            app:showAsAction="always"/>
    </group>
</menu>

辅助,在这种情况下,我们无需为Activity设置意图过滤器,也无需为SearchView设置可搜索信息。

AndroidManifest.xml中此活动的定义:

<activity
    android:name="com.myapp.myActivity"
    android:label="@string/app_name" />

ActionMode.Callback实施:

private ActionMode.Callback mActionModeSearchCallback = new ActionMode.Callback() {

    private SearchView mSearchView;

    @Override
    public boolean onCreateActionMode(ActionMode actionMode, Menu menu) {
        actionMode.getMenuInflater().inflate(R.menu.home, menu);
        mSearchView = (SearchView) MenuItemCompat.getActionView(menu.findItem(R.id.pdf_menu_search_item));
        mSearchView.setIconifiedByDefault(false);
        mSearchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
            @Override
            public boolean onQueryTextSubmit(String s) {
                return false;
            }

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

    @Override
    public boolean onPrepareActionMode(ActionMode actionMode, Menu menu) {
        mSearchView.requestFocus();
        return true;
    }

    @Override
    public boolean onActionItemClicked(ActionMode actionMode, MenuItem menuItem) {
        switch (menuItem.getItemId()) {
            case R.id.pdf_menu_search_prev:
                findPrevSearchResult();
                return true;
            case R.id.pdf_menu_search_next:
                findNextSearchResult();
                return true;
            default:
                return false;
        }
    }

    @Override
    public void onDestroyActionMode(ActionMode actionMode) {

    }
};

我刚刚在三个4.0+设备上尝试了这个代码,它完全正常工作。但我没有测试较低操作系统版本的设备。

希望它对你有所帮助。

答案 1 :(得分:2)

我在CAB中遇到问题searchView 所以我在manu项目中设置布局(使用edittext),它给我与searchview相同的视图 试试这个我希望它适合你

菜单/ search.xml

<menu xmlns:android="http://schemas.android.com/apk/res/android" >

    <item
        android:id="@+id/edt_mySearch"
        android:actionLayout="@layout/search_bar"
        android:enabled="true"
        android:showAsAction="always"
        android:visible="true"/>

</menu>

layout / search _bar.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    >


    <EditText 
        android:layout_alignParentLeft="true"
        android:id="@+id/edt_search"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:hint=" Search..."
        />


</RelativeLayout>

和myAction模式

mActionModeCallback = new ActionMode.Callback() {

            @Override
            public boolean onCreateActionMode(ActionMode mode, Menu menu) {
                // mode.setTitle("Demo");
                getSupportMenuInflater().inflate(R.menu.search, menu);
                RelativeLayout m = (RelativeLayout) menu.findItem(
                        R.id.edt_mySearch).getActionView();
                EditText mSearchView = (EditText) m
                        .findViewById(R.id.edt_search);

                mSearchView.addTextChangedListener(new TextWatcher() {

                    @Override
                    public void onTextChanged(CharSequence s, int start,
                            int before, int count) {
                        // TODO Auto-generated method stub

                    }

                    @Override
                    public void beforeTextChanged(CharSequence s, int start,
                            int count, int after) {

                    }

                    @Override
                    public void afterTextChanged(Editable s) {
                        // search here
                    }
                });
                return true;
            }

            @Override
            public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
                // TODO Auto-generated method stub
                return false;
            }

            @Override
            public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
                return false;
            }

            @Override
            public void onDestroyActionMode(ActionMode mode) {
            }

        };