两种不同实现,使用系统键盘和使用自定义键盘
1.简单功能,可结合自定义键盘使用,未处理系统键盘输入
布局
<?xml version="1.0" encoding="utf-8"?>
<merge xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView
android:id="@+id/input1"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
<TextView
android:id="@+id/input2"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:layout_marginLeft="-1dp"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
<TextView
android:id="@+id/input3"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:layout_marginLeft="-1dp"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
<TextView
android:id="@+id/input4"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:layout_marginLeft="-1dp"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
<TextView
android:id="@+id/input5"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:layout_marginLeft="-1dp"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
<TextView
android:id="@+id/input6"
android:layout_width="@dimen/dimen_36_dip"
android:layout_height="@dimen/dimen_36_dip"
android:layout_marginLeft="-1dp"
android:textSize="20sp"
android:textColor="#000000"
android:gravity="center"
android:background="@drawable/shape_bg_single_input"/>
</merge>
代码:
public class VerifyCodeView extends LinearLayout {
private static final int MESSAGE_VERIFY_LENGTH = 6;
private int mCurrent;
private StringBuilder mMessageVerify = new StringBuilder();
private InputCompleteListener mCompleteListener;
public VerifyCodeView(Context context) {
super(context);
init();
}
public VerifyCodeView(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
public VerifyCodeView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init();
}
private void init() {
setOrientation(LinearLayout.HORIZONTAL);
setGravity(Gravity.CENTER);
LayoutInflater.from(getContext()).inflate(R.layout.view_single_input, this);
mCurrent = 0;
}
public void append(String num) {
if (mCurrent == MESSAGE_VERIFY_LENGTH) {
return;
}
mMessageVerify.append(num);
((TextView) getChildAt(mCurrent)).setText(num);
mCurrent++;
if (mCurrent == MESSAGE_VERIFY_LENGTH && mCompleteListener != null) {
mCompleteListener.onComplete();
clearContent();
return;
}
}
public void delete() {
if (mCurrent > 0) {
mCurrent--;
mMessageVerify.delete(mCurrent, mCurrent);
((TextView) getChildAt(mCurrent)).setText("");
}
}
public void clearContent() {
mCurrent = 0;
mMessageVerify = new StringBuilder();
for (int i = 0; i < MESSAGE_VERIFY_LENGTH; i++) {
((TextView) getChildAt(i)).setText("");
}
}
public String getMessage() {
return mMessageVerify.toString();
}
public interface InputCompleteListener {
void onComplete();
}
public void setCompleteListener(InputCompleteListener completeListener) {
mCompleteListener = completeListener;
}
}
2.系统键盘输入
public class VerifyCodeView extends LinearLayout implements View.OnFocusChangeListener, TextWatcher, VerifyEditText.EmptyBackListener {
private static final int MESSAGE_VERIFY_LENGTH = 6;
private int mCurrent;
private StringBuilder mMessageVerify = new StringBuilder();
private VerifyEditText mItem1;
private VerifyEditText mItem2;
private VerifyEditText mItem3;
private VerifyEditText mItem4;
private VerifyEditText mItem5;
private VerifyEditText mItem6;
public VerifyCodeView(Context context) {
super(context);
init();
}
public VerifyCodeView(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
public VerifyCodeView(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
init();
}
private void init() {
setOrientation(LinearLayout.HORIZONTAL);
setGravity(Gravity.CENTER);
LayoutInflater.from(getContext()).inflate(R.layout.view_single_input, this);
mItem1 = (VerifyEditText) findViewById(R.id.input1);
initEditText(mItem1, 1);
mItem2 = (VerifyEditText) findViewById(R.id.input2);
initEditText(mItem2, 2);
mItem3 = (VerifyEditText) findViewById(R.id.input3);
initEditText(mItem3, 3);
mItem4 = (VerifyEditText) findViewById(R.id.input4);
initEditText(mItem4, 4);
mItem5 = (VerifyEditText) findViewById(R.id.input5);
initEditText(mItem5, 5);
mItem6 = (VerifyEditText) findViewById(R.id.input6);
initEditText(mItem6, 6);
mCurrent = 0;
}
private void initEditText(VerifyEditText item, int tag) {
item.setOnFocusChangeListener(this);
item.setTag(tag);
item.setListener(this);
item.addTextChangedListener(this);
}
public void append(String num) {
if (mCurrent == MESSAGE_VERIFY_LENGTH) {
return;
}
mMessageVerify.append(num);
mCurrent++;
}
public void delete() {
if (mCurrent > 0) {
mMessageVerify = mMessageVerify.deleteCharAt(mCurrent - 1);
mCurrent--;
}
}
public void clearContent() {
mCurrent = 0;
mMessageVerify = new StringBuilder();
for (int i = 0; i < MESSAGE_VERIFY_LENGTH; i++) {
((TextView) getChildAt(i)).setText("");
}
}
public String getMessage() {
return mMessageVerify.toString();
}
@Override
public void onFocusChange(View v, boolean hasFocus) {
if (hasFocus && (int) v.getTag() != mCurrent) {
if (mCurrent < MESSAGE_VERIFY_LENGTH) {
getChildAt(mCurrent).requestFocus();
} else {
getChildAt(MESSAGE_VERIFY_LENGTH - 1).requestFocus();
}
}
}
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
}
@Override
public void afterTextChanged(Editable s) {
if (!TextUtils.isEmpty(s.toString())) {
append(s.toString());
if (mCurrent < MESSAGE_VERIFY_LENGTH) {
getChildAt(mCurrent).requestFocus();
}
} else if (mCurrent == MESSAGE_VERIFY_LENGTH) {
delete();
EditText edt = (EditText) getChildAt(mCurrent);
edt.setText(null);
edt.requestFocus();
}
}
@Override
public void onEmptyBack() {
delete();
EditText edt = (EditText) getChildAt(mCurrent);
edt.setText(null);
edt.requestFocus();
}
}
public class VerifyEditText extends AppCompatEditText {
private EmptyBackListener mListener;
public VerifyEditText(Context context) {
super(context);
}
public VerifyEditText(Context context, AttributeSet attrs) {
super(context, attrs);
}
public VerifyEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
public void setListener(EmptyBackListener listener) {
mListener = listener;
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (TextUtils.isEmpty(getText()) && keyCode == KeyEvent.KEYCODE_DEL && mListener != null) {
mListener.onEmptyBack();
}
return super.onKeyDown(keyCode, event);
}
interface EmptyBackListener {
void onEmptyBack();
}
}