सॉफ्ट कीबोर्ड पर ऑटो संक्षिप्त एक्शनबार सर्च व्यू बंद करें


79

मैं वर्तमान में एक्शन बार में SearchView प्रदर्शित करने के लिए ActionBar मेनू आइटम का उपयोग कर रहा हूं। जब खोज मेनू आइटम का विस्तार किया जाता है तो नरम कीबोर्ड प्रदर्शित किया जाता है जो कि मैं चाहता हूं। अब, जब उपयोगकर्ता सॉफ्ट कीबोर्ड को बंद करने के लिए बैक बटन दबाता है, तो मैं भी सर्च बार को एक्शन बार में संक्षिप्त करना चाहूंगा।

मैंने MenuItem और ActionView पर निम्न श्रोताओं OnKeyListener और OnFocusChangeListener को लागू करने की कोशिश की है। मैंने भी गतिविधि में OnBackPressed () का उपयोग करने का प्रयास किया है। मुलायम कीबोर्ड को बंद करने के लिए बैक बटन का उपयोग करने पर उपरोक्त में से कोई भी पता नहीं चलता है।

कोई विचार?

SearchView के दिखाई देने पर मैंने यह जानने के लिए OnActionExpandListener को लागू किया है।


यहाँ एक बहुत ही लोकप्रिय उत्तर है stackoverflow.com/questions/1109022/…
jmishra

2
यह उसकी मदद नहीं करेगा, उसे कीबोर्ड से बैक कुंजी को इंटरसेप्ट करने की आवश्यकता है
dor506

@acrespo क्या जवाब है? आप एक प्रश्न पर टिप्पणी करते हैं ...
अविश्वसनीय जन

जवाबों:


100

मैं आलसी के लिए @ user1258568 के उत्तर पर विस्तार करूंगा। इसने मेरे लिए काम किया। ध्यान दें कि फोकस खो जाने पर यह आपकी क्वेरी को साफ़ कर देता है।

final MenuItem searchMenuItem = optionsMenu.findItem(R.id.search);
final SearchView searchView = (SearchView) searchMenuItem.getActionView();

searchView.setOnQueryTextFocusChangeListener(new View.OnFocusChangeListener() {
    @Override
    public void onFocusChange(View view, boolean queryTextFocused) {
        if(!queryTextFocused) {
            searchMenuItem.collapseActionView();
            searchView.setQuery("", false);
        }
    }
});

1
अच्छी तरह से काम। यदि आप कोड में एक खोज दृश्य जोड़ते हैं, तो आपको menu.getItem(yourSearchViewItemPosition)इसके बजाय उपयोग करने की आवश्यकता हो सकती है ।
GeeF

@AlexBonel कैसे? मुझे पता है कि S3 और S4 में बेवकूफ हार्डवेयर बटन हैं, लेकिन मैं स्पष्ट नहीं हूं कि इस स्निपेट को कैसे प्रभावित किया जाएगा। शायद यह इसलिए है क्योंकि ActionBar मेनू छिपा हुआ है और searchMenuItem अलग तरह से कार्य करता है। मुझे हाथ पर एक एस 4 मिला है, मुझे इसका परीक्षण करना होगा।
जॉन विलिस

@JonWillis यदि यह आपके लिए मुश्किल नहीं है, तो क्या आप S4 कृपया इस तरह के व्यवहार का अपना अनुभव साझा कर सकते हैं?
एलेक्स बोनेल

4
अच्छा लगा, घंटे और अनुसंधान के कार्यान्वयन के बाद ऐसा करने की कोशिश में मुझे आपका जवाब मिला :) ... पहली बात मैंने सोचा था कि एक फोकस श्रोता का उपयोग करना था लेकिन मैंने setOnFocusChangeListener()इसके बजाय उपयोग किया setOnQueryTextFocusChangeListener()। आपकी विधि के साथ सब कुछ अच्छी तरह से काम करता है। धन्यवाद।
इओनट नेगरू

2
@IonutNegru आपका स्वागत है! कभी-कभी एंड्रॉइड एसडीके से प्यार होता है। मैं देखना चाहता हूं कि वे इसे एक समझदार, आधुनिक तरीके से फिर से लिखेंगे और विरासत का समर्थन करेंगे, लेकिन ऐसा कभी नहीं होगा।
जॉन विलिस

37

मुझे एक बेहतर समाधान मिला।

searchView.setOnQueryTextFocusChangeListener(). 

OnQueryTextFocusChangeListenerजब कुंजीपटल प्रदर्शित या छिपा हुआ है कहा जाता हो जाता है। जब कीबोर्ड प्रदर्शित होता है तो सबसे पहले कॉल किया जाता है और खोज दृश्य में फोकस होगा। फिर से कहा जाता है जब keyboardछिपा हुआ है और खोज दृश्य फ़ोकस खो देगा, close search viewतब उपयोग कर सकता है

menuItem.collapseActionView().

5
यह भ्रामक है। OnQueryTextFocusChangeListenerजब कुंजीपटल प्रदर्शित या छिपा है नहीं कहा जाता हो जाता है। यह तभी कहा जाता है जब searchViewफोकस में आता है और फोकस से बाहर निकलता है। इसलिए, जब SearchViewपहली बार फोकस किया OnQueryTextFocusChangeListenerजाता है , तो कॉल किया जाता है और कीबोर्ड को भी प्रदर्शित किया जाता है। अब यदि बैक बटन दबाया जाता है, तो कीबोर्ड छिप जाता है, लेकिन OnQueryTextFocusChangeListenerकॉल नहीं किया जाता है। दूसरी बार बैक बटन दबाने पर searchViewढह OnQueryTextFocusChangeListenerजाता है और कहा जाता है।
फ़ैज़ल

11

इस तरह बस ओवरराइड करें

@Override
    public void onBackPressed() {
        if (searchView.isShown()){
            searchView.onActionViewCollapsed();  //collapse your ActionView
            searchView.setQuery("",false);       //clears your query without submit
            isClosed = true;                     //needed to handle closed by back
        } else{
            super.onBackPressed();
        }
    }

और आपका onCreateOptionsMenu इस तरह mSearchView को बढ़ाएगा:

@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        super.onCreateOptionsMenu(menu);
        getMenuInflater().inflate(R.menu.menu_search, menu);
        mSearchView = (SearchView) menu.findItem(R.id.menu_action_search).getActionView();
        mSearchView.setOnQueryTextListener(this);
        mSearchView.setOnSearchClickListener(this);
        mSearchView.setOnCloseListener(this);
        isClosed = true;
        return true;
    }

क्या आपने निम्न को इस तरह लागू किया है:

public class myActivity extends FragmentActivity implements
    SearchView.OnQueryTextListener, View.OnClickListener, SearchView.OnCloseListener {

जिसकी आपको भी आवश्यकता होगी:

@Override
public void onClick(View view) {
    isClosed = false;
}

@Override
public boolean onClose() {
    isClosed = true;
    return false;
}

आपको गतिविधि के लिए "वैश्विक खोज" और "बंद किया गया" दोनों वैश्विक चर बनाने की आवश्यकता होगी।


3
मुझे नहीं लगता कि वह काम करता है; मेरे अनुभव में ऑनबैकप्रेस्ड विधि को नहीं कहा जाता है यदि कीबोर्ड ऊपर है; यह बस कीबोर्ड को खारिज कर देता है और आपको उस विधि को कॉल करने के लिए इसे फिर से दबाने की आवश्यकता होती है। यह 2.3 पर है; मैंने 3.x और 4.0 के साथ प्रयोग नहीं किया है, लेकिन मुझे संदेह है कि यह भी वहीं है।
केवलर

@ केवलर मुझे लगता है कि आप सही हो सकते हैं। मैं इसे फिर से परीक्षण करूँगा और सुनिश्चित करूँगा कि कोई रास्ता नहीं है। मेरा समाधान लगता है कि वे क्या चाहते हैं के थोड़ा अलग करता है। जहां तक ​​मुझे पता है मुझे नहीं लगता कि सॉफ्ट कीबोर्ड दिखाए जाने के दौरान किसी भी बैक को हैंडल करने का एक तरीका है। सुनिश्चित करने के लिए कीबोर्ड बंद होने के बाद मेरा समाधान संभालता है। विभिन्न एसडीके पर परीक्षण करेंगे।
बजकर 32 मिनट पर कोड किया

1
मैंने खोज का उपयोग करने की कोशिश की थी: searchMenuItem.collapseActionView (); लेकिन यह पता चला कि searchView.onActionViewCollapsed (); मेरे लिए चाल चली गई - धन्यवाद!
21

मुझे नहीं लगता कि आपको सीधे कॉल करना चाहिए ... फ़ंक्शन। उन कार्यों को आपके कोड से सीधे कॉल नहीं किया जाता है ...
user457015

api लेवल 11. पर पतनActionView () का उपयोग कैसे करें
मदन V

3

जॉन विलिस का जवाब बहुत अच्छा काम करता है। यह उसके जवाब में सुधार है।

सबसे पहले, एक नया वर्ग बनाएं जो लागू होता है View.OnFocusChangeListener:

public class SearchViewFocusListener implements View.OnFocusChangeListener {

    private final MenuItem mMenuItem;

    public SearchViewFocusListener(MenuItem menuItem) {
        mMenuItem = menuItem;
    }

    @Override
    public void onFocusChange(View v, boolean hasFocus) {
        if (!hasFocus) {
            mMenuItem.collapseActionView();
            if (v instanceof SearchView) {
                ((SearchView) v).setQuery("", false);
            }
        }
    }

}

इसके बाद, श्रोता को अपने पर सेट करें SearchView:

searchView.setOnQueryTextFocusChangeListener(new SearchViewFocusListener(menuItem));

अच्छी तरह से काम करता है, लेकिन मैं खोज आइकन से फ़ोकस कैसे साफ़ करूं? FocusChangeListener एक डिवाइस पर बैक बटन का एक प्रेस कैप्चर करता है और जो सॉफ्ट कीबोर्ड को बंद कर देता है और SearchView को बंद कर देता है और फिर सर्च आइकन वैसा ही दिखाई देता है जैसा मैं चाहता हूं। हालाँकि, खोज आइकन हाइलाइट किया गया है (फोकस है) और मैं इसे पसंद नहीं करने के लिए पसंद करूंगा। मैंने साफ़ करने के कुछ तरीके आज़माए लेकिन किस्मत नहीं। कोई विचार?
एजेडब्ल्यू

2

आपको केवल मेनू लेआउट में "CollapseActionView" विशेषता डालनी होगी

<menu xmlns:android="http://schemas.android.com/apk/res/android"
      xmlns:app="http://schemas.android.com/apk/res-auto">
    <item
        android:id="@+id/menu_item_search"
        android:title="@string/search"
        android:iconifiedByDefault="true"
        android:icon="@drawable/ic_action_search" 
        app:actionViewClass="android.support.v7.widget.SearchView"
        app:showAsAction="ifRoom|collapseActionView"/> <--this one
</menu>

इससे आपको वह कार्यक्षमता मिलेगी जो आप सभी के लिए देखते हैं। क्वेरी भेजने के बाद कीबोर्ड को बंद करने के लिए SearchView पर "clearFocus" विधि को कॉल करना न भूलें।


1

यह मैंने कीबोर्ड को गायब करने के लिए किया था। आप यह देखने की कोशिश कर सकते हैं कि क्या यह आपके लिए काम करता है। मैंने searchViewअदृश्य और फिर फिर से दिखाई देने के लिए सेट किया ।

    //set query change listener
     searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener(){
        @Override
        public boolean onQueryTextChange(String newText) {
            // TODO Auto-generated method stub
            return false;
        }

        @Override
        public boolean onQueryTextSubmit(String query) {
            /**
             * hides and then unhides search tab to make sure keyboard disappears when query is submitted
             */
                  searchView.setVisibility(View.INVISIBLE);
                  searchView.setVisibility(View.VISIBLE);
            return false;
        }

     });

मेरे लिए भी काम किया है, लेकिन आपको getActivity () जोड़ना होगा। supportInvalidateOptionsMenu (); एक्शन बार को बहाल करने के लिए
अल्मिसॉफ्ट

1

यह इस तरह से प्राप्त करने योग्य है:

   private void setupSearchView(Menu menu) {
        final MenuItem searchMenuItem = menu.findItem(R.id.action_search);
        final SearchView searchView = (SearchView) searchMenuItem.getActionView();

        [...]

        searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
            @Override
            public boolean onQueryTextSubmit(String query) {
                searchMenuItem.collapseActionView();
                return false;
            }
            @Override
            public boolean onQueryTextChange(String newText) {
                return true;
            }
        });
    }

सेटऑनविकटेक्स्टफोकस चेंजलिस्टनर () पर आधारित समाधान मेरे लिए काम नहीं करता था क्योंकि इवेंट लॉन्च नहीं किया गया था - सबमिट किए जाने पर खोज दृश्य ने अपना ध्यान नहीं खोया, शायद इसलिए कि मैं उसी गतिविधि में खोज करता हूं जिसमें खोज दृश्य शामिल है।

वैसे भी, मुझे लगता है कि OnQueryTextListener का उपयोग करना अधिक सही है, क्योंकि यह पाठ को अधिक सटीक रूप से सबमिट करने की घटना का वर्णन करता है।


0
@Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getSupportMenuInflater().inflate(R.menu.home_screen, menu);

        SearchManager searchManager = (SearchManager) getSystemService(Context.SEARCH_SERVICE);
        final MenuItem searchMenuItem = menu.findItem(R.id.menu_search);
        final SearchView searchView = (SearchView) searchMenuItem
                .getActionView();
        searchView.setIconifiedByDefault(false);
        if (searchManager != null && searchView != null) {
            searchView.setSearchableInfo(searchManager
                    .getSearchableInfo(getComponentName()));

            searchView
                    .setOnQueryTextFocusChangeListener(new View.OnFocusChangeListener() {

                        @Override
                        public void onFocusChange(View v, boolean hasFocus) {

                            if (!hasFocus) {
                                if (searchMenuItem != null) {
                                    searchMenuItem.collapseActionView();
                                }// end if
                                if (searchView != null) {
                                    searchView.setQuery("", false);

                                }// end if
                            }// end if

                        }
                    });

            searchView
                    .setOnQueryTextListener(new SearchView.OnQueryTextListener() {

                        @Override
                        public boolean onQueryTextSubmit(String query) {
                            /**
                             * hides and then unhides search tab to make sure
                             * keyboard disappears when query is submitted
                             */
                            if (searchView != null) {
                                searchView.setVisibility(View.INVISIBLE);
                                searchView.setVisibility(View.VISIBLE);

                            }
                            return false;
                        }

                        @Override
                        public boolean onQueryTextChange(String newText) {
                            // TODO Auto-generated method stub
                            return false;
                        }
                    });

        }

        return super.onCreateOptionsMenu(menu);
    }

0

यदि आप कीबोर्ड को ध्वस्त करना चाहते हैं जब उपयोगकर्ता कीबोर्ड पर खोज आइकन पर क्लिक करता है तो इसे सरल द्वारा प्राप्त किया जा सकता है

inside onquerytextsubmitted {

searchView.clearfocus()

}


0

आपको दो बार setIconified कॉल करने की आवश्यकता है।

वास्तव में अपने खोज दृश्य को संक्षिप्त करें और कीबोर्ड को बंद करें।
पहले कॉल टेक्स्ट के साथ दूसरे कॉल कीबोर्ड से खोज दृश्य साफ़ हो जाता है और खोज दृश्य बंद हो जाता है।


0

किसी कारण से, menuItem.collapseActionView()काम नहीं किया इसलिए मैंने searchView.setIconified(true)इसके बजाय उपयोग किया।

यह नीचे दिए गए परिणाम को कोड नमूने के रूप में देता है।

final MenuItem searchItem = (MenuItem) menu.findItem(R.id.menu_item_search);
final SearchView searchView = (SearchView) searchItem.getActionView();

searchView.setOnQueryTextFocusChangeListener(new SearchView.OnFocusChangeListener() {
    @Override
    public void onFocusChange(View v, boolean hasFocus) {
        if (!hasFocus) {
            searchView.setIconified(true);
        }
    }
});
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.