前言
一开始大概是这种

需求
组长说 要不搞一个自定义软键盘吧 数字搞大点 方便外卖员输入数字
我设置了输入edittext的输入格式为number 还是不行
那就开搞吧
先来看下实现的效果图吧
实现效果gif

实现代码
自定义view 一个ninenumerickeyboardview
/**
* author by lyu
* date on 2021/5/26-19:55
* description:九宫格数字软键盘
*/
public class ninenumerickeyboardview extends view {
/**
* 列
*/
private static final int total_col = 3;
/**
* 行
*/
private static final int total_row = 4;
private paint huisebgpaint, linepaint;
private paint mtextpaint;
private int mviewwidth; // 键盘宽度
private int mviewhight; // 键盘高度
private float mcellwidth, mcellhight; // 单元格宽度、高度
private row rows[] = new row[total_row];
private bitmap bitmap; // 删除按钮图片
private paint mcuttextpaint;
//回调方法
public interface callback {
void clicknum(string num);// 回调点击的数字
void deletenum();// 回调删除
}
private callback mcallback;// 回调
public void setoncallback(callback callback) {
mcallback = callback;
}
public ninenumerickeyboardview(context context, attributeset attrs, int defstyle) {
super(context, attrs, defstyle);
init(context);
}
public ninenumerickeyboardview(context context, attributeset attrs) {
super(context, attrs);
init(context);
}
public ninenumerickeyboardview(context context) {
super(context);
init(context);
}
@override
protected void ondraw(canvas canvas) {
super.ondraw(canvas);
drawline(canvas);
for (int i = 0; i < total_row; i++) {
if (rows[i] != null)
rows[i].drawcells(canvas);
}
}
/**
* 画6条直线
*
* @param canvas
*/
private void drawline(canvas canvas) {
canvas.drawline(0, 0, mviewwidth, 0, linepaint);
canvas.drawline(0, mcellhight, mviewwidth, mcellhight, linepaint);
canvas.drawline(0, mcellhight * 2, mviewwidth, mcellhight * 2, linepaint);
canvas.drawline(0, mcellhight * 3, mviewwidth, mcellhight * 3, linepaint);
canvas.drawline(mcellwidth, 0, mcellwidth, mviewhight, linepaint);
canvas.drawline(mcellwidth * 2, 0, mcellwidth * 2, mviewhight, linepaint);
}
/**
* 初始化画笔
*
* @param context
*/
private void init(context context) {
mtextpaint = new paint(paint.anti_alias_flag);
mcuttextpaint = new paint(paint.anti_alias_flag);
linepaint = new paint(paint.anti_alias_flag);
linepaint.settextsize(1.0f);
linepaint.setcolor(0x90000000);
huisebgpaint = new paint(paint.anti_alias_flag);
huisebgpaint.setstyle(paint.style.fill);
huisebgpaint.setcolor(color.parsecolor("#e9e9e9"));
initdate();
}
private void initdate() {
filldate();
}
@override
protected void onsizechanged(int w, int h, int oldw, int oldh) {
super.onsizechanged(w, h, oldw, oldh);
mviewwidth = w;
mviewhight = h;
mcellwidth = mviewwidth / total_col;
mcellhight = mviewhight / total_row;
mtextpaint.settextsize(mcellhight / 3);
}
private cell mclickcell = null;
private float mdownx;
private float mdowny;
/*
*
* 触摸事件为了确定点击位置的数字
*/
@override
public boolean ontouchevent(motionevent event) {
switch (event.getaction()) {
case motionevent.action_down:
mdownx = event.getx();
mdowny = event.gety();
int col = (int) (mdownx / mcellwidth);
int row = (int) (mdowny / mcellhight);
measureclickcell(col, row);
break;
case motionevent.action_up:
if (mclickcell != null) {
// 在抬起后把状态置为默认
rows[mclickcell.i].cells[mclickcell.j].state = state.default_num;
mclickcell = null;
invalidate();
}
break;
}
return true;
}
/**
* 测量点击单元格
*
* @param col 列
* @param row 行
*/
private void measureclickcell(int col, int row) {
if (col >= total_col || row >= total_row)
return;
if (rows[row] != null) {
mclickcell = new cell(rows[row].cells[col].num, rows[row].cells[col].state, rows[row].cells[col].i,
rows[row].cells[col].j);
rows[row].cells[col].state = state.click_num;
if ("-5".equals(rows[row].cells[col].num)) {
mcallback.deletenum();
} else {
mcallback.clicknum(rows[row].cells[col].num);
}
invalidate();
}
}
/**
* 组 以一行为一组
*/
private class row {
public int j;
row(int j) {
this.j = j;
}
// 一行3个单元格
public cell[] cells = new cell[total_col];
public void drawcells(canvas canvas) {
for (int i = 0; i < cells.length; i++) {
if (cells[i] != null)
cells[i].drawself(canvas);
}
}
}
// 单元格
private class cell {
public string num;
public state state;
/**
* i = 行 j = 列
*/
public int i;
public int j;
public cell(string num, state state, int i, int j) {
super();
this.num = num;
this.state = state;
this.i = i;
this.j = j;
}
// 绘制一个单元格 如果颜色需要自定义可以修改
public void drawself(canvas canvas) {
switch (state) {
case click_num:
// 绘制点击效果灰色背景
canvas.drawrect((mcellwidth * j), (mcellhight * i),
(mcellwidth * (j + 1)), (mcellhight * (i + 1)), huisebgpaint);
break;
}
if ("-5".equals(num)) {
// 绘制删除图片
canvas.drawbitmap(bitmap, (float) (mcellwidth * 2.5 - bitmap.getwidth() / 2), (float) (mcellhight * 3.5 - bitmap.getheight() / 2), huisebgpaint);
} else {
// 绘制数字
canvas.drawtext(num, (float) ((j + 0.5) * mcellwidth - mtextpaint.measuretext(num) / 2),
(float) ((i + 0.5) * mcellhight + mtextpaint.measuretext(num, 0, 1) / 2),
mtextpaint);
}
}
}
/**
* cell的state
*/
private enum state {
default_num, click_num;
}
private list<string> numkeys = arrays.aslist("1", "2", "3", "4", "5", "6", "7", "8", "9", "0");
/**
* 填充数字
*/
private void filldate() {
int postion = 0;
for (int i = 0; i < total_row; i++) {
rows[i] = new row(i);
for (int j = 0; j < total_col; j++) {
if (i == 3 && j == 0) {
rows[i].cells[j] = new cell(".", state.default_num, i, j);
continue;
} else if (i == 3 && j == 2) {
rows[i].cells[j] = new cell("-5", state.default_num, i, j);
continue;
} else {
rows[i].cells[j] = new cell(numkeys.get(postion), state.default_num, i, j);
postion++;
}
}
}
//这里是插入一张删除数字的图 一般是 x
bitmap = bitmapfactory.decoderesource(getresources(), r.mipmap.keyboard_delete);
}
}
使用方法
利用android自带的组件popupwindow在指定页面的下方弹出即可 完成效果
在指定的view页面
//初始化键盘
private void initkeyboardview() {
// 设置不弹出系统键盘
etinputpickupcode.setinputtype(inputtype.type_null);
// 自己监听edittext的点击事件弹出我们自定义的键盘
etinputpickupcode.setonclicklistener(view -> mpop.showatlocation(llkey, gravity.bottom, 0, 0));
mpop = new popupwindow();
mpopview = layoutinflater.from(getapplicationcontext()).inflate(r.layout.custom_keyboardview, null);
mpop.setcontentview(mpopview);
mpop.settouchable(true);
mpop.setfocusable(true);
mpop.setbackgrounddrawable(new colordrawable());
mpop.setwidth(viewgroup.layoutparams.match_parent);
mpop.setheight(viewgroup.layoutparams.wrap_content);
mcustomkeyview = mpopview.findviewbyid(r.id.key_view);
// 设置回调,并进行文本的插入与删除
mcustomkeyview.setoncallback(this);
}
@override
public void clicknum(string num) {
if (etinputpickupcode.gettext().length() < 8) {
etinputpickupcode.append(num);
}
}
@override
public void deletenum() {
int last = etinputpickupcode.gettext().length();
if (last > 0) {
//删除最后一位
etinputpickupcode.gettext().delete(last - 1, last);
}
}
以上就是android 实现数字九宫格软键盘的详细内容,更多关于android 数字九宫格软键盘的资料请关注其它相关文章!
____你瞒我瞒__