Pertanyaan Tutup / sembunyikan Keyboard Android Lembut


Saya punya EditText dan a Button di layout saya.

Setelah menulis di bidang edit dan mengklik pada ButtonSaya ingin menyembunyikan keyboard virtual. Saya berasumsi bahwa ini adalah potongan kode yang sederhana, tetapi di mana saya dapat menemukan contohnya?


3085


asal


Jawaban:


Untuk membantu mengklarifikasi kegilaan ini, saya ingin memulai dengan meminta maaf atas nama semua pengguna Android untuk perawatan keyboard lunak yang benar-benar konyol dari Google. Alasannya ada begitu banyak jawaban, masing-masing berbeda, untuk pertanyaan sederhana yang sama adalah karena API ini, seperti banyak lainnya di Android, dirancang secara mengerikan. Saya tidak bisa memikirkan cara sopan untuk menyatakannya.

Saya ingin menyembunyikan keyboard. Saya berharap menyediakan Android dengan pernyataan berikut: Keyboard.hide(). Tamat. Terima kasih banyak. Tetapi Android memiliki masalah. Anda harus menggunakan InputMethodManager untuk menyembunyikan keyboard. OK, baiklah, ini adalah API Android ke keyboard. TAPI! Anda wajib memiliki Context untuk mendapatkan akses ke IMM. Sekarang kita punya masalah. Saya mungkin ingin menyembunyikan keyboard dari kelas statis atau utilitas yang tidak memiliki penggunaan atau kebutuhan untuk itu Context. atau Dan JAUH lebih buruk, IMM mengharuskan Anda menentukan apa View (atau lebih buruk lagi, apa Window) Anda ingin menyembunyikan keyboard FROM.

Inilah yang membuat menyembunyikan keyboard begitu menantang. Google yang terhormat: Saat saya mencari resep kue, tidak ada RecipeProvider di Bumi yang akan menolak memberikan resep itu kepada saya kecuali saya pertama kali menjawab bahwa kue itu akan dimakan oleh AND di mana makanan itu akan dimakan !!

Kisah sedih ini berakhir dengan kebenaran yang buruk: untuk menyembunyikan keyboard Android, Anda akan diminta untuk memberikan 2 bentuk identifikasi: a Context dan apakah a View atau a Window.

Saya telah membuat metode utilitas statis yang dapat melakukan pekerjaan SANGAT kokoh, asalkan Anda memanggilnya dari Activity.

public static void hideKeyboard(Activity activity) {
    InputMethodManager imm = (InputMethodManager) activity.getSystemService(Activity.INPUT_METHOD_SERVICE);
    //Find the currently focused view, so we can grab the correct window token from it.
    View view = activity.getCurrentFocus();
    //If no view currently has focus, create a new one, just so we can grab a window token from it
    if (view == null) {
        view = new View(activity);
    }
    imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}

Ketahuilah bahwa metode utilitas ini HANYA berfungsi saat dipanggil dari Activity! Metode di atas memanggil getCurrentFocus dari target Activity untuk mengambil token jendela yang tepat.

Tetapi misalkan Anda ingin menyembunyikan keyboard dari EditText di-hosting di DialogFragment? Anda tidak dapat menggunakan metode di atas untuk itu:

hideKeyboard(getActivity()); //won't work

Ini tidak akan berfungsi karena Anda akan memberikan referensi ke FragmentTuan rumah Activity, yang tidak akan memiliki kontrol terfokus sementara Fragment ditunjukkan! Wow! Jadi, untuk menyembunyikan keyboard dari fragmen, saya beralih ke tingkat yang lebih rendah, lebih umum, dan lebih buruk:

public static void hideKeyboardFrom(Context context, View view) {
    InputMethodManager imm = (InputMethodManager) context.getSystemService(Activity.INPUT_METHOD_SERVICE);
    imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}

Di bawah ini adalah beberapa informasi tambahan yang dikumpulkan dari lebih banyak waktu yang terbuang mengejar solusi ini:

Tentang windowSoftInputMode

Masih ada titik lain yang harus diperhatikan. Secara default, Android akan secara otomatis menetapkan fokus awal ke yang pertama EditText atau kontrol yang dapat difokuskan pada Anda Activity. Secara alami mengikuti bahwa InputMethod (biasanya keyboard lunak) akan merespon peristiwa fokus dengan menunjukkan dirinya. Itu windowSoftInputMode atribut dalam AndroidManifest.xml, saat disetel ke stateAlwaysHidden, menginstruksikan keyboard untuk mengabaikan fokus awal yang ditetapkan secara otomatis ini.

<activity
    android:name=".MyActivity"
    android:windowSoftInputMode="stateAlwaysHidden"/>

Hampir luar biasa, tampaknya tidak melakukan apa pun untuk mencegah keyboard membuka ketika Anda menyentuh kontrol (kecuali focusable="false" dan / atau focusableInTouchMode="false" ditugaskan ke kontrol). Tampaknya, pengaturan windowSoftInputMode hanya berlaku untuk acara fokus otomatis, bukan untuk memfokuskan acara yang dipicu dari acara sentuh.

Karena itu, stateAlwaysHidden SANGAT bernama buruk memang. Mungkin harus dipanggil ignoreInitialFocus sebagai gantinya.

Semoga ini membantu.


UPDATE: Lebih banyak cara untuk mendapatkan token jendela

Jika tidak ada tampilan fokus (mis. Dapat terjadi jika Anda baru saja mengubah fragmen), ada tampilan lain yang akan menyediakan token jendela yang berguna.

Ini adalah alternatif untuk kode di atas if (view == null) view = new View(activity);  Ini tidak secara eksplisit merujuk pada aktivitas Anda.

Di dalam kelas fragmen:

view = getView().getRootView().getWindowToken();

Diberikan fragmen fragment sebagai parameter:

view = fragment.getView().getRootView().getWindowToken();

Mulai dari isi konten Anda:

view = findViewById(android.R.id.content).getRootView().getWindowToken();

UPDATE 2: Bersihkan fokus untuk menghindari menampilkan keyboard lagi jika Anda membuka aplikasi dari latar belakang

Tambahkan baris ini ke bagian akhir metode:

view.clearFocus();


1008



Anda dapat memaksa Android menyembunyikan keyboard virtual menggunakan InputMethodManager, menelepon hideSoftInputFromWindow, melewati token dari jendela yang berisi pandangan terfokus Anda.

// Check if no view has focus:
View view = this.getCurrentFocus();
if (view != null) {  
    InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
    imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}

Ini akan memaksa keyboard disembunyikan di semua situasi. Dalam beberapa kasus, Anda ingin melewatinya InputMethodManager.HIDE_IMPLICIT_ONLY sebagai parameter kedua untuk memastikan Anda hanya menyembunyikan keyboard saat pengguna tidak secara eksplisit memaksanya untuk muncul (dengan menahan menu).

catatan: Jika Anda ingin melakukan ini di Kotlin, gunakan: context?.getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager


4171



Juga berguna untuk menyembunyikan soft-keyboard adalah:

getWindow().setSoftInputMode(
    WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN
);

Ini dapat digunakan untuk menekan soft-keyboard sampai pengguna benar-benar menyentuh tampilan editText.


741



Saya punya satu solusi lagi untuk menyembunyikan keyboard:

InputMethodManager imm = (InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE);
imm.toggleSoftInput(InputMethodManager.HIDE_IMPLICIT_ONLY, 0);

Di sini lulus HIDE_IMPLICIT_ONLY pada posisi showFlag dan 0 pada posisi hiddenFlag. Ini akan menutup Keyboard lunak secara paksa.


294



Solusi Meier bekerja untuk saya juga. Dalam kasus saya, tingkat teratas Aplikasi saya adalah tabHost dan saya ingin menyembunyikan kata kunci ketika berpindah tab - saya mendapatkan token jendela dari tabHost View.

tabHost.setOnTabChangedListener(new OnTabChangeListener() {
    public void onTabChanged(String tabId) {
        InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
        imm.hideSoftInputFromWindow(tabHost.getApplicationWindowToken(), 0);
    }
}

128



Silakan coba kode di bawah ini di onCreate()

EditText edtView=(EditText)findViewById(R.id.editTextConvertValue);
edtView.setInputType(0);

115



Memperbarui: Saya tidak tahu mengapa solusi ini tidak berfungsi lagi (saya baru saja menguji pada Android 23). Silakan gunakan solusi Saurabh Pareek sebagai gantinya. Ini dia:

InputMethodManager imm = (InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE);
//Hide:
imm.toggleSoftInput(InputMethodManager.HIDE_IMPLICIT_ONLY, 0);
//Show
imm.toggleSoftInput(InputMethodManager.SHOW_IMPLICIT, 0);

Jawaban lama:

//Show soft-keyboard:
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
//hide keyboard :
 getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);

107



protected void hideSoftKeyboard(EditText input) {
    input.setInputType(0);
    InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
    imm.hideSoftInputFromWindow(input.getWindowToken(), 0);    
}

63



Jika semua jawaban lain di sini tidak bekerja untuk Anda seperti yang Anda inginkan, ada cara lain untuk mengendalikan keyboard secara manual.

Buat fungsi dengan yang akan mengelola beberapa EditTextproperti:

public void setEditTextFocus(boolean isFocused) {
    searchEditText.setCursorVisible(isFocused);
    searchEditText.setFocusable(isFocused);
    searchEditText.setFocusableInTouchMode(isFocused);

    if (isFocused) {
        searchEditText.requestFocus();
    }
}

Kemudian, pastikan bahwa onFocus of the EditText Anda membuka / menutup keyboard:

searchEditText.setOnFocusChangeListener(new OnFocusChangeListener() {
    @Override
    public void onFocusChange(View v, boolean hasFocus) {
        if (v == searchEditText) {
            if (hasFocus) {
                // Open keyboard
                ((InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE)).showSoftInput(searchEditText, InputMethodManager.SHOW_FORCED);
            } else {
                // Close keyboard
                ((InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE)).hideSoftInputFromWindow(searchEditText.getWindowToken(), 0);
            }
        }
    }
});

Sekarang, kapan pun Anda ingin membuka keyboard secara manual:

setEditTextFocus(true);

Dan untuk menutup panggilan:

setEditTextFocus(false);

58



Saurabh Pareek memiliki jawaban terbaik sejauh ini.

Mungkin juga menggunakan bendera yang benar.

/* hide keyboard */
((InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE))
    .toggleSoftInput(InputMethodManager.SHOW_IMPLICIT, 0);

/* show keyboard */
((InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE))
    .toggleSoftInput(0, InputMethodManager.HIDE_IMPLICIT_ONLY);

Contoh penggunaan nyata

/* click button */
public void onClick(View view) {      
  /* hide keyboard */
  ((InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE))
      .toggleSoftInput(InputMethodManager.SHOW_IMPLICIT, 0);

  /* start loader to check parameters ... */
}

/* loader finished */
public void onLoadFinished(Loader<Object> loader, Object data) {
    /* parameters not valid ... */

    /* show keyboard */
    ((InputMethodManager) getSystemService(Activity.INPUT_METHOD_SERVICE))
        .toggleSoftInput(0, InputMethodManager.HIDE_IMPLICIT_ONLY);

    /* parameters valid ... */
}

51



dari begitu mencari, di sini saya menemukan jawaban yang bekerja untuk saya

// Show soft-keyboard:
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
imm.toggleSoftInput(InputMethodManager.SHOW_FORCED, 0);

// Hide soft-keyboard:
getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);

45