android 延时执行任务

最后更新于:2022-04-01 20:09:13

~~~ package com.example.delaydemo; import java.util.Timer; import java.util.TimerTask; import android.os.Bundle; import android.os.Handler; import android.app.Activity; import android.util.Log; import android.view.Menu; public class MainActivity extends Activity { //非UI线程不能更新UI需要借助Handler Handler handler =new Handler() { public void handleMessage(android.os.Message msg) { setContentView(R.layout.main); }; }; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.welcome); //第一种方法就是启动一个子线程做加载数据之类的耗时操作 //做完之后使用handler通知主线程更新UI // new Thread(new Runnable() { // @Override // public void run() { // // TODO Auto-generated method stub // try { // Thread.sleep(4000); // } catch (InterruptedException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } // handler.sendEmptyMessage(0); // } // }).start(); //第二种方法 //直接使用handler,这里可以更新UI,原因是new Handler()相当于new Handler(getMainLooper()) //下面的Log打印的是main 说明还是运行在主线程中 // new Handler().postDelayed(new Runnable() // { // @Override // public void run() { // // TODO Auto-generated method stub // setContentView(R.layout.main); // Log.i("MainActivity", Thread.currentThread().getName()); // } // }, 4000); Timer timer = new Timer(); timer.schedule(task, 4000); //schedule(TimerTask task, long delay) //在延时delay毫秒后执行task。并没有重复执行 // schedule(TimerTask task, long delay, long period) //在延时delay毫秒后重复的执行task,周期是period毫秒。 //也就是说在delay毫秒后每隔period毫秒执行一次task //schedule(TimerTask task, Date time) //在指定的时间执行一次 } //第三种方法 //使用TimerTask和handler TimerTask task = new TimerTask() { @Override public void run() { // TODO Auto-generated method stub handler.sendEmptyMessage(0); //这里打印的是 Timer-0 说明不是运行在主线程中 //若在这里直接使用setContentView(R.layout.main); //会报CalledFromWrongThreadException: Only the original thread that created a //view hierarchy can touch its views.错误 Log.i("MainActivity", Thread.currentThread().getName()); } }; } ~~~ 除了上面3种方法其实还可以使用AlarmManager来实现延时执行或重复执行,只是这种方法有点繁琐,是用广播机制实现的,对于循环执行的任务,如果需要停止执行的话,必须执行closeAlarm()方法,不然即使是退出了程序,这个任务还是会一直执行。 ~~~ package com.example.delaydemo; import java.util.Calendar; import android.app.AlarmManager; import android.app.PendingIntent; import android.content.Context; import android.content.Intent; import android.widget.Toast; public class Alarm { /** * delay秒后执行一次 * @param context * @param delay */ public Alarm(Context context,int delay) { Intent intent =new Intent(context, AlarmReceiver.class); intent.setAction("com.alarm.justonce"); PendingIntent sender= PendingIntent.getBroadcast(context, 0, intent, 0); Calendar calendar=Calendar.getInstance(); calendar.setTimeInMillis(System.currentTimeMillis()); calendar.add(Calendar.SECOND, delay); AlarmManager alarm=(AlarmManager)context.getSystemService(context.ALARM_SERVICE); alarm.set(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(), sender); Toast.makeText(context, delay+"后alarm开启", 2000).show(); } /** * 到firstTime 后 以period周期执行 * @param context * @param firstTime * @param period */ public Alarm(Context context,long firstTime,long period) { Intent intent =new Intent(context, AlarmReceiver.class); intent.setAction("com.alarm.repeating"); PendingIntent sender=PendingIntent .getBroadcast(context, 0, intent, 0); //开始时间 long firstime=firstTime; AlarmManager am=(AlarmManager)context.getSystemService(context.ALARM_SERVICE); //period秒一个周期,不停的发送广播 am.setRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP , firstime, period*1000, sender); Toast.makeText(context, firstTime+"后alarm开启", 2000).show(); } /** * 取消周期执行任务 * @param context */ public void closeAlarm(Context context) { Intent intent =new Intent(context, AlarmReceiver.class); intent.setAction("repeating"); PendingIntent sender=PendingIntent .getBroadcast(context, 0, intent, 0); AlarmManager alarm=(AlarmManager)context.getSystemService(context.ALARM_SERVICE); alarm.cancel(sender); } } ~~~ 广播接受器,别忘了在Manifest中注册 ~~~ package com.example.delaydemo; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.widget.Toast; public class AlarmReceiver extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { // TODO Auto-generated method stub if(intent.getAction().equals("com.alarm.justonce")) { Toast.makeText(context, "justonce alarm", 2000).show(); } else { Toast.makeText(context, "repeating alarm", 2000).show(); } } } ~~~ 最后附上程序:[http://download.csdn.net/detail/tangnengwu/7217595](http://download.csdn.net/detail/tangnengwu/7217595)
';