android自定义金额输入键盘_Android 自定义输入支付密码的软键盘实例代码

本文介绍了如何在Android中创建一个自定义的输入支付密码的软键盘,类似于支付宝的键盘。通过`android.inputmethodservice.KeyboardView`实现,提供删除和数字输入功能,并展示了如何随机打乱数字顺序以增加安全性。
摘要由CSDN通过智能技术生成

Android 自定义输入支付密码的软键盘

有项目需求需要做一个密码锁功能,还有自己的软键盘,类似与支付宝那种,这里是整理的资料,大家可以看下,如有错误,欢迎留言指正

需求:要实现类似支付宝的输入支付密码的功能,效果图如下:

软键盘效果图

使用 android.inputmethodservice.KeyboardView这个类自定义软键盘

软键盘的实现

1. 自定义只输入数字的软键盘 PasswordKeyboardView 类,继承自 android.inputmethodservice.KeyboardView

/**

* 输入数字密码的键盘布局控件。

*/

public class PasswordKeyboardView extends KeyboardView implements

android.inputmethodservice.KeyboardView.OnKeyboardActionListener {

// 用于区分左下角空白的按键

private static final int KEYCODE_EMPTY = -10;

private int mDeleteBackgroundColor;

private Rect mDeleteDrawRect;

private Drawable mDeleteDrawable;

private IOnKeyboardListener mOnKeyboardListener;

public PasswordKeyboardView(Context context, AttributeSet attrs) {

super(context, attrs);

init(context, attrs, 0);

}

public PasswordKeyboardView(Context context, AttributeSet attrs,

int defStyleAttr) {

super(context, attrs, defStyleAttr);

init(context, attrs, defStyleAttr);

}

private void init(Context context, AttributeSet attrs,

int defStyleAttr) {

TypedArray a = context.obtainStyledAttributes(attrs,

R.styleable.PasswordKeyboardView, defStyleAttr, 0);

mDeleteDrawable = a.getDrawable(

R.styleable.PasswordKeyboardView_pkvDeleteDrawable);

mDeleteBackgroundColor = a.getColor(

R.styleable.PasswordKeyboardView_pkvDeleteBackgroundColor,

Color.TRANSPARENT);

a.recycle();

// 设置软键盘按键的布局

Keyboard keyboard = new Keyboard(context,

R.xml.keyboard_number_password);

setKeyboard(keyboard);

setEnabled(true);

setPreviewEnabled(false);

setOnKeyboardActionListener(this);

}

@Override

public void onDraw(Canvas canvas) {

super.onDraw(canvas);

// 遍历所有的按键

List keys = getKeyboard().getKeys();

for (Keyboard.Key key : keys) {

// 如果是左下角空白的按键,重画按键的背景

if (key.codes[0] == KEYCODE_EMPTY) {

drawKeyBackground(key, canvas, mDeleteBackgroundColor);

}

// 如果是右下角的删除按键,重画背景,并且绘制删除的图标

else if (key.codes[0] == Keyboard.KEYCODE_DELETE) {

drawKeyBackground(key, canvas, mDeleteBackgroundColor);

drawDeleteButton(key, canvas);

}

}

}

// 绘制按键的背景

private void drawKeyBackground(Keyboard.Key key, Canvas canvas,

int color) {

ColorDrawable drawable = new ColorDrawable(color);

drawable.setBounds(key.x, key.y,

key.x + key.width, key.y + key.height);

drawable.draw(canvas);

}

// 绘制删除按键

private void drawDeleteButton(Keyboard.Key key, Canvas canvas) {

if (mDeleteDrawable == null)

return;

// 计算删除图标绘制的坐标

if (mDeleteDrawRect == null || mDeleteDrawRect.isEmpty()) {

int intrinsicWidth = mDeleteDrawable.getIntrinsicWidth();

int intrinsicHeight = mDeleteDrawable.getIntrinsicHeight();

int drawWidth = intrinsicWidth;

int drawHeight = intrinsicHeight;

// 限制图标的大小,防止图标超出按键

if (drawWidth > key.width) {

drawWidth = key.width;

drawHeight = drawWidth * intrinsicHeight / intrinsicWidth;

}

if (drawHeight > key.height) {

drawHeight = key.height;

drawWidth = drawHeight * intrinsicWidth / intrinsicHeight;

}

// 获取删除图标绘制的坐标

int left = key.x + (key.width - drawWidth) / 2;

int top = key.y + (key.height - drawHeight) / 2;

mDeleteDrawRect = new Rect(left, top,

left + drawWidth, top + drawHeight);

}

// 绘制删除的图标

if (mDeleteDrawRect != null && !mDeleteDrawRect.isEmpty()) {

mDeleteDrawable.setBounds(mDeleteDrawRect.left,

mDeleteDrawRect.top, mDeleteDrawRect.right,

mDeleteDrawRect.bottom);

mDeleteDrawable.draw(canvas);

}

}

@Override

public void onKey(int primaryCode, int[] keyCodes) {

// 处理按键的点击事件

// 点击删除按键

if (primaryCode == Keyboard.KEYCODE_DELETE) {

if (mOnKeyboardListener != null) {

mOnKeyboardListener.onDeleteKeyEvent();

}

}

// 点击了非左下角按键的其他按键

else if (primaryCode != KEYCODE_EMPTY) {

if (mOnKeyboardListener != null) {

mOnKeyboardListener.onInsertKeyEvent(

Character.toString((char) primaryCode));

}

}

}

@Override

public void onPress(int primaryCode) {

}

@Override

public void onRelease(int primaryCode) {

}

@Override

public void onText(CharSequence text) {

}

@Override

public void swipeLeft() {

}

@Override

public void swipeRight() {

}

@Override

public void swipeDown() {

}

@Override

public void swipeUp() {

}

/**

* 设置键盘的监听事件。

*

* @param listener

* 监听事件

*/

public void setIOnKeyboardListener(IOnKeyboardListener listener) {

this.mOnKeyboardListener = listener;

}

public interface IOnKeyboardListener {

void onInsertKeyEvent(String text);

void onDeleteKeyEvent();

}

}

2. 自定义属性:

values/attrs.xml

3. 软键盘按键的布局文件 res/xml/keyboard_number_password:

说明:

android:keyWidth="33.33333%p":指定按键的宽度,保证键盘的每一列宽度一致

android:keyHeight="8%p":设置键盘的高度

android:horizontalGap="1dp":实现键盘每一列之间的分割线

android:verticalGap="1dp":实现键盘每一行之间的分割线

xmlns:android="http://schemas.android.com/apk/res/android"

android:keyWidth="33.33333%p"

android:keyHeight="8%p"

android:horizontalGap="1dp"

android:verticalGap="1dp">

android:codes="49"

android:keyLabel="1"/>

android:codes="50"

android:keyLabel="2"/>

android:codes="51"

android:keyLabel="3"/>

android:codes="52"

android:keyLabel="4"/>

android:codes="53"

android:keyLabel="5"/>

android:codes="54"

android:keyLabel="6"/>

android:codes="55"

android:keyLabel="7"/>

android:codes="56"

android:keyLabel="8"/>

android:codes="57"

android:keyLabel="9"/>

android:codes="-10"

android:keyLabel=""/>

android:codes="48"

android:keyLabel="0"/>

android:codes="-5"

android:keyIcon="@mipmap/keyboard_backspace"/>

3. 在布局中引用软键盘控件:

android:layout_width="match_parent"

android:layout_height="wrap_content"

android:background="#b0b0b0"

android:focusable="true"

android:focusableInTouchMode="true"

android:keyBackground="#ffffff"

android:keyTextColor="#000000"

android:shadowColor="#00000000"

android:shadowRadius="0"

app:pkvDeleteBackgroundColor="#d2d2d2"

app:pkvDeleteDrawable="@drawable/keyboard_backspace" />

随机数字键盘的实现

目前能想到的有两种实现方式:

1. 在 onDraw 方法里重新绘制键盘上的文字,覆盖掉原来的键盘,这种实现方式相对比较麻烦。

2. 调用 KeyboardView.setKeyboard() 方法重新设置键盘,实现的代码如下:

// 0-9 的数字

private final List keyCodes = Arrays.asList(

'0', '1', '2', '3', '4', '5', '6', '7', '8', '9');

/**

* 随机打乱数字键盘上显示的数字顺序。

*/

public void shuffleKeyboard() {

Keyboard keyboard = getKeyboard();

if (keyboard != null && keyboard.getKeys() != null

&& keyboard.getKeys().size() > 0) {

// 随机排序数字

Collections.shuffle(keyCodes);

// 遍历所有的按键

List keys = getKeyboard().getKeys();

int index = 0;

for (Keyboard.Key key : keys) {

// 如果按键是数字

if (key.codes[0] != KEYCODE_EMPTY

&& key.codes[0] != Keyboard.KEYCODE_DELETE) {

char code = keyCodes.get(index++);

key.codes[0] = code;

key.label = Character.toString(code);

}

}

// 更新键盘

setKeyboard(keyboard);

}

}

调用 shuffleKeyboard 即可生成随机的键盘。

最终实现的效果如下:

随机键盘

踩坑

1. 点击按键的放大镜效果提示

软键盘默认点击按键时会显示放大镜效果的提示,如果不需要可以使用 setPreviewEnabled(false) 设置不显示提示。

可以在布局中使用 android:keyPreviewLayout 指定提示文字的布局。

2. 按键文字不清晰

软键盘按键默认带有阴影效果,会导致文字不清楚,可以使用下面方式去掉阴影:

android:shadowColor="@color/transparent"

android:shadowRadius="0"

...

/>

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值