Android alarm is cancelled after closing the application

半城伤御伤魂 提交于 2019-12-17 10:58:45

问题


I have a problem with AlarmManager, I set the code for scheduling a repeating alarm and after I run the application, the alarm runs fine. Even if I click on Home button (and the application is paused), the alarm still runs on its interval.

The problem is if I open the Task Manager and force close the application, then the alarm stops from running.

Is this a normal behavior, is there any way to avoid this and keep the alarm running after closing the application?

The code is below - the method is called by the ApplicationContext class, onCreate().

 private void scheduleAlarm() {
  if (alarmScheduled == true) { return; } // we only need to schedule once.

  int alarmInterval = Def.pref(getApplicationContext()).getInt("alarmInterval", 30);

  final Intent intent = new Intent(getApplicationContext(), CollectorAlarmReceiver.class);
  final PendingIntent pending = PendingIntent.getBroadcast(getApplicationContext(), 0, intent, 0);

  AlarmManager alarmMgr = (AlarmManager) getApplicationContext().getSystemService(Context.ALARM_SERVICE);

  alarmMgr.cancel(pending); // cancel others.

  alarmMgr.setRepeating(AlarmManager.RTC_WAKEUP, System.currentTimeMillis()+1000,
    alarmInterval*1000, pending);

  Def.log(TAG,"scheduleAlarm(): alarm scheduled, interval: "+alarmInterval+" seconds");
  alarmScheduled = true;
 }

Receiver code:

public void onReceive(Context context, Intent intent) {
    Log.i(TAG, "CollectorAlarmReceiver invoked, starting CollectorService in background");

    context.startService(new Intent(context, CollectorService.class));

    Intent collectorService = new Intent(context,CollectorService.class);
    collectorService.putExtra("action", CollectorService.ACTION_BACKGROUND_REQUEST_MESSAGES);

    context.sendBroadcast(collectorService);
}

Thanks!


回答1:


This is normal behaviour. If the user voluntarily force stop the applicaiton, then it should be stopped. Else, you are creating a virus like application.

If you really want, you could write another service which monitors if your other service is running and runs the service if the one is not running. But this will be another application and (you hope) the user wont kill this app using task manager.

Personally, I wouldn't worry. If the user stopped it, they wanted to stop it. Don't annoy the user.




回答2:


I believe @GSree is wrong. There's a simple way to achieve this. Just use a custom action. Here's how:

First, define a custom action name, such as:

public static final String MY_ACTION = "com.sample.myaction"

Then create a BroadcastReceiver:

public class MyAlarmReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        if (intent.getAction().equals(MY_ACTION)) {
            // Do something here
        }
    }    
}

Register the receiver on your AndroidManifest.xml:

<receiver android:name="com.sample.MyAlarmReceiver">
    <intent-filter>
        <action android:name="com.sample.myaction"/>
    </intent-filter>
</receiver>

Then, to setup the alarm, use the following PendingIntent:

Intent i = new Intent(MY_ACTION);
PendingIntent pi = PendingIntent.getBroadcast(getApplicationContext(), 0, i, 0);

There may be other ways to do it, but I tried this solution and the BroadcastReceiver gets called even if I force-quit my app from the shell.

Notice how this solution does not require you to create a service.




回答3:


I've done this a few times, but wonder why ya'll are assigning a requestCode of 0; I'd think that giving your alarm a unique number would help a lot.




回答4:


That's a normal behavoiur ! The alarm will stop working when your app goes to onDestroy().




回答5:


Forcing your application to close is not the correct way to close an app and may give you incorrect behavior.

This question might also be of some help.




回答6:


I have been able to do exactly what you need. Even if you stop the application through the running tab in the application manager tool, the service restarts itself. The only way to kill it is throught the force stop button next to the unistall option in application manager. Basically you call the Service directly. Here is My Code:

public class TestService extends Service {

@Override
public int onStartCommand(Intent intent, int flags, int startId) {
        Toast.makeText(this, "Ejecutando Servicio ...", Toast.LENGTH_SHORT).show();
    return Service.START_NOT_STICKY;    
    }

@Override
    public void onCreate() {
      super.onCreate();
      Toast.makeText(this, "Iniciando Servicio ...", Toast.LENGTH_SHORT).show();
}

    @Override
    public void onDestroy() {
      super.onDestroy();
      Toast.makeText(this, "Deteniendo Servicio ...", Toast.LENGTH_SHORT).show();
}   

On client activity write the following code:

            Calendar cal = Calendar.getInstance();
        Intent intent = new Intent(this,TestService.class);
        PendingIntent pIntent = PendingIntent.getService(this.getApplicationContext(), 0, intent, 0);
        alarm=  (AlarmManager) getSystemService(Context.ALARM_SERVICE);
        alarm.setRepeating(AlarmManager.RTC_WAKEUP,cal.getTimeInMillis(), 3*1000, pIntent);

And declare the service in manifest:

        <service
      android:name="TestService"
      android:icon="@drawable/ic_launcher"
      android:label="TestService"
      >
    </service>         



回答7:


Add

<receiver android:name=".AlarmReceiver" android:process=":remote" />

in manifest file. The alarm will work even if app is killed.



来源:https://stackoverflow.com/questions/4643850/android-alarm-is-cancelled-after-closing-the-application

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!