关于二维码刷新[自己的小垃圾研究]

今天刚好在写一个在线二维码的刷新,每间隔1分钟进行刷新,android的机制导致了如果android App在后台运行的化,会一直走,这样用户的流量什么的完全耗不起,顾有了下面的小小研究。
导致流量走的比较快的原因如下:
1.访问数据的流量,这个和后端接口查询等有很大的关系,然而本宝并不能怎么样,这里接口端的兄弟可以优化下。
2.多次访问数据会导致流量使用比较多

作为android开发,研究点就在这里的访问次数了,有了方向,应该比较好容易优化了happy,因为本人使用的访问数据框架为 OKHTTp+RXAndroid等观察模式的数据访问框架,顾已经对,请求错误超时等做过一系列的处理。

1.本人首先用了一个简单粗暴的方法谢了一个计时器,这里并没有使用轮询访问

   /***
     * 倒计时
     */
    private CountDownTimer timer = new CountDownTimer(6000, 1000) {

        @Override
        public void onTick(long millisUntilFinished) {
            timerIsStart = true;
            Logs.d(TAG, "倒计时开始--------------->");
        }

        @Override
        public void onFinish() {
            Logs.d(TAG, "timer is onFinish");
            timerIsStart = false;
            timer.cancel();
            //完成之后
            getNetData();
        }
    };

2.拉取数据的方法

比较简单粗暴的方式,这里的getNetData();为本人的一个拉取数据的处理

   /***
     * 拉取网络数据
     */
    private void getNetData() {
        Logs.d(TAG, "getNetData()---------------->");
        Logs.d(TAG, "data is :" + bundle_data + ",id:" + bundle_data.getBusinessId());
        if (bundle_data != null && !StringUtlis.isEmpty(bundle_data.getBusinessId())) {
            String company = "", groupShortName = "", businessId = "", miniLogo = "";
            if (!StringUtlis.isEmpty(bundle_data.getCompany())) {
                company = bundle_data.getCompany();
            }
            if (!StringUtlis.isEmpty(bundle_data.getMiniLogo())) {
                miniLogo = bundle_data.getMiniLogo();
            }
            businessId = bundle_data.getBusinessId();
            groupShortName = bundle_data.getGroupShortName();
            NetService.getInstance().getScanDiscount(company, groupShortName, businessId, miniLogo, new Observer<CommResultBeanVo>() {
                @Override
                public void onSubscribe(Disposable d) {

                }

                @Override
                public void onNext(CommResultBeanVo value) {
                    timeStamp = System.currentTimeMillis();
                    ScanDiscountBean data = new ScanDiscountBean();
                    if (value != null && !StringUtlis.isEmpty(value.getData())) {
                        data = new Gson().fromJson(value.getData(), ScanDiscountBean.class);
                        Logs.d(TAG, "value.getData() is " + value.getData());
                    }
                    scanDiscountBean = data;
                    if (data != null) {
                        if (!StringUtlis.isEmpty(data.getDimensionCodeForShow())) {
                            if (jifenTxt.getText() != null && !StringUtlis.isEmpty(jifenTxt.getText().toString())
                                    && jifenTxt.getText().toString().indexOf("*") == -1) {
                                jifenTxt.setText(data.getAvailablePoint());
                            }
                        }
                        if (!StringUtlis.isEmpty(data.getDimensionCodeForShow())) {
                            qrCodeNumber.setText(data.getDimensionCodeForShow());
                        }
                        if (!StringUtlis.isEmpty(data.getDimensionCode())) {
                            String dimensionCode = data.getDimensionCode();
                            //条形码
                            Bitmap barCodeBitmap = QRCodeUtil.creatBarcode(activity,
                                    dimensionCode, (int) barCodeWidth, (int) barCodeHeight, false);
                            barCodeImg.setImageBitmap(barCodeBitmap);
                            //二维码生成
                            Bitmap qrCodeBitmap = null;
                            try {
                                qrCodeBitmap = QRCodeUtil.createQRCode(dimensionCode, (int) qrCodeWidth);
                            } catch (Exception e) {

                            }
                            qrcodeImg.setImageBitmap(qrCodeBitmap);
                        }
                    }
                    if(!timerIsStart) {
                        timer.start();
                    }
                }

                @Override
                public void onError(Throwable e) {
                    int code = 0;
                    try {
                        code = ((NetException) e).getCode();
                    } catch (Exception error) {
                        code = 0;
                    }
                    if (code == NetException.TOKEN_ERROR) {
                        NetExceptionUtils.getInstance().tokenNetLoginOut(e, activity);
                    } else {
                        if (e != null && !StringUtlis.isEmpty(e.getMessage())) {
                            ToastTools.showShort(activity, e.getMessage());
                        }
                        if(!timerIsStart) {
                            timer.start();
                        }
                    }
                }

                @Override
                public void onComplete() {

                }
            });
        } else {

        }

    }

3.监听前后台运行方法

考虑:当前使用了比较傻瓜式的自写轮询机制,就是开始拉取一次二维码数据,然而开始轮询,接口访问到,再次倒计时。简单粗暴的方式,也比较好控制,下面先写一个监听是否在后台执行的方法,然后在考虑相关其他判断
[这个方法是直接copy之前很久写的]

 /**
     * 程序是否在前台运行
     *
     * @return
     */
    public boolean isAppOnForeground() {
        ActivityManager activityManager = (ActivityManager) getApplicationContext().getSystemService(Context.ACTIVITY_SERVICE);
        String packageName = getApplicationContext().getPackageName();

        List<ActivityManager.RunningAppProcessInfo> appProcesses = activityManager
                .getRunningAppProcesses();
        if (appProcesses == null) {
            return false;
        }
        for (ActivityManager.RunningAppProcessInfo appProcess : appProcesses) {
            if (appProcess.processName.equals(packageName)
                    && appProcess.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) {
                return true;
            }
        }
        return false;
    }

写好,之后,更具页面的生成周期,开始写入前后台判断

    @Override
    protected void onStop() {
        // TODO Auto-generated method stub
        super.onStop();
        if (!isAppOnForeground()) {
            //app 从前台进入后台
            isActive = false;
            timer.cancel();
            Logs.d(TAG, "app 从前台进入后台------");
            //全局变量isActive = false 记录当前已经进入后台
        }
    }

    @Override
    protected void onResume() {
        // TODO Auto-generated method stub
        super.onResume();
        Logs.d(TAG, "onResume()------");
        if (!isActive) {
            //app 从后台唤醒,进入前台
            Logs.d(TAG, "app 从后台唤醒,进入前台------");
            isActive = true;
            if (timeStamp > 0) {
                long lastTime = System.currentTimeMillis();
                if (lastTime - timeStamp > 60 * 1000) {
                    if(!timerIsStart) {
                        getNetData();
                    }
                } else {
                    if(!timerIsStart) {
                        timer.start();
                    }
                }
            } else {
                if(!timerIsStart) {
                    getNetData();
                }
            }
        }
    }

哈哈,前后台监控拉取数据就完成了。

4.打开一个新页面,当前页面倒计时还在走,怎么办

本来以为有上面的操作就ojbk了,然而还需要屏蔽掉在当前页面打开一个activity,并且当前页面没有关闭的情况,定时器一直走,下面是生命周期,屏蔽掉了一些比如oncreate()呀,这样对我没什么卵用的
打开当前activity
onPause() ———> onStop() ———-> onResume()
当前activity在打开一个activity 当前activity为
onPause() ————–> onStop()
关闭打开的activiy回到当前activity 生命周期为:
onRestart() ————–> onResume()
顾决定在onRestart()中添加是否第一个页面是当前activiy并加上开启定时器的判断,
在onStop()中添加是否第一个页面是当前activiy的判断,并关闭定时器
于是有了下面的代码:

 @Override
    protected void onResume() {
        // TODO Auto-generated method stub
        super.onResume();
        Logs.e(TAG,"onResume()------");
        if(AppManager.getAppManager().currentActivity()!=null && AppManager.getAppManager().currentActivity() instanceof ScabDiscountFragmentActivity){
            Logs.d(TAG, "onResume()当前activity 在栈顶------");
            if (!isAppOnForeground()) {
                //app 从后台唤醒,进入前台
                Logs.d(TAG, "app 从后台唤醒,进入前台------");
                isActive = true;
                if (timeStamp > 0) {
                    long lastTime = System.currentTimeMillis();
                    if (lastTime - timeStamp > 60 * 1000) {
                        if(!timerIsStart) {
                            Logs.d(TAG, "onResume()当前activity timeStamp>60*1000 getNetData(); -------");
                            getNetData();
                        }else{
                            Logs.d(TAG, "onResume()当前activity timerIsStart is true -------");
                        }
                    } else {
                        if(!timerIsStart) {
                            timer.start();
                            Logs.d(TAG, "onResume()当前activity timeStamp>0 && timeStamp <60*1000 不执行操作 -------");
                        }
                    }
                } else {
                    if(!timerIsStart) {
                        Logs.d(TAG, "onResume()当前activity timeStamp==0 timer关闭执行拉取数据------");
                        getNetData();
                    }else{
                        Logs.d(TAG, "onResume()当前activity timeStamp==0 不执行操作 -------");
                    }
                }
            }else{
                //在前台操作
                if(!timerIsStart) {
                    Logs.d(TAG, "onResume()当前activity timeStamp==0 timer关闭执行拉取数据------");
                    getNetData();
                }else{
                    Logs.d(TAG, "onResume()当前activity timeStamp==0 不执行操作 -------");
                }
            }
        }else{
            Logs.e(TAG,"onResume()非当前activity---");
            if(timerIsStart){
                Logs.d(TAG, "onResume()非当前activity timer开启执行关闭------");
                timerIsStart=false;
                timer.cancel();
            }else{
                Logs.d(TAG, "onResume()非当前activity timer关闭不开启------");
            }
        }
    }
   @Override
    protected void onStop() {
        // TODO Auto-generated method stub
        super.onStop();
        Logs.e(TAG,"onStop()------------->");
        if(AppManager.getAppManager().currentActivity()!=null && AppManager.getAppManager().currentActivity() instanceof ScabDiscountFragmentActivity){
            //判断当前
            if (!isAppOnForeground()) {
                //app 从前台进入后台
                if(isActive) {
                    isActive = false;
                    timerIsStart=false;
                    timer.cancel();
                }
                Logs.d(TAG, "app 从前台进入后台------");
                //全局变量isActive = false 记录当前已经进入后台
            }
        }else{
            Logs.d(TAG, "当前activity非定栈顶activity------");
            if(timerIsStart) {
                timerIsStart = false;
                timer.cancel();
            }
        }

    }

呵呵,搞定,写好了,开心,商业APP简单粗暴挺好,写一个轮询继麻烦又很消耗性能。简单粗暴ojbk

猜你喜欢

转载自blog.csdn.net/onlymetagain/article/details/79581157