CountDownTimer倒计时

            短信验证码倒计时是一个在app端再常见不过的功能了,要实现倒计时,写法有很多,有用handler来做的,也有用timer来做的,当然现在的Rxjava里面的Observable的interval方法也可以做这样子的事情,后来会发现其实android已经给了一个很适合做倒计时的控件CountDownTimer;

            看下官方的解释: Schedule a countdown until a time in the future, with regular notifications on intervals along the way.大致的意思就是在未来的一段时间之内计划一个倒计时,在这个过程中的每一个间隔都会发送出通知;看来其是很契合我们短信验证码的使用场景的呀;在看官方的例子:

           

  Example of showing a 30 second countdown in a text field:
  new CountDownTimer(30000, 1000) {
 
      public void onTick(long millisUntilFinished) {
          mTextField.setText("seconds remaining: " + millisUntilFinished / 1000);
      }
      public void onFinish() {
          mTextField.setText("done!");
      }
   }.start();
上面的第一个参数30000就是倒计时的总时长,毫秒为单位了,后面的1000则是倒计时的间隔,同样单位也是毫秒,方法onTick则是会在每次间隔都会被调用,而onFInish则是在倒计时结束时候会被调用,可以看到两个方法也都是在ui线程执行的,所以可以刷新ui。

         在使用的过程中会发现,我们有时候会根据业务需求取消倒计时,会发现在5.0以下手机上,取消不好使,是的,是有个bug存在,看那个代码所谓的cancel方法其实就是将消息从handler中移除了,但是在onTick执行时候,这个即使移除也无法生效,所以在5.0及其以上时候CountDownTimer类增加了一个mCancelled参数,用来控制是否要继续倒计时

调用cancel方法时候,其为false,而它为false时候,则不在sendMessageDelayed了,所以倒计时也就停止了。这个类算是说完了。下面看下自己写的一个封装类:

          

/**
 * 验证码倒计时60s
 * Created by hexiaopang on 2017/5/22 18:52.
 */
public class CountTimeUtils  extends CountDownTimer {
    private TextView resendTv;
    private boolean isCanClick = true;
    //实例化静态常量
    public static final CountTimeUtils countTime = new CountTimeUtils(60 * 1000,1000);
    // 参数依次为总时长,和计时的时间间隔
    public CountTimeUtils(long millisInFuture, long countDownInterval) {
        super(millisInFuture, countDownInterval);
    }

    public void setTextView(TextView resend,String className){
        resendTv = resend;
        //如果之前进入的类名不为空,且当前进入的类名不为空,且两者不相同,那么则取消当前正在进行的倒计时,如果在倒计时的话
        if(!TextUtils.isEmpty(UserSPUtils.prfcounttimer.get()) && !TextUtils.isEmpty(className) && !UserSPUtils.prfcounttimer.get().equals(className)){
            countTime.cancel();
            isCanClick = true;
        }
        if(!TextUtils.isEmpty(className)){
            UserSPUtils.prfcounttimer.set(className);
        }
        if(!isCanClick){
            resendTv.setTextColor(BaseApplication.getInstance().getResources().getColor(R.color.color_b3b3b3));
        } else {
            resendTv.setTextColor(BaseApplication.getInstance().getResources().getColor(R.color.color_3295f9));
        }
    }

    //倒计时进行时
    @Override
    public void onTick(long l) {
        if(resendTv != null){
            resendTv.setText("剩余"+(l / 1000)+"s");
        }
        isCanClick = false;
    }

    //重置为可点击
    public void reset(){
        countTime.cancel();
        isCanClick = true;
        if(resendTv != null){
            resendTv.setTextColor(BaseApplication.getInstance().getResources().getColor(R.color.color_3295f9));
        }
    }

    //倒计时结束
    @Override
    public void onFinish() {
        if(resendTv != null){
            resendTv.setText("获取验证码");
            resendTv.setTextColor(BaseApplication.getInstance().getResources().getColor(R.color.color_3295f9));
        }
        isCanClick = true;
    }
    //开始倒计时,不要在外部调用start方法
    public void startCount(){
        isCanClick = false;
        resendTv.setTextColor(BaseApplication.getInstance().getResources().getColor(R.color.color_b3b3b3));
        countTime.start();
    }
    //当前 倒计时 文本是否可以点击。在倒计时过程中是不可以点击的
    public boolean canClick(){
        return isCanClick;
    }
}
        其实代码里面的注释写的也比较清楚了。这个类功能就是对于验证码的发送做了一些封装,setTextView方法就是把需要倒计时的textview和此textview所在类的类名传入进来,为啥传入类名呢?我们写验证码的目的就是为了防止用户在一段时间一般都是60秒内重复获取验证码,即使退出了这个页面再次进入,但是如果用户进了两个不同的需要发送短信验证码,那么其实倒计时不应该继续了,所以用了不同的类名做了区分,当然在退出时候也是要清空验证码,对于倒计时过程中的颜色也做了区分。如果自己不需要可以去掉;开始倒计时时候需要调用startCount,不能直接调用start方法,因为里面也是有isCanClick的判断,因为倒计时时候肯定是不能点击重新获取的呀。其中UserSPUtils是自己的一个sharedpreferences类了,get就是取值。

       以上就是本次内容,有问题欢迎讨论。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值