Das mag spät sein, aber ich hoffe, es hilft jemandem.
Ich war so lange mit dem gleichen Problem beschäftigt. Aber jetzt weiß ich, wie ich dieses Problem lösen kann. Dies ist für alle, die das gleiche Problem haben könnten. Die Leute sagen immer wieder, dass Sie AutoStart aktivieren müssen, aber ich habe es ohne automatischen Start geschafft.
Zunächst einmal ist WakeFullBroadcastaReceiver jetzt veraltet und Sie sollten BroadcastReceiver verwenden. Zweitens müssen Sie den ForegroudService anstelle des BackgroundService verwenden.
Ich werde Ihnen das folgende Beispiel geben:
IntentService.class
public class NotificationService extends IntentService {
//In order to send notification when the app is close
//we use a foreground service, background service doesn't do the work.
public NotificationService() {
super("NotificationService");
}
@Override
public void onCreate() {
super.onCreate();
}
@Override
public int onStartCommand(@Nullable Intent intent, int flags, int startId) {
super.onStartCommand(intent, flags, startId);
//There is no difference in the result between start_sticky or start_not_sticky at the moment
return START_NOT_STICKY;
}
@Override
protected void onHandleIntent(@Nullable Intent intent) {
//TODO check if the app is in foreground or not, we can use activity lifecyclecallbacks for this
startForegroundServiceT();
sendNotification(intent);
stopSelf();
}
/***
* you have to show the notification to the user when running foreground service
* otherwise it will throw an exception
*/
private void startForegroundServiceT(){
if (Build.VERSION.SDK_INT >= 26) {
String CHANNEL_ID = "my_channel_01";
NotificationChannel channel = new NotificationChannel(CHANNEL_ID,
"Channel human readable title",
NotificationManager.IMPORTANCE_DEFAULT);
((NotificationManager)
getSystemService(Context.NOTIFICATION_SERVICE)).createNotificationChannel(channel);
Notification notification = new Notification.Builder(this, CHANNEL_ID)
.setContentTitle("")
.setContentText("").build();
startForeground(1, notification);
}
}
private void sendNotification(Intent intent){
//Send notification
//Use notification channle for android O+
}
}
Starten Sie den Vordergrunddienst in BroadcastReceiver.class
public class AlarmReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Intent service = new Intent(context, NotificationService.class);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
context.startForegroundService(service);
} else {
context.startService(service);
}
}
}
Und die setAlarms mögen das:
public static void setAlarm(Context context, int requestCode, int hour, int minute){
AlarmManager alarmManager =( AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context//same activity should be used when canceling the alarm
, AlarmReceiver.class);
intent.setAction("android.intent.action.NOTIFY");
//setting FLAG_CANCEL_CURRENT makes some problems. and doest allow the cancelAlarm to work properly
PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 1001, intent, 0);
Calendar time = getTime(hour, minute);
//set Alarm for different API levels
if (Build.VERSION.SDK_INT >= 23){
alarmManager.setExactAndAllowWhileIdle(AlarmManager.RTC_WAKEUP,time.getTimeInMillis(),pendingIntent);
}
else{
alarmManager.set(AlarmManager.RTC_WAKEUP,time.getTimeInMillis(),pendingIntent);
}
Dann müssen Sie den Empfänger und den Vordergrundservice im Manifest deklarieren.
<receiver android:name=".AlarmReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.intent.action.NOTIFY">
</action>
</intent-filter>
</receiver>
<service
android:name=".NotificationService"
android:enabled="true"
android:exported="true"></service>
Ich hoffe das hilft jemandem.