APP中登记时常用的发送验证码的Button,带倒计时重发功能
APP中注册时常用的发送验证码的Button,带倒计时重发功能
finddreams:http://blog.****.net/finddreams/article/details/44174775
注册时我们经常会碰到,给手机发送验证码的功能,点击发送验证码,然后就是显示剩余多少秒之后重新发送验证码,效果图如下:
为了实现这样的效果,当用户点击发送验证码时,显示为剩余多少秒重新发送,同时设置这个Button的状态为不可点击,所以是个灰色背景。等倒计时完了之后,把Button的状态置为可以点击状态。Android中内置的普通的Button是达不到要求的,我们需要拓展,所以需要自定义一个Button,代码如下:
/**
* @Description:发送验证码的button,带有倒计时,以及在发送的过程中不可点击;
* 调用方式 view.startTickWork()方法即可;
* @author http://blog.****.net/finddreams
*/
public class SendValidateButton extends Button {
private static final int DISABLE_TIME = 60;
private static final int MSG_TICK = 0;
private Timer mTimer = null;
private TimerTask mTask = null;
private int mDisableTime = DISABLE_TIME; // 倒计时时间,默认60秒
private int mEnableColor = Color.WHITE;
private int mDisableColor = Color.GRAY;
private String mEnableString = "获取验证码";
private String mDisableString = "剩余";
private String Second = "秒";
private boolean mClickBle = true;
private SendValidateButtonListener mListener = null;
public int getmDisableTime() {
return mDisableTime;
}
public int getmEnableColor() {
return mEnableColor;
}
public void setmEnableColor(int mEnableColor) {
this.mEnableColor = mEnableColor;
this.setTextColor(mEnableColor);
}
public int getmDisableColor() {
return mDisableColor;
}
public void setmDisableColor(int mDisableColor) {
this.mDisableColor = mDisableColor;
}
public String getmEnableString() {
return mEnableString;
}
public boolean isDisable() {
if (mDisableTime > 0) {
return true;
}
return false;
}
public void setmEnableString(String mEnableString) {
this.mEnableString = mEnableString;
if (this.mEnableString != null) {
this.setText(mEnableString);
}
}
public String getmDisableString() {
return mDisableString;
}
public void setmDisableString(String mDisableString) {
this.mDisableString = mDisableString;
}
public void setmListener(SendValidateButtonListener mListener) {
this.mListener = mListener;
}
private Handler mHandler = new Handler(Looper.getMainLooper()) {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case MSG_TICK:
tickWork();
break;
default:
break;
}
super.handleMessage(msg);
}
};
public SendValidateButton(Context context, AttributeSet attrs) {
super(context, attrs);
initView();
}
private void initView() {
this.setText(mEnableString);
this.setGravity(Gravity.CENTER);
this.setTextColor(mEnableColor);
initTimer();
this.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
if (mListener != null && mClickBle)
{
// startTickWork();
mListener.onClickSendValidateButton();
}
}
});
}
private void initTimer() {
mTimer = new Timer();
}
private void initTimerTask() {
mTask = new TimerTask()
{
@Override
public void run()
{
mHandler.sendEmptyMessage(MSG_TICK);
}
};
}
public void startTickWork() {
if (mClickBle) {
mClickBle = false;
SendValidateButton.this.setText(mDisableString + mDisableTime
+ Second);
this.setEnabled(false);
SendValidateButton.this.setTextColor(mDisableColor);
initTimerTask();
mTimer.schedule(mTask, 0, 1000);
}
}
/**
* 每秒钟调用一次
*/
private void tickWork() {
mDisableTime--;
this.setText(mDisableString + mDisableTime + Second);
if (mListener != null)
{
mListener.onTick();
}
if (mDisableTime <= 0)
{
stopTickWork();
}
}
public void stopTickWork() {
mTask.cancel();
mTask = null;
mDisableTime = DISABLE_TIME;
this.setText(mEnableString);
this.setTextColor(mEnableColor);
this.setEnabled(true);
mClickBle = true;
}
public interface SendValidateButtonListener {
public void onClickSendValidateButton();
public void onTick();
}
}
然后我们只需要在用到地方引用一下即可:
<com.finddreams.view.SendValidateButton
android:id="@id/getcode_btn"
android:textColor="@color/white"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:padding="5dip"
android:background="@drawable/bg_btn_shape_login"
android:text="发送验证码"
android:textSize="16sp" />
我们来看一下自定义Button的background的选择器bg_btn_shape_login.xml是如何做的:
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true"><shape android:shape="rectangle">
<stroke android:width="1.0px" android:color="#ffd3dde6" />
<corners android:bottomLeftRadius="5.0dip" android:bottomRightRadius="5.0dip" android:topLeftRadius="5.0dip" android:topRightRadius="5.0dip" />
<gradient android:angle="270.0" android:endColor="#ff0e9379" android:startColor="#ff0e9379" />
</shape></item>
<item android:state_focused="true"><shape android:shape="rectangle">
<gradient android:angle="270.0" android:endColor="#ff0e9379" android:startColor="#ff0e9379" />
<stroke android:width="1.0px" android:color="#ffd3dde6" />
<corners android:bottomLeftRadius="5.0dip" android:bottomRightRadius="5.0dip" android:topLeftRadius="5.0dip" android:topRightRadius="5.0dip" />
</shape></item>
<item android:state_enabled="false"><shape android:shape="rectangle">
<gradient android:angle="270.0" android:endColor="#ffe8ecef" android:startColor="#ffe8ecef" />
<stroke android:width="1.0px" android:color="#ffd3dde6" />
<corners android:bottomLeftRadius="5.0dip" android:bottomRightRadius="5.0dip" android:topLeftRadius="5.0dip" android:topRightRadius="5.0dip" />
</shape></item>
<item>
<shape android:shape="rectangle">
<gradient android:angle="270.0" android:endColor="#2B86E3" android:startColor="#2B86E3" />
<stroke android:width="1.0px" android:color="#ffd3dde6" />
<corners android:bottomLeftRadius="5.0dip" android:bottomRightRadius="5.0dip" android:topLeftRadius="5.0dip" android:topRightRadius="5.0dip" />
</shape>
</item>
</selector>
这样就可以实现发送验证码的Button功能了,是不是很简单?当然应该还是有其他实现形式的,大家有兴趣的话可以自己去琢磨一下。
- 2楼tzr0330前天 11:17
- 楼主,我也做过发送验证码的Button。个人感觉用一个普通的Button再加上handler更改Button上的text可能更简单一些,写一个自定义的好麻烦啊
- Re: finddreams前天 11:23
- 回复tzr0330n写自定义的Button的好处,是封装之后可以很方便的迁移使用,用起来很简单。
- Re: tzr0330前天 11:32
- 回复finddreamsn也是,写了以后可以拿过来随便用。
- 1楼u010850027前天 15:26
- 移动互联时代,梦想一定是要有的
- Re: finddreams前天 17:07
- 回复u010850027n你也是有梦想的人呐!