Java 如何停止 Handler Runnable?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/18671067/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-12 10:03:26  来源:igfitidea点击:

How to stop Handler Runnable?

javaandroidmultithreadingperformanceandroid-handler

提问by user2745636

I am using a handler in the following program and I want to stop it when i=5 but the handler doesn't stop and run continuously.

我在以下程序中使用了一个处理程序,我想在 i=5 时停止它,但处理程序不会停止并连续运行。

   b1.setOnClickListener(new OnClickListener() {

        public void onClick(View v) {
            handler = new Handler();
           runnable = new Runnable() {
                 public void run() {

                    try {
                        Toast.makeText(getApplicationContext(), "Handler is working", Toast.LENGTH_LONG).show();
                        System.out.print("Handler is working");

                       if(i==5){
                           //Thread.currentThread().interrupt();
                            handler.removeCallbacks(runnable);


                            System.out.print("ok");
                                        Toast.makeText(getApplicationContext(), "ok", Toast.LENGTH_LONG).show();
                        }
                       i++;
                    } catch (Exception e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    } 
                   handler.postDelayed(this, 5000); 

               }
           };
           handler.postDelayed(runnable, 5000);
           //return;
        }
    });

回答by Ahmed Ekri

protected void onStop() {
    super.onStop();
    handler.removeCallbacks(runnable);
}

you can stop it like this

你可以像这样停止

回答by M-WaJeEh

Because you call postDelayed()again after removing call backs. Please use this code:

因为您postDelayed()在删除回调后再次调用。请使用此代码:

final Handler handler = new Handler();
final Runnable runnable = new Runnable() {
         public void run() {
               Log.d("Runnable","Handler is working");
               if(i == 5){ // just remove call backs
                    handler.removeCallbacks(this); 
                    Log.d("Runnable","ok");
                } else { // post again
                    i++;
                    handler.postDelayed(this, 5000); 
                }
       }
   };

//now somewhere in a method
 b1.setOnClickListener(new OnClickListener() {
    public void onClick(View v) {
        handler.removeCallbacks(runnable); 
        handler.postDelayed(runnable, 5000); 
    }
});

回答by Glenn Pavel

I found a solution which works for me. This is an example of code, where I expect a timer stop, but I saw it was alive, even if I was out of activity:

我找到了一个对我有用的解决方案。这是一个代码示例,我希望计时器停止,但我看到它还活着,即使我没有活动:

boolean bFlagForceExit = false; 
Handler timerHandler = new Handler();
private   Runnable timerRunnable = new Runnable() {
    @Override
    public void run() {

        if  (bFlagForceExit )
    MyProcessForExit(); 

        if (bSomeflagForRunAction)
            RunProcess();

        timerHandler.postDelayed(this, MILISEGUNDOS_ESPERA);        }
};


private void  MyProcessForExit()
{
    timerHandler.removeCallbacks(timerRunnable);
// close activity or whatever
finish();
}


private void  RunProcess()
{
   // action that i do when tick 
// time to leave or stop
bFlagForceExit = true;
}

Then I found that this works if removeCallbacks(timerRunnable)was called for other threads, so, I solved the problem like this.

然后我发现如果removeCallbacks(timerRunnable)被其他线程调用,这会起作用,所以,我解决了这样的问题。

boolean bFlagForceExit = false; 
Handler timerHandler = new Handler();
private   Runnable timerRunnable = new Runnable() {
    @Override
    public void run() {

        if  (bFlagForceExit )
        {
    // add a thred for run your stop handler
            new Thread(new Runnable() {
                public void run() {
                    SalirDeProceso();
                }
            }).start();
        }

        if (bSomeflagForRunAction)
            RUnProcess();

        timerHandler.postDelayed(this, MILISEGUNDOS_ESPERA);        }
};

回答by Zod

Just saw this question. I would use CountDownTimer() instead. Run it for 5 seconds total and every second:

刚看到这个问题。我会改用 CountDownTimer() 。总共运行 5 秒,每秒运行一次:

new CountDownTimer(5000, 1000) {
    public void onTick(long milsecRemain) {
        // Code to run every second
        Log.i("Seconds left", String.valueOf(milsecRemain/1000));
}
    public void onFinish() {
        // 10 seconds have passed
    }
}.start();