Android服务重新创建
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android服务重新创建相关的知识,希望对你有一定的参考价值。
我正在编写一个应用程序,以便在首选日期和时间通知用户(假设每个月的第一天)
我搜索并阅读了一些帖子,建议我使用AlarmManager
和BroadcastReceiver
和Service
它的工作原理,但Service
似乎创建了多次,Notification
随机显示。我添加了log.i()
来跟踪它。它收到了BOOT_RECEIVED
或首先启动了应用程序的Service
,初始服务和创建服务被记录,通知正确和正常显示。一段时间后,再次创建服务而没有销毁日志,并再次显示通知。这是正常的吗?
日志
02-23 20:17:15.235: I/CMP(19210): Init Service
02-23 20:17:15.235: I/CMP(19210): Start Service
02-23 20:17:15.285: I/CMP(19210): Create Service
02-23 20:17:15.295: I/CMP(19210): 10157
02-23 20:17:15.295: I/CMP(19210): ON START COMMAND
02-23 20:17:25.785: I/CMP(19210): action_notify
02-23 20:21:12.415: I/CMP(23666): Create Service
02-23 20:21:12.515: I/CMP(23666): 10157
02-23 20:21:12.525: I/CMP(23666): ON START COMMAND
02-23 20:21:22.515: I/CMP(23666): action_notify
服务类
public class AppService extends Service {
@Override
public void onCreate() {
super.onCreate();
Log.i("CMP", "Create Service");
Utility.scheduleNotification(this.getBaseContext());
}
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
super.onStartCommand(intent, flags, startId);
Log.i("CMP", "ON START COMMAND");
return START_STICKY;
}
@Override
public void onDestroy() {
super.onDestroy();
Log.i("CMP", "Destroy Service");
Utility.cancelScheduleNotification(getBaseContext());
}
}
广播接收器
public class AlarmReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(Intent.ACTION_BOOT_COMPLETED)) {
Common.setSettings(context);
if (Utility.isEnabledService(context)) {
Utility.initService(context);
Utility.startService(context);
}
} else if (intent.getAction().equals(Utility.ACTION_NOTIFY)) {
Log.i("CMP", "action_notify");
Utility.genNotify(context, intent);
}
}
}
一些功能
public static void scheduleNotification(Context context) {
Common.setSettings(context);
if (ScheduleTask.getAlarmManager() == null)
ScheduleTask.initAlarmManager(context);
Calendar cal = Calendar.getInstance();
cal.Add(Calendar.SECOND, 10);
Intent intent = new Intent(context, AlarmReceiver.class);
intent.setAction(Utility.ACTION_NOTIFY);
intent.putExtra("Job", i);
intent.putExtra("Name", name);
intent.addCategory(String.format("Job_$1%s", name));
PendingIntent pi = PendingIntent.getBroadcast(context, i, intent, PendingIntent. FLAG_ONE_SHOT);
ScheduleTask.getAlarmManager().set(AlarmManager.RTC_WAKEUP, cal.getTimeInMillis(), pi);
Log.i("CMP", String.valueOf(pi.getCreatorUid()));
}
public static void genTimeSheetNotify(Context context, Intent intent) {
Intent notificationIntent = new Intent(context, MainActivity.class);
PendingIntent pi = PendingIntent.getActivity(context, 0, notificationIntent, PendingIntent.FLAG_ONE_SHOT);
Bundle extras = intent.getExtras();
Notification notification = new Notification.Builder(context)
.setContentTitle("Test Notify")
.setContentText("Testing Notify")
.setSmallIcon(android.R.drawable.ic_dialog_info)
.setVibrate(new long[] { 0, 100, 200, 300 })
.setLights(0xff00ff00, 100, 100)
.setContentIntent(pi)
.setAutoCancel(true)
.build();
if (Notify.getNotificationManager() == null)
Notify.initNotificationManager(context);
Notify.getNotificationManager().notify(extras.getInt("Job"), notification);
}
public static void genTimeSheetNotify(Context context, Intent intent) {
Intent notificationIntent = new Intent(context, MainActivity.class);
// notificationIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
PendingIntent pi = PendingIntent.getActivity(context, 0, notificationIntent, PendingIntent.FLAG_ONE_SHOT);
Bundle extras = intent.getExtras();
Notification notification = new Notification.Builder(context)
.setContentTitle("TimeSheet Submission")
.setContentText(String.format("Timesheet of %1$s is due today.", extras.get("Name").toString()))
.setSmallIcon(android.R.drawable.ic_dialog_info)
.setVibrate(new long[] { 0, 100, 200, 300 })
.setLights(0xff00ff00, 100, 100)
.setContentIntent(pi)
.setAutoCancel(true)
.build();
if (Notify.getNotificationManager() == null)
Notify.initNotificationManager(context);
Notify.getNotificationManager().notify(extras.getInt("Job"), notification);
}
答案
系统正在终止并重新启动服务(因为它是粘性的)。因此,通知是随机创建的。您需要在onStartCommand()中检查null的意图,因为当系统启动服务时,intent将为null。
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
if(intent != null)
{
//create notification here
}
return START_STICKY;
}
以上是关于Android服务重新创建的主要内容,如果未能解决你的问题,请参考以下文章
Android Honeycomb:如何更改 FrameLayout 中的片段,而不重新创建它们?
Android Honeycomb:如何更改 FrameLayout 中的片段,而不重新创建它们?