Android 动态设置搜索提示

Android 动态设置搜索提示,android,android-searchmanager,Android,Android Searchmanager,有人知道如何动态设置android搜索对话框提示吗? I don’我没有试着做像这样的事情: <?xml version="1.0" encoding="utf-8"?> <searchable xmlns:android="http://schemas.android.com/apk/res/android" android:label="@string/search_label" android:hint="@string/search_hint" android:i

有人知道如何动态设置android搜索对话框提示吗? I don’我没有试着做像这样的事情:

<?xml version="1.0" encoding="utf-8"?>
<searchable xmlns:android="http://schemas.android.com/apk/res/android"
 android:label="@string/search_label"
 android:hint="@string/search_hint"
 android:id="@+id/search_dialog_text">
</searchable>
但文本等于空


所以期待你的建议。谢谢。

这感觉很粗糙,但对我来说很有用-不是真正的动态,但可以在我需要的两个搜索提示之间交替使用:

  • 我创建了第二个searchable.xml(如中所述),名为searchable 2.xml,并定义了第二个搜索提示
  • 我创建了一个从原始活动扩展而来的虚拟活动,并且没有覆盖任何内容
  • 在清单中,虚拟活动与新的searchable2.xml关联:

    <activity android:name=".MainActivity">
        <intent-filter>
            <action android:name="android.intent.action.VIEW" />
            <action android:name="android.intent.action.SEARCH" />
        </intent-filter>
        <meta-data android:name="android.app.searchable"
            android:resource="@xml/searchable"/>
    </activity>
    
    <activity android:name=".DummyActivity">
        <intent-filter>
            <action android:name="android.intent.action.VIEW" />
            <action android:name="android.intent.action.SEARCH" />
        </intent-filter>
        <meta-data android:name="android.app.searchable"
            android:resource="@xml/searchable2"/>
    </activity>
    
    
    
  • 在“MainActivity”中,我覆盖了“onSearchRequested()”以引用适当的可搜索活动:

    
    公共布尔值onSearchRequested()
    {
    SearchManager SearchManager=(SearchManager)getSystemService(Context.SEARCH_SERVICE);
    if(searchManager!=null) { //使用适当的可搜索活动开始搜索 //因此,我们在搜索对话框中获得了正确的搜索提示 如果(/*您的情况在此*/) startSearch(null,false,新组件名(this,MainActivity.class),null,false); 其他的 startSearch(null,false,新组件名(this,DummyActivity.class),null,false)

    返回true; } 返回false; }
  • 讨厌。但绝望的时刻需要采取绝望的措施


    好的,从Android源代码来看,这个类只用于查找元数据,但是如果有人知道不同的情况,请告诉我。

    看起来你就快到了

    SearchDialog
    source执行此操作以获得自动完成的可编辑文件

    mSearchAutoComplete = (SearchAutoComplete) findViewById(com.android.internal.R.id.search_src_text);
    
    (注意,
    SearchAutoComplete
    类是
    AutoCompleteTextView
    的一个子类)

    他们在声明中添加了一个注释

    注意:系统使用此文件实例化SearchableInfo对象,但您不能在运行时自己创建此对象,您必须用XML声明可搜索配置


    因此,您的问题的答案似乎是您无法动态设置搜索对话框提示。

    我使用OnActionExpandListener和自定义actionView通过ABS实现了这一点,例如:

    menu.add("Search")
    .setActionView(R.layout.collapsible_edittext)
    .setOnActionExpandListener(new MenuItem.OnActionExpandListener()
    {
        @Override
        public boolean onMenuItemActionExpand(MenuItem item) {
            ((EditText) item.getActionView()).setHint("Your custom text here");
            return true;
        }
    
        @Override
        public boolean onMenuItemActionCollapse(MenuItem item) {
            return true;
        }
    });
    
    使用可折叠的_edittext.xml:

    <EditText
        xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:textColor="@color/search_fg"
        android:background="@drawable/textfield_default_holo_light"
        android:hint="[will be replaced at runtime]"/>
    

    感谢村上春树先生的想法,我已经实现了相同的概念来执行切换搜索,根据我的观点,这不是一种黑客行为,而是OOPs的美妙之处。下面的程序在操作栏中有一个切换图标,用于在搜索提示之间切换

  • RestaurantListingActivity.java

    public class RestaurantListingActivity extends BaseMainActivity implements
    TabListener {
    private boolean isRestaurantSearch = true;
    private SearchManager searchManager;
    private SearchView searchView;
    
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        ActionBar aBar = getActionBar();
        aBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
        aBar.addTab(aBar.newTab().setText("Place Order").setTabListener(this));
        aBar.addTab(aBar.newTab().setText("My Account").setTabListener(this));
        aBar.addTab(aBar.newTab().setText("Favorite").setTabListener(this));
        aBar.addTab(aBar.newTab().setText("Vendor Portal").setTabListener(this));
    }
    
    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.restaturant_listing_menu, menu);
        searchManager = (SearchManager) getSystemService(SEARCH_SERVICE);
        searchView = (SearchView) menu.findItem(R.id.rlm_search)
                .getActionView();
        searchView.setSearchableInfo(searchManager
                .getSearchableInfo(new ComponentName(this,
                        RestaurantListingActivity.class)));
        return super.onCreateOptionsMenu(menu);
    }
    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
        case R.id.rlm_toggle:
    isRestaurantSearch = !isRestaurantSearch;
        if (isRestaurantSearch)
            searchView.setSearchableInfo(searchManager
                    .getSearchableInfo(new ComponentName(this,
                            RestaurantListingActivity.class)));
        else
            searchView.setSearchableInfo(searchManager
                    .getSearchableInfo(new ComponentName(this,
                            RestaurantFoodSwitcherActivity.class)));
    
    
        break;
    case R.id.rlm_change_loc:
    
        break;
    case R.id.rlm_filter_search:
    
        break;
    }
    
        return super.onOptionsItemSelected(item);
    }
    
    @Override
    public void onTabReselected(Tab tab, FragmentTransaction ft) {
        // TODO Auto-generated method stub
    
    }
    
    @Override
    public void onTabSelected(Tab tab, FragmentTransaction ft) {
    // TODO Auto-generated method stub
    }
    
    @Override
    public void onTabUnselected(Tab tab, FragmentTransaction ft) {
        // TODO Auto-generated method stub
    
    }
    
    @Override
    public void setScreenData(Object screenData, int event, long time) {
        // TODO Auto-generated method stub
    
    }
    
    @Override
    public Activity getMyActivityReference() {
        // TODO Auto-generated method stub
        return null;
    }
    
    @Override
    public void onClick(View v) {
        // TODO Auto-generated method stub
    
    }
    }
    
    public class RestaurantFoodSwitcherActivity extends RestaurantListingActivity {
    }
    
  • 餐厅清单菜单
  • searchablefood.xml

    <?xml version="1.0" encoding="utf-8"?>
    <searchable xmlns:android="http://schemas.android.com/apk/res/android"
        android:hint="@string/search_hint_food"
        android:label="@string/app_name">
    </searchable>
    
    
    
  • manifest.xml

    <activity         android:name="com.example.app.ui.activity.RestaurantListingActivity" >
        <!-- This intent-filter identifies this activity as "searchable" -->
        <intent-filter>
            <action android:name="android.intent.action.SEARCH" />
    
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
        <!-- This metadata entry provides further configuration details for searches -->
        <!-- that are handled by this activity. -->
        <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchablerestra"
    
             />
    </activity>
    <activity android:name="com.example.app.ui.activity.RestaurantFoodSwitcherActivity">
        <!-- This intent-filter identifies this activity as "searchable" -->
        <intent-filter>
            <action android:name="android.intent.action.SEARCH" />
    
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
        <!-- This metadata entry provides further configuration details for searches -->
        <!-- that are handled by this activity. -->
         <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchablefood"
             />
    </activity>
    
    
    

  • 有一个比上述任何一个更简单的答案。它为您的活动加载默认的searchable.xml,然后使用java反射更新SearchableInfo实例中的私有mhintd字段:

    @Override
    public void onPrepareOptionsMenu(Menu menu) {
        SearchManager searchManager = (SearchManager)getActivity().getSystemService(Context.SEARCH_SERVICE);
        SearchableInfo si = searchManager.getSearchableInfo( getActivity().getComponentName() );
    
        try {
            Field mHintId = si.getClass().getDeclaredField("mHintId");
            mHintId.setAccessible(true);
            mHintId.setInt(si, R.string.your_custom_hint);
        } catch (Exception e) {
        }
    
        MenuItem mi = menu.findItem(R.id.menu_search);
        SearchView searchView = (SearchView)mi.getActionView();
        searchView.setSearchableInfo( si );
    }
    

    如果您正在使用
    工具栏
    搜索视图
    小部件,可以通过调用以下命令轻松设置搜索查询提示:

    SearchView.setQueryHint(CharSequence hint)
    

    非常有趣的黑客。混乱,但似乎有效。你能想出一种方法让这种情况动态发生吗?i、 e.在运行时更新搜索提示?e、 g.设置一个提示字符串的格式,其中包含正在搜索的项目数量的实时计数。上述方法是最好、最简单的方法。忘掉所有其他复杂的建议吧@zyamys从哪个类和哪个方法调用invalidateLayout(),以便调用这个onPrepareOptions函数()重写?谢谢它由框架调用,您不需要调用活动。invalidateOptionsMenu(),除非出于某些无关的原因需要。
    <?xml version="1.0" encoding="utf-8"?>
    <searchable xmlns:android="http://schemas.android.com/apk/res/android"
        android:hint="@string/search_hint_food"
        android:label="@string/app_name">
    </searchable>
    
    <activity         android:name="com.example.app.ui.activity.RestaurantListingActivity" >
        <!-- This intent-filter identifies this activity as "searchable" -->
        <intent-filter>
            <action android:name="android.intent.action.SEARCH" />
    
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
        <!-- This metadata entry provides further configuration details for searches -->
        <!-- that are handled by this activity. -->
        <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchablerestra"
    
             />
    </activity>
    <activity android:name="com.example.app.ui.activity.RestaurantFoodSwitcherActivity">
        <!-- This intent-filter identifies this activity as "searchable" -->
        <intent-filter>
            <action android:name="android.intent.action.SEARCH" />
    
            <category android:name="android.intent.category.DEFAULT" />
        </intent-filter>
        <!-- This metadata entry provides further configuration details for searches -->
        <!-- that are handled by this activity. -->
         <meta-data
            android:name="android.app.searchable"
            android:resource="@xml/searchablefood"
             />
    </activity>
    
    @Override
    public void onPrepareOptionsMenu(Menu menu) {
        SearchManager searchManager = (SearchManager)getActivity().getSystemService(Context.SEARCH_SERVICE);
        SearchableInfo si = searchManager.getSearchableInfo( getActivity().getComponentName() );
    
        try {
            Field mHintId = si.getClass().getDeclaredField("mHintId");
            mHintId.setAccessible(true);
            mHintId.setInt(si, R.string.your_custom_hint);
        } catch (Exception e) {
        }
    
        MenuItem mi = menu.findItem(R.id.menu_search);
        SearchView searchView = (SearchView)mi.getActionView();
        searchView.setSearchableInfo( si );
    }
    
    SearchView.setQueryHint(CharSequence hint)