Как удалить все обратные вызовы из обработчика?
у меня есть проводник из моей под-деятельности, которая была вызвана главным активность. Этот обработчик используется подклассами для postDelay
некоторые Runnables, и я не могу ими управлять. Теперь, в onStop
событие, мне нужно удалить их перед завершением действия (как-то я назвал finish()
, но он все равно звонит снова и снова). Есть ли возможность удалить все вызовы из обработчиков?
5 ответов:
по моему опыту называя это работал отлично!
handler.removeCallbacksAndMessages(null);
в документах для removeCallbacksAndMessages он говорит...
удалите все ожидающие сообщения обратных вызовов и отправленных сообщений, объект которых является токеном. если маркер
null
все вызовы и сообщения будут удалены.
для любого конкретного
Runnable
умHandler.removeCallbacks()
. Обратите внимание, что он используетRunnable
сам экземпляр, чтобы определить, какие обратные вызовы отменить регистрацию, поэтому, если вы создаете новый экземпляр каждый раз, когда создается сообщение, вам нужно убедиться, что у вас есть ссылки на точноеRunnable
отменить. Пример:Handler myHandler = new Handler(); Runnable myRunnable = new Runnable() { public void run() { //Some interesting task } };
можно назвать
myHandler.postDelayed(myRunnable, x)
чтобы отправить еще один обратный вызов в очередь сообщений в других местах вашего кода и удалить все ожидающие обратные вызовы с помощьюmyHandler.removeCallbacks(myRunnable)
к сожалению, вы не можете просто "очистить" весь
MessageQueue
наHandler
, даже если вы сделаете запросMessageQueue
объект, связанный с ним, потому что методы добавления и удаления элементов защищены пакетом (только классы в android.пакет ОС может вызвать их). Возможно, вам придется создать тонкийHandler
подкласс для управления спискомRunnable
s по мере их размещения / выполнения...или посмотрите на другую парадигму для передачи ваших сообщений между каждымActivity
надеюсь, что это поможет!
Если у вас нет выполняемых ссылок, при первом обратном вызове получите obj сообщения и используйте removeCallbacksAndMessages () удалить все обратные вызовы.
определите новый обработчик и runnable:
private Handler handler = new Handler(Looper.getMainLooper()); private Runnable runnable = new Runnable() { @Override public void run() { // Do what ever you want } };
сообщение о задержке вызова:
handler.postDelayed(runnable, sleep_time);
удалите обратный вызов из вашего обработчика:
handler.removeCallbacks(runnable);
на самом деле здесь есть небольшой, но очень важный момент. Вы должны определить
Handler
иRunnable
только в первый раз. На самом делеremoveCallbacks(runnable)
работает правильно, но если вы определяете их каждый раз, вы не можете обрабатывать их.ложным образом :
public class FooActivity extends Activity { private void handleSomething(){ Handler handler = new Handler(); Runnable runnable = new Runnable() { @Override public void run() { doIt(); } }; if(shouldIDoIt){ //doIt() works after 3 seconds. handler.postDelayed(runnable, 3000); } else { handler.removeCallbacks(runnable); } } public void onClick(View v){ handleSomething(); } }
если вы называете
onClick(..)
метод, вы никогда не остановитьdoIt()
вызов метода перед его вызовом. Потому что каждый раз создаетnew Handler
иnew Runnable
экземпляров. Таким образом, вы потеряли необходимые ссылки, которые принадлежат проводник и runnable экземпляров.истинный путь :
public class FooActivity extends Activity { Handler handler = new Handler(); Runnable runnable = new Runnable() { @Override public void run() { doIt(); } }; private void handleSomething(){ if(shouldIDoIt){ //doIt() works after 3 seconds. handler.postDelayed(runnable, 3000); } else { handler.removeCallbacks(runnable); } } public void onClick(View v){ handleSomething(); } }
таким образом, вы не потеряли актуальных ссылок и
removeCallbacks(runnable)
успешно работает.ключевая фраза заключается в том, что 'определите их как глобальные в вашем
Activity
илиFragment
что вы используете'.