Ich habe eine EditText
namens myTextview
. Ich möchte, dass die Soft-Tastatur angezeigt wird, wenn ich auf die Variable EditText
klicke, sie aber dann verwerfen, wenn ich außerhalb der Variablen EditText
klicke. Also benutze ich die Methode unten. Die Tastatur wird jedoch nicht verworfen, wenn ich außerhalb der Ansicht klicke (ich klicke auf eine TextView
). Wie kann ich diesen Code korrigieren?
myTextview.setOnFocusChangeListener(new OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (hasFocus) {
getActivity().getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
} else {
InputMethodManager imm = (InputMethodManager) getActivity().getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(myTextview.getWindowToken(), 0);
}
}
});
Ich habe eine bessere Lösung gefunden:
Überschreiben Sie die dispatchTouchEvent
-Methode in Ihrer Aktivität.
@Override
public boolean dispatchTouchEvent(MotionEvent ev) {
View v = getCurrentFocus();
if (v != null &&
(ev.getAction() == MotionEvent.ACTION_UP || ev.getAction() == MotionEvent.ACTION_MOVE) &&
v instanceof EditText &&
!v.getClass().getName().startsWith("Android.webkit.")) {
int scrcoords[] = new int[2];
v.getLocationOnScreen(scrcoords);
float x = ev.getRawX() + v.getLeft() - scrcoords[0];
float y = ev.getRawY() + v.getTop() - scrcoords[1];
if (x < v.getLeft() || x > v.getRight() || y < v.getTop() || y > v.getBottom())
hideKeyboard(this);
}
return super.dispatchTouchEvent(ev);
}
public static void hideKeyboard(Activity activity) {
if (activity != null && activity.getWindow() != null && activity.getWindow().getDecorView() != null) {
InputMethodManager imm = (InputMethodManager)activity.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(activity.getWindow().getDecorView().getWindowToken(), 0);
}
}
Dies gilt auch, wenn Sie mit Webview arbeiten.
Vielleicht etwas einfacher:
Legen Sie einen focusChangedListener für Ihren Bearbeitungstext fest und blenden Sie dann die Tastatur aus, wenn Sie keinen Fokus haben.
yourEditText.setOnFocusChangeListener(new OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if(!hasFocus){
hideKeyboard();
}
}
});
private void hideKeyboard() {
InputMethodManager imm = (InputMethodManager)context.getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(yourEditText.getWindowToken(), 0);
}
verwenden Sie folgenden Code.
public static void hideSoftKeyboard(Activity activity) {
InputMethodManager inputMethodManager = (InputMethodManager) activity.getSystemService(Activity.INPUT_METHOD_SERVICE);
inputMethodManager.hideSoftInputFromWindow(activity.getCurrentFocus().getWindowToken(), 0);
}
es funktioniert für mich.
Auf diese Weise verschwindet die Tastatur nur, wenn Sie eine Ansicht berühren, die den Fokus erhält. Ich schlage vor, folgendes zu tun:
Erstellen Sie eine benutzerdefinierte Ansichtsgruppe wie folgt:
public class TouchLayout extends LinearLayout {
private OnInterceptTouchEventListener mListener;
public TouchLayout(Context context, AttributeSet attrs) {
super(context, attrs);
}
@Override
public boolean onInterceptTouchEvent(MotionEvent event) {
if(mListener != null) {
return mListener.onInterceptTouchEvent(event);
}
return super.onInterceptTouchEvent(event);
}
public void setOnInterceptTouchEventListener(OnInterceptTouchEventListener listener) {
mListener = listener;
}
public interface OnInterceptTouchEventListener {
public boolean onInterceptTouchEvent(MotionEvent event);
}
}
Fügen Sie dann die benutzerdefinierte Ansicht als Stamm Ihres XML-Layouts hinzu:
<com.example.TouchLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:id="@+id/root"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:orientation="vertical" >
<EditText
Android:id="@+id/text"
Android:layout_width="wrap_content"
Android:layout_height="wrap_content" />
Und in Ihrer Aktivität sollten Sie Folgendes tun:
final TouchLayout root = (TouchLayout) findViewById(R.id.root);
final EditText text = (EditText) findViewById(R.id.text);
final InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
root.setOnInterceptTouchEventListener(new OnInterceptTouchEventListener() {
@Override
public boolean onInterceptTouchEvent(MotionEvent event) {
final View v = getCurrentFocus();
if(v != null && v.equals(text)) {
final int screenCords[] = new int[2];
text.getLocationOnScreen(screenCords);
final Rect textRect = new Rect(screenCords[0], screenCords[1], screenCords[0] + text.getWidth(), screenCords[1] + text.getHeight());
if(!textRect.contains(event.getRawX(), event.getRawY() {
imm.hideSoftInputFromWindow(myTextview.getWindowToken(), 0);
// Optionally you can also do the following:
text.setCursorVisible(false);
text.clearFocus();
}
}
return false;
}
};
Klagegrund: Ich erkenne, dass ich keine Schlagkraft habe, aber bitte nehmen Sie meine Antwort ernst.
Problem: Weiche Tastatur schließen, wenn Sie nicht auf die Tastatur klicken oder Text mit minimalem Code bearbeiten.
Lösung: Externe Bibliothek, bekannt als Buttermesser.
One Line Solution:
@OnClick(R.id.activity_signup_layout) public void closeKeyboard() { ((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE)).hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0); }
Mehr lesbare Lösung:
@OnClick(R.id.activity_signup_layout)
public void closeKeyboard() {
InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0);
}
Erläuterung: Binden Sie OnClick Listener an die übergeordnete ID des XML-Layouts der Aktivität, sodass jeder Klick auf das Layout (nicht auf den Bearbeitungstext oder die Tastatur) dies ausführt Code-Schnipsel, das die Tastatur verdeckt.
Beispiel: Wenn Ihre Layoutdatei R.layout.my_layout lautet und Ihre Layout-ID R.id.my_layout_id lautet, sollte Ihr Butterknife-Bind-Aufruf folgendermaßen aussehen:
(@OnClick(R.id.my_layout_id)
public void yourMethod {
InputMethodManager imm = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0);
}
Butterknife Documentation Link: http://jakewharton.github.io/butterknife/
Stecker: Butterknife wird Ihre Android) - Entwicklung revolutionieren. Betrachten Sie es.
Xamarin Android-Code dafür:
public override bool DispatchTouchEvent(MotionEvent ev)
{
try
{
View view = CurrentFocus;
if (view != null && (ev.Action == MotionEventActions.Up || ev.Action == MotionEventActions.Move) && view is EditText && !view.Class.Name.StartsWith("Android.webkit."))
{
int[] Touch = new int[2];
view.GetLocationOnScreen(Touch);
float x = ev.RawX + view.Left - Touch[0];
float y = ev.RawY + view.Top - Touch[1];
if (x < view.Left || x > view.Right || y < view.Top || y > view.Bottom)
((InputMethodManager)GetSystemService(InputMethodService)).HideSoftInputFromWindow((Window.DecorView.ApplicationWindowToken), 0);
}
}
catch (System.Exception ex)
{
}
return base.DispatchTouchEvent(ev);
}
Das Berührungsereignis in einer Ansicht beginnt damit, dass ACTION_DOWN
von oben an diese Ansichtsansicht-Hierarchie übergeben wird. Überschreiben Sie dispatchTouchEvent
, um weitere Aktionen auszuführen. Hier ein Beispiel, um von FrameLayout
in kotlin auszugehen:
class TLayout @JvmOverloads constructor(context: Context, attrs: AttributeSet?=null):
FrameLayout(context, attrs){
var preDispatchTouchEvent: ((ev: MotionEvent?)->Boolean)? = null
override fun dispatchTouchEvent(ev: MotionEvent?): Boolean {
if (preDispatchTouchEvent==null || !preDispatchTouchEvent!!.invoke(ev)) {
super.dispatchTouchEvent(ev)
}
return true
}
}
Wickeln Sie Ihre EditText
und andere relative View
s in dieses Layout ein, und legen Sie preDispatchTouchEvent
fest, um EditText
zu verwerfen, wenn das Ereignis nicht darüber liegt.
Überprüfen Sie diese OS-Frage und offizielle Dokumente , um ein tieferes Verständnis für die Bereitstellung von Touch-Ereignissen zu haben.
Ich verwende unter Prozess. Es funktioniert perfekt für mich. Fügen Sie in Ihrer Aktivitätsklasse folgende Funktion hinzu.
override fun dispatchTouchEvent(event: MotionEvent): Boolean {
if (event.action == MotionEvent.ACTION_DOWN) {
val v = currentFocus
if (v is EditText) {
val outRect = Rect()
v.getGlobalVisibleRect(outRect)
if (!outRect.contains(event.rawX.toInt(), event.rawY.toInt())) {
Log.d("focus", "touchevent")
v.clearFocus()
val imm = getSystemService(Context.INPUT_METHOD_SERVICE) as InputMethodManager
imm.hideSoftInputFromWindow(v.windowToken, 0)
}
}
}
return super.dispatchTouchEvent(event)
}
Dann werde ich den Fokusstatus in meinem Fragment überprüfen.
appCompatEditText.onFocusChangeListener = View.OnFocusChangeListener { view, hasFocus ->
if (!hasFocus) {
toast("Focus Off")
}else {
toast("Focus On")
}
}
Ich wurde in Fragment eingecheckt. Ich brauchte den Fokusstatus für meine Aufgabe Anforderung. Focus Out Ich brauchte eine Aufgabe.