你們聽說過需要在Andrid設備上輸入IP地址的需求嗎,不管你們聽說了沒有,反正我是沒聽說。這不,產品提出了這麼逆天的需求。
祖傳的圖,傳男不傳女。
爲了點擊鍵盤效果明顯,特地下載一款這麼風騷的皮膚。
先說下大致思路
- 繼承LinearLayout
- 實現了多個EditText橫向排列。
- 去掉每個EditText的背景
- Linearlayout中onDraw()方法繪製邊框
- 爲每個EditText添加輸入監聽
解說一下越到坑
1. LinearLayout的onDraw方法需要執行,需要添加下面代碼
setDividerDrawable(getResources().getDrawable(android.R.drawable.divider_horizontal_textfield));
2. 每個EditText輸入完畢,如何讓下一個EditText選中,
3. 當一個EditText刪除完畢,如何讓上一個EditText被選中
4. **未解決的BUG,現在每個EditText的長度必須是3,才能完美的焦點切換**
下面貼一下代碼
**
* Created by xiongchengguang on 2016/12/22.
*/
public class SuperEditText extends LinearLayout implements TextWatcher {
private static final String TAG = "IPEditText";
private int width;
private int height;
private Paint paint;
private static final int DEFAULT_TEXT_MAX_LENGTH = 3;
private static final int DEFAULT_TEXT_SIZE = 16;
private static final int DEFAULT_TEXT_COLOR = Color.BLACK;
private static final int DEFAULT_BORDER_COLOR = Color.BLACK;
private static final int DEFAULT_BORDER_WIDTH = 2;
private static final int DEFAULT_POINT_COLOR = Color.BLACK;
private static final int DEFAULT_POINT_WIDTH = 5;
private static final int DEFAULT_IP_EDITTEXT_LENGTH = 4;
private int textLength;
private int textSize;
private int textColor;
private int borderColor;
private int borderWidth;
private int pointColor;
private int pointWidth;
private int editNumber;
private int default_height = px2dp(20);
private int default_width = px2dp(60);
private List<EditText> data = new ArrayList<>();
public SuperEditText(Context context) {
this(context, null);
}
public SuperEditText(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public SuperEditText(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.SuperEditText, defStyleAttr, 0);
textLength = ta.getInt(R.styleable.SuperEditText_textLength, DEFAULT_TEXT_MAX_LENGTH);
textSize = (int) ta.getDimension(R.styleable.SuperEditText_textSize, DEFAULT_TEXT_SIZE);
textColor = ta.getColor(R.styleable.SuperEditText_textColor, DEFAULT_TEXT_COLOR);
borderColor = ta.getColor(R.styleable.SuperEditText_borderColor, DEFAULT_BORDER_COLOR);
borderWidth = (int) ta.getDimension(R.styleable.SuperEditText_borderWidth, DEFAULT_BORDER_WIDTH);
pointColor = ta.getColor(R.styleable.SuperEditText_pointColor, DEFAULT_POINT_COLOR);
pointWidth = (int) ta.getDimension(R.styleable.SuperEditText_pointWidth, DEFAULT_POINT_WIDTH);
editNumber = ta.getInt(R.styleable.SuperEditText_editNumber, DEFAULT_IP_EDITTEXT_LENGTH);
init(context);
initPaint();
}
public float getTextSize() {
return data.get(0).getTextSize();
}
private void initPaint() {
paint = new Paint();
paint.setAntiAlias(true);
paint.setStrokeWidth(2);
paint.setStyle(Paint.Style.FILL);
}
private void init(Context context) {
for (int i = 0; i < editNumber; i++) {
EditText edit = new EditText(context);
edit.setBackground(null);
edit.setFilters(new InputFilter[]{new InputFilter.LengthFilter(textLength)});
edit.setTextSize(textSize);
edit.setTextColor(textColor);
edit.setGravity(Gravity.CENTER);
edit.setInputType(InputType.TYPE_CLASS_NUMBER);
edit.setMinHeight(default_height);
edit.setMinWidth(default_width);
edit.setTag(i);
edit.setMaxLines(1);
edit.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT, 1));
edit.addTextChangedListener(this);
addView(edit);
data.add(edit);
}
setDividerDrawable(getResources().getDrawable(android.R.drawable.divider_horizontal_textfield));
setOrientation(LinearLayout.HORIZONTAL);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
int l = data.get(0).getLeft();
int t = data.get(0).getTop() - getPaddingTop();
int r = width - getPaddingRight();
int b = height;
Rect rect = new Rect(l, t, r, b);
paint.setColor(borderColor);
paint.setStrokeWidth(borderWidth);
paint.setStyle(Paint.Style.STROKE);
canvas.drawRect(rect, paint);
int y = height / 2;
int x = width / editNumber;
paint.setStrokeWidth(pointWidth);
paint.setColor(pointColor);
for (int i = 1; i < data.size(); i++) {
canvas.drawPoint(x * i, y, paint);
}
}
@Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
width = w;
height = h;
}
@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 (listener != null) {
listener.afterTextChanged(getSuperEditTextValue());
}
if (s.length() == 3) {
for (int i = 0; i < data.size(); i++) {
EditText edit = data.get(i);
String val = edit.getText().toString();
if (val.length() == 0) {
edit.requestFocus();
return;
}
}
} else if (s.length() == 0) {
for (int i = data.size() - 1; i >= 0; i--) {
EditText edit = data.get(i);
edit.setFocusable(true);
String val = edit.getText().toString();
if (val.length() == 3) {
edit.requestFocus();
edit.setSelection(3);
return;
}
}
}
}
public String[] getSuperEditTextValue() {
String[] val = new String[editNumber];
for (int i = 0; i < editNumber; i++) {
val[i] = data.get(i).getText().toString();
KLog.d(data.get(i).getText().toString());
}
return val;
}
public void setSuperEdittextValue(String[] s) {
for (int i = 0; i < s.length; i++) {
data.get(i).setText(s[i]);
}
}
public boolean getSuperCompile() {
for (int i = 0; i < editNumber; i++) {
String str = data.get(i).getText().toString();
if (Integer.parseInt(str) <= 255) {
return true;
}
}
return false;
}
public int px2dp(int val) {
return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, val, getResources().getDisplayMetrics());
}
public int px2sp(int val) {
return (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP, val, getResources().getDisplayMetrics());
}
public interface SuperTextWatcher {
public void afterTextChanged(String[] s);
}
private SuperTextWatcher listener;
public void setSuperTextWatcher(SuperTextWatcher listener) {
this.listener = listener;
}
}
自定義屬性的
<?xml version="1.0" encoding="utf-8"?>
<resources>
<declare-styleable name="SuperEditText">
<attr name="textLength" format="integer" />
<attr name="textSize" format="dimension" />
<attr name="textColor" format="color" />
<attr name="borderColor" format="color" />
<attr name="borderWidth" format="dimension" />
<attr name="pointColor" format="color" />
<attr name="pointWidth" format="dimension" />
<attr name="editNumber" format="integer" />
</declare-styleable>
</resources>
歡迎各位老司機前來帶路