在实际开发项目中,业务需求在输入框中启动自定义的软键盘,光标可以移动,可复制等。例如:在输入框中输入身份证号码,弹出的软键盘只有数字与字母X。
需要处理的问题:
1.EditText 输入框焦点处理
2.系统在输入框获取焦点是弹出系统软键盘
解决思路:
1.继承EditText 自定义输入框,添加方法。(此方法在获取自定义控件之后就调用,告知系统不使用系统软键盘)
public void hideInput(Activity activity) {
if (android.os.Build.VERSION.SDK_INT <= 10) {
this.setInputType(InputType.TYPE_NULL);
} else {
activity.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
try {
Class<EditText> cls = EditText.class;
Method setSoftInputShownOnFocus;
setSoftInputShownOnFocus = cls.getMethod("setShowSoftInputOnFocus", boolean.class);
setSoftInputShownOnFocus.setAccessible(true);
setSoftInputShownOnFocus.invoke(this, false);
} catch (Exception e) {
e.printStackTrace();
}
}
}
重新方法以下2个方法
@Override
protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) {
super.onFocusChanged(focused, direction, previouslyFocusedRect);
if (focused) {
//显示自定义软键盘
show();
this.requestFocus();
} else {
//隐藏自定义软键盘
dismiss();
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
super.onTouchEvent(event);
//显示软键盘
show();
//设置光标位置
int index = getSelectionStart();
setSelection(index);
requestFocus();
return true;
}
完整代码:
public class IDCardEditText extends android.support.v7.widget.AppCompatEditText {
public IDCardEditText(Context context) {
super(context);
}
public IDCardEditText(Context context, AttributeSet attrs) {
super(context, attrs);
}
public IDCardEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
@Override
protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) {
super.onFocusChanged(focused, direction, previouslyFocusedRect);
if (focused) {
show();
this.requestFocus();
} else {
dismiss();
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
super.onTouchEvent(event);
show();
int index = getSelectionStart();
setSelection(index);
requestFocus();
return true;
}
private void dismiss() {
//TODO 隐藏自定义popuwidow软键盘
}
private void show() {
//TODO 添加自己的显示自定义popuwidow软键盘
}
public void onDelete() {
//自定义软键盘点击删除按钮,删除输入框内容
String s = getText().toString();
if (TextUtils.isEmpty(s)) {
return;
}
int end = getSelectionStart();
int start = end - 1;
if (end < start) {
return;
}
int len = s.length();
if (start > len || end > len) {
return;
}
if (start < 0 || end < 0) {
return;
}
getText().delete(start, end);
}
@Override
public void onClickNum(@NotNull String txt) {
//自定义软键盘点击内容,设置输入框内容
int index = getSelectionStart();
getText().insert(index, txt);
}
public void hideInput(Activity activity) {
if (android.os.Build.VERSION.SDK_INT <= 10) {
this.setInputType(InputType.TYPE_NULL);
} else {
activity.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_HIDDEN);
try {
Class<EditText> cls = EditText.class;
Method setSoftInputShownOnFocus;
setSoftInputShownOnFocus = cls.getMethod("setShowSoftInputOnFocus", boolean.class);
setSoftInputShownOnFocus.setAccessible(true);
setSoftInputShownOnFocus.invoke(this, false);
} catch (Exception e) {
e.printStackTrace();
}
}
}
需要注意点:
在同一个界面存在其他输入框时,需要对其他输入框进行进行焦点监听,隐藏有此输入框弹出软键盘
EditText.setOnFocusChangeListener(new View.OnFocusChangeListener() {
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (!hasFocus) {
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
if (imm != null) {
imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
}
}
}
});