4

ネストされた postDelayed を使用しようとしています。これは、5 分後に何かを実行し、30 秒後に停止し、別のことを行い、最初からサイクル内の両方のイベントを繰り返す必要があるためです。私はそれを正しく理解できないようです。

私がソファーを持っているコード:

private long EnabledAfter  = 300000; // 5 minutes
private long DisabledAfter = 30000;  // 30 seconds

public void start_timers(){
    on_delayed(EnabledAfter);
}//end method

private void on_delayed(long period_off){       
    Delayed = new Runnable() {
        public void run() {                                                     
            something.enable(context);                          
            something.enable_else(context, true);       
            off_delayed(DisabledAfter); // and disable both again delayed

            Handler.postDelayed(Delayed, EnabledAfter);
        }
    };
    Handler.postDelayed(Delayed, EnabledAfter);
}//end method

private void off_delayed(long period_on){       
    Delayed = new Runnable() {
        public void run() {
            something.disable(context);                                 
            something.disable_else(context, false); 
            on_delayed(period_on); // start the proces again from the start...

            //Handler.postDelayed(Delayed, DisabledAfter);              
        }
    };
    Handler.postDelayed(Delayed, period_on);
}//end method

これに関する問題は、最初の実行では問題なく実行されますが、その後、互いに重なり合っているように見えます...そしてすべての遅延が中断されます。Runnable正確に 5 分 30 秒で両方の s を実行してから、プロセスを繰り返す必要があります。

4

1 に答える 1

8

このコードを数回実行した後の最終的な結果はHandler、各Runnable. 上記のように:

  1. 最初の on_delayed 投稿 1 実行可能
  2. そのランナブルが起動し、2 つのランナブル (1 つは off_delayed に、もう 1 つは run() から戻る前) を送信します。
  3. これらの 2 つの Runnables が起動すると、4 つが作成されるため、これは増加し続けます。

また、同じキューに複数回投稿できるという事実を利用しRunnableていません。毎回新しく作成する必要はありません。これは、アクションをキャンセルする場合に不可欠です。これは、remove メソッドHandlerが一致するすべてのインスタンスを探してキューから削除するためです。代わりに次のようなことを試してみてください:

private long EnabledAfter  = 300000; // 5 minutes
private long DisabledAfter = 30000;  // 30 seconds

private Runnable Enabler = new Runnable() {
    public void run() {                                                     
        something.enable(context);                          
        something.enable_else(context, true);       

        Handler.postDelayed(Disabler, DisabledAfter);
    }
};

private Runnable Disabler = new Runnable() {
    public void run() {
        something.disable(context);                                 
        something.disable_else(context, false); 

        Handler.postDelayed(Enabler, EnabledAfter);              
    }
};

public void start_timers(){
    Handler.postDelayed(Enabler, EnabledAfter);
}//end method

public void stop_timers(){
   Handler.removeCallbacks(Enabler);
   Handler.removeCallbacks(Disabler);
}//end method

Runnableまた、アイテムのすべてのインスタンスをキューから削除することで、タイマー操作をキャンセルするために使用できるメソッドをもう 1 つ追加しました。

HTH

于 2012-06-25T22:03:28.327 に答える