web-dev-qa-db-ja.com

編集テキストの外側をタップしてフォーカスを失います

「編集テキスト」の外側をクリックすると、自動的にフォーカスが失われ、キーボードが非表示になります。現時点では、「edittext」をクリックするとフォーカスが合いますが、フォーカスを外すには戻るボタンを押す必要があります。

39
JustCurious

この問題を解決するには、まずそのEdittextのsetOnFocusChangeListenerを使用する必要があります

edittext.setOnFocusChangeListener(new View.OnFocusChangeListener() {
            @Override
            public void onFocusChange(View v, boolean hasFocus) {
                if (!hasFocus) {
                    Log.d("focus", "focus loosed");
                    // Do whatever you want here
                } else {
                    Log.d("focus", "focused");
                }
            }
        });

そして、あなたがする必要があるのは、そのEdittextを含むアクティビティのdispatchTouchEventをオーバーライドすることです

@Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        if (event.getAction() == MotionEvent.ACTION_DOWN) {
            View v = getCurrentFocus();
            if ( v instanceof EditText) {
                Rect outRect = new Rect();
                v.getGlobalVisibleRect(outRect);
                if (!outRect.contains((int)event.getRawX(), (int)event.getRawY())) {
                    Log.d("focus", "touchevent");
                    v.clearFocus();
                    InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
                    imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
                }
            }
        }
        return super.dispatchTouchEvent(event);
    }

次に、ユーザーが外側をクリックすると、まずこのdispatchTouchEventが呼び出され、次にeditextからフォーカスがクリアされます。OnFocusChangeListenerが呼び出され、フォーカスが変更されたので、ここで何でも実行できます、うまくいくことを願って:)

21
Sudhanshu Gaur

@woodshyはキーボードを隠すための答えを持っていますが、おそらくonClickにコードを置くことはonFocusChangedに置くほど良くありません。強制的にフォーカスを失うには、XMLファイルでフォーカスを転送するオブジェクトを設定する必要があります。

Android:focusable="true"
Android:focusableInTouchMode ="true"
18
lynnyilu

EditTextがリニアレイアウトまたは他のViewGroupに配置されているとします。次に、このコンテナーをクリック可能、フォーカス可能、およびフォーカス可能InTouchModeにする必要があります。その後、onClick Overrideメソッドで次のコードを使用して、このコンテナにonClickListenerを設定します。

@Override
public void onClick(View view) {
    InputMethodManager imm = (InputMethodManager) view.getContext()
            .getSystemService(Context.INPUT_METHOD_SERVICE);
    imm.hideSoftInputFromWindow(view.getWindowToken(), 0);
}
14
woodshy

だから私は少し調べてみたが、私が探していたソリューションは他にはなかった。私の意見では、フォーカスはEditTextビューに奇妙に振る舞います。

私がやったことは...

  1. ルートビューがRelativeLayoutであることを確認してください

  2. EditTextではなく、キーボードを非表示にする領域の上にあるオーバーレイレイアウトを追加します。以下のようなもの:

私の場合、EditTextは画面下部のコンテナにありました。他のすべてをカバーしていました。

  1. 次のようなメソッドがあります:
 private void hideKeyboard(){
 final InputMethodManager imm =(InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE); 
 imm.hideSoftInputFromWindow(editText.getWindowToken()、0); 
 keyboardOverlay.setVisibility(View.GONE); 
 editText.clearFocus(); 
} 
  1. 次に、作成したオーバーレイのonClickでこのメソッドを呼び出します。

  2. ここで必要なのは、editTextを押したときにオーバーレイが表示されるようにすることです。 onFocusイベントを使用することはできません(少なくとも機能しませんでした...)だから、代わりにonTouchイベントを管理しました。

 editText.setOnTouchListener(new OnTouchListener(){
 
 @Override 
 public boolean onTouch(final View v、final MotionEvent event){
 keyboardOverlay .setVisibility(View.VISIBLE); 
 editText.requestFocus(); 
 return false; 
} 
}); 

ここのrequestFocus()は、onTouchでフォーカスイベントをオーバーライドしないことです。

簡単なアドバイスとして、これを試してみると、オーバーレイに背景色を追加して、何が起こっているのかを正確に確認できます。

それがあなたのために働くことを願っています!

1
Charles

これを実現するには、次の手順を実行します。

1.次の属性を追加して、親ビュー(アクティビティのコンテンツビュー)をクリック可能およびフォーカス可能にする

    Android:clickable="true" 
    Android:focusableInTouchMode="true" 

2. hideKeyboard()メソッドを実装する

    public void hideKeyboard(View view) {
        InputMethodManager inputMethodManager =(InputMethodManager)getSystemService(Activity.INPUT_METHOD_SERVICE);
        inputMethodManager.hideSoftInputFromWindow(view.getWindowToken(), 0);
    }

3.最後に、編集テキストのonFocusChangeListenerを設定します。

    edittext.setOnFocusChangeListener(new View.OnFocusChangeListener() {
        @Override
        public void onFocusChange(View v, boolean hasFocus) {
            if (!hasFocus) {
                hideKeyboard(v);
            }
        }
    });
1
Rajul Goel

ボタンまたは任意のビューで設定:this.getCurrentFocus()。clearFocus();例えば:

@Override
public boolean onMenuOpened(int featureId, Menu menu) {
    InputMethodManager imm = (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
    imm.hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0);
    this.getCurrentFocus().clearFocus();
    return super.onMenuOpened(featureId, menu);
}
0
nobjta_9x_tq

次のコードは私にとって完璧に機能し、私はこれを定期的にSoftKeyboard onTouchを閉じる EditText以外の場所で使用します。

_public void hideSoftKeyboard()
{
        //Hides the SoftKeyboard
        InputMethodManager inputMethodManager = (InputMethodManager)  getActivity().getSystemService(Activity.INPUT_METHOD_SERVICE);
        inputMethodManager.hideSoftInputFromWindow(getActivity().getCurrentFocus().getWindowToken(), 0);
}

public void setupUI(View view) 
{
        String s = "inside";
        //Set up touch listener for non-text box views to hide keyboard.
        if (!(view instanceof EditText)) {

            view.setOnTouchListener(new View.OnTouchListener() {

                public boolean onTouch(View v, MotionEvent event) {
                    hideSoftKeyboard();
                    return false;
                }

            });        
        }


    //If a layout container, iterate over children and seed recursion.
        if (view instanceof ViewGroup) {

            for (int i = 0; i < ((ViewGroup) view).getChildCount(); i++) {

                View innerView = ((ViewGroup) view).getChildAt(i);

                setupUI(innerView);
            }
        }    
}
_

したがって、setupUI()メソッドとvoillaでonCreate()関数を1回呼び出すだけで、hidingSoftKeyboardがセットアップされます。

EditTextのLosing complete focusの場合、hideSoftKeyboard()関数でeditText.clearFocus()を実行するだけです。

0
Kaushik NP