Wecker stellen

Alarme (basierend auf AlarmManager Kurs) bieten Ihnen die Möglichkeit, zeitbasierte Vorgänge außerhalb der Lebensdauer der Anwendung. Sie könnten beispielsweise einen Alarm verwenden, um einen lang andauernden Vorgang zu initiieren, wenn Sie einmal täglich einen Dienst starten, um eine Wettervorhersage herunterzuladen.

Alarme haben folgende Eigenschaften:

  • Sie ermöglichen es, Intents zu festgelegten Zeiten und/oder Intervallen auszulösen.

  • Sie können sie zusammen mit Übertragungsempfängern verwenden, um jobs oder WorkRequests zum Ausführen anderer Geschäftsabläufe.

  • Sie werden außerhalb Ihrer Anwendung ausgeführt, sodass Sie sie zum Auslösen von Aktionen ausführen, auch wenn die App nicht ausgeführt wird selbst schläft.

  • Sie helfen Ihnen, den Ressourcenbedarf Ihrer Anwendung zu minimieren. Sie können ohne Timer oder kontinuierlich laufende Dienste auszuführen.

Ungenauen Alarm einstellen

Wenn eine App einen ungenauen Alarm einstellt, löst das System den Alarm irgendwann aus zu erhalten. Ungenaue Alarme bieten gewisse Garantien bezüglich des Timings von unter Berücksichtigung von Energiesparmodus-Einschränkungen wie Stromsparmodus:

Entwickler können die folgenden API-Garantien nutzen, um den Zeitplan ungenaue Alarmausgabe.

Nach einer bestimmten Zeit einen Wecker stellen

Wenn Ihre App set() aufruft, setInexactRepeating(), oder setAndAllowWhileIdle(), wird der Alarm nie vor der festgelegten Auslösungszeit ausgelöst.

Unter Android 12 (API-Level 31) und höher löst das System den Alarm innerhalb eines Stunde der angegebenen Auslösezeit, es sei denn, der Energiesparmodus ist eingeschränkt Energiesparmodus oder Stromsparmodus.

Alarm während eines bestimmten Zeitfensters auslösen

Wenn deine App setWindow() aufruft, wird der Wecker nie ausgelöst, bevor die festgelegten die Auslösungszeit. Sofern keine Einschränkungen zum Energiesparmodus gelten, wird der Alarm innerhalb des angegebenen Zeitfensters ausgeliefert, beginnend mit dem angegebenen Trigger .

Wenn deine App auf Android 12 oder höher ausgerichtet ist, kann das System Aufrufen eines ungenauen Alarms mit Zeitfenster um mindestens 10 Minuten Für Aus diesem Grund werden windowLengthMillis Parameterwerte unter 600000 auf 600000.

In regelmäßigen Abständen einen sich wiederholenden Alarm auslösen

Wenn Ihre App setInexactRepeating() aufruft, löst das System mehrere Alarme aus:

  1. Der erste Alarm wird innerhalb des festgelegten Zeitfensters ausgelöst, beginnend ab bestimmten Trigger-Zeit.
  2. Nachfolgende Alarme werden normalerweise nach dem angegebenen Zeitfenster ausgelöst an. Die Zeit zwischen zwei aufeinanderfolgenden Alarmen kann variieren.

Exakten Wecker stellen

Das System löst einen genauen Alarm zu einem bestimmten Zeitpunkt in der Zukunft aus.

Die meisten Apps können Aufgaben und Ereignisse mit ungenauen Alarmen planen, Anwendungsfälle Wenn der Kern Ihrer App funktioniert, hängt von einem genau abgestimmten Alarm ab – z. B. bei einer Wecker-App. oder eine Kalender-App haben, dann ist es in Ordnung, stattdessen einen exakten Wecker zu verwenden.

Anwendungsfälle, die möglicherweise keine genauen Alarme erfordern

Die folgende Liste zeigt gängige Arbeitsabläufe, für die möglicherweise kein exakter Alarm erforderlich ist:

Timing von Vorgängen während der Lebensdauer deiner App planen
Die Klasse Handler umfasst mehrere gute Methoden zur Verarbeitung von Timing-Vorgängen, wie z. B. n Sekunden, während die App aktiv ist: postAtTime() und postDelayed() Beachten Sie, dass diese APIs von der Systemverfügbarkeit abhängig sind. und nicht Echtzeit.
Geplante Hintergrundarbeiten wie das Aktualisieren der App und das Hochladen von Protokollen
WorkManager bietet die Möglichkeit, zeitgesteuerte regelmäßige Termine zu planen. arbeiten. Sie können ein Wiederholungsintervall und flexInterval (mindestens 15 Minuten) angeben, um detaillierte Laufzeit für die Arbeit definieren.
Vom Nutzer angegebene Aktion, die nach einer bestimmten Zeit ausgeführt werden soll (auch bei Inaktivität)
Einen ungenauen Alarm verwenden. Rufen Sie insbesondere setAndAllowWhileIdle()
Vom Nutzer angegebene Aktion, die nach einer bestimmten Zeit ausgeführt werden soll
Einen ungenauen Alarm verwenden. Rufen Sie insbesondere set()
Eine vom Nutzer angegebene Aktion, die innerhalb eines bestimmten Zeitfensters ausgeführt werden kann
Einen ungenauen Alarm verwenden. Rufen Sie insbesondere setWindow() Wenn deine App auf Android 12 oder höher ausgerichtet ist, Die zulässige Fensterlänge beträgt 10 Minuten.

Möglichkeiten zum Stellen eines exakten Alarms

Mit einer der folgenden Methoden kann Ihre App exakte Alarme einstellen. Diese Methoden so angeordnet, dass diejenigen, die näher am Ende der Liste stehen, zeitkritische Aufgaben zu erledigen, die aber mehr Systemressourcen erfordern.

setExact()

Einen Alarm zu einem fast genauen Zeitpunkt in der Zukunft auslösen, solange andere Energiesparmaßnahmen sind nicht aktiviert.

Mit dieser Methode kannst du exakte Alarme einstellen, es sei denn, deine App ist zeitkritisch sind.

setExactAndAllowWhileIdle()

Einen Alarm zu einem fast genauen Zeitpunkt in der Zukunft auslösen, selbst wenn der Akku spart in Kraft sind.

setAlarmClock()

Einen Alarm zu einem bestimmten Zeitpunkt in der Zukunft auslösen. Diese Alarme sind für Nutzer gut sichtbar ist, passt das System die Lieferdauer nie an. Die erkennt das System diese Alarme als die kritischsten und verliert den Energieverbrauch wenn nötig, um die Alarme auszulösen.

Verbrauch von Systemressourcen

Wenn das System exakte Alarme auslöst, die deine App einstellt, wird das Gerät verbraucht eine Menge Ressourcen, wie beispielsweise die Akkulaufzeit, um einen Energiesparmodus zu aktivieren. Außerdem kann das System diese Anfragen nicht einfach in Batches zusammenfassen. um Ressourcen effizienter zu nutzen.

Wir empfehlen dringend, einen ungenauen Alarm zu erstellen, möglich. Wenn Sie längere Aufgaben erledigen möchten, planen Sie sie mithilfe von WorkManager oder JobScheduler aus dem Wecker BroadcastReceiver Wenn Sie Ihre Arbeit erledigen möchten, während sich das Gerät im Stromsparmodus befindet, erstellen Sie einen ungenauen Alarm setAndAllowWhileIdle(), und einen Job über den Wecker starten.

Deklariere die entsprechende Berechtigung für den exakten Alarm

Wenn deine App auf Android 12 oder höher ausgerichtet ist, musst du die "Wecker und Erinnerungen“ App-Zugriff haben. Deklarieren Sie dazu die SCHEDULE_EXACT_ALARM in der Manifestdatei Ihrer App, wie im folgenden Code-Snippet gezeigt:

<manifest ...>
    <uses-permission android:name="android.permission.SCHEDULE_EXACT_ALARM"/>
    <application ...>
        ...
    </application>
</manifest>

Wenn Ihre App auf Android 13 (API-Level 33) oder höher ausgerichtet ist, können Sie Deklarieren Sie entweder die SCHEDULE_EXACT_ALARM oder die USE_EXACT_ALARM Berechtigung.

<manifest ...>
    <uses-permission android:name="android.permission.USE_EXACT_ALARM"/>
    <application ...>
        ...
    </application>
</manifest>

Die Berechtigungen SCHEDULE_EXACT_ALARM und USE_EXACT_ALARM Sie signalisieren die gleichen Fähigkeiten, werden unterschiedlich gewährt und unterstützen unterschiedliche Anwendungsfälle. Ihre App sollte exakte Alarme verwenden und entweder Berechtigung SCHEDULE_EXACT_ALARM oder USE_EXACT_ALARM, nur wenn ein für den Nutzer sichtbarer Funktionen in Ihrer App erfordern zeitgenaue Aktionen.

USE_EXACT_ALARM

SCHEDULE_EXACT_ALARM

  • Vom Nutzer gewährt
  • Breitere Auswahl an Anwendungsfällen
  • Apps müssen bestätigen, dass die Berechtigung nicht widerrufen wurde

Die Berechtigung SCHEDULE_EXACT_ALARM wird für Neuinstallationen von Apps, die auf Android 13 (API-Level 33) und höher ausgerichtet sind Wenn ein Nutzer eine App überträgt Daten über einen Back-up- und Wiederherstellungsvorgang auf ein Gerät mit Android 14 Die Berechtigung „SCHEDULE_EXACT_ALARM“ wird auf dem neuen Gerät verweigert. Wenn jedoch bereits eine vorhandene App hat, wird diese Berechtigung vorab gewährt, wenn der auf Android 14 aktualisiert.

Hinweis: Wenn der exakte Wecker mit einem OnAlarmListener -Objekt enthält, zum Beispiel mit dem setExact API verwenden, ist die Berechtigung SCHEDULE_EXACT_ALARM nicht erforderlich.

Berechtigung SCHEDULE_EXACT_ALARM verwenden

Im Gegensatz zu USE_EXACT_ALARM muss die SCHEDULE_EXACT_ALARM-Berechtigung die der Nutzer gewährt. Sowohl der Nutzer als auch das System können die Berechtigung „SCHEDULE_EXACT_ALARM“.

Um zu prüfen, ob Ihrer App die Berechtigung gewährt wurde, rufen Sie canScheduleExactAlarms() bevor du versuchst, einen exakten Alarm einzustellen. Wenn die Berechtigung SCHEDULE_EXACT_ALARM wird für Ihre App widerrufen, Ihre App wird beendet und alle zukünftigen exakten Wecker werden abgebrochen. Das bedeutet auch, dass der von canScheduleExactAlarms() bleibt für den gesamten Lebenszyklus deiner App gültig.

Wenn deiner App die Berechtigung SCHEDULE_EXACT_ALARMS gewährt wird, sendet das System ACTION_SCHEDULE_EXACT_ALARM_PERMISSION_STATE_CHANGED Nachricht an alle. Ihre App sollte eine Übertragung implementieren. Empfänger, der den Folgendes:

  1. Bestätigt, dass Ihre App weiterhin den speziellen App-Zugriff hat. Rufen Sie dazu unter canScheduleExactAlarms() Diese Prüfung schützt Ihre App vor dem Fall, dass der Nutzer Ihrer App die und widerruft sie fast unmittelbar danach.
  2. Richtet alle exakten Alarme, die Ihre App benötigt, basierend auf ihrem aktuellen Status neu ein. Diese Logik sollte der Aktion Ihrer App ähneln, wenn sie die ACTION_BOOT_COMPLETED Nachricht an alle.

Nutzer um die Berechtigung SCHEDULE_EXACT_ALARM bitten

<ph type="x-smartling-placeholder">
</ph> Die Option heißt „Einrichten von Weckern und Erinnerungen zulassen“
Abbildung 1: "Wecker und Erinnerungen“ spezieller App-Zugriff in den Systemeinstellungen, auf der Nutzer Ihrer App erlauben können, Wecker

Bei Bedarf können Sie Nutzer auf die Seite Alarme & Erinnerungen im System wie in Abbildung 1 dargestellt. Führen Sie dazu die folgenden Schritte aus:

  1. Erklären Sie dem Nutzer auf der Benutzeroberfläche Ihrer App, warum Ihre App exakte Zeitplanung Alarme.
  2. Rufen Sie einen Intent auf, der den ACTION_REQUEST_SCHEDULE_EXACT_ALARM Intent-Aktion.

Sich wiederholenden Wecker stellen

Durch wiederkehrende Alarme kann das System deine App bei einer wiederkehrenden ein.

Ein schlecht konzipierter Alarm kann den Akku stark beanspruchen und die Server. Daher werden ab Android 4.4 (API-Level 19) alle sich wiederholende Weckrufe sind ungenaue Alarme.

Ein sich wiederholender Alarm hat die folgenden Eigenschaften:

  • Ein Alarmtyp. Weitere Informationen finden Sie unter Alarmtyp auswählen.

  • Eine Auslösungszeit. Wenn die angegebene Auslösezeit in der Vergangenheit liegt, wird der Alarm sofort ausgelöst.

  • Das Intervall des Alarms. Zum Beispiel einmal täglich, stündlich oder alle 5 Minuten.

  • Ein ausstehender Intent, der ausgelöst wird, wenn der Alarm ausgelöst wird. Wenn Sie eine zweiten Alarm, der denselben ausstehenden Intent verwendet, ersetzt er den ursprünglichen Alarm.

Um eine PendingIntent() zu stornieren, FLAG_NO_CREATE an PendingIntent.getService() um eine Instanz des Intents abzurufen (falls vorhanden), und übergeben Sie diesen Intent an AlarmManager.cancel()

Kotlin

val alarmManager =
    context.getSystemService(Context.ALARM_SERVICE) as? AlarmManager
val pendingIntent =
    PendingIntent.getService(context, requestId, intent,
                                PendingIntent.FLAG_NO_CREATE)
if (pendingIntent != null && alarmManager != null) {
  alarmManager.cancel(pendingIntent)
}

Java

AlarmManager alarmManager =
    (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
PendingIntent pendingIntent =
    PendingIntent.getService(context, requestId, intent,
                                PendingIntent.FLAG_NO_CREATE);
if (pendingIntent != null && alarmManager != null) {
  alarmManager.cancel(pendingIntent);
}

Weckertyp auswählen

Einer der ersten Überlegungen bei der Verwendung eines sich wiederholenden Weckers ist der Wecktyp das sein sollte.

Es gibt zwei allgemeine Uhrtypen für Wecker: „Verstrichene Echtzeit“. und "Echtzeituhr" (RTC) Für die verstrichene Zeit wird die „Zeit seit Systemstart“ verwendet als Referenz und die Echtzeituhr verwendet die UTC-Zeit. Das bedeutet, dass ist am besten geeignet, um einen Alarm auf Grundlage der verstrichenen Zeit (für z. B. einen Alarm, der alle 30 Sekunden ausgelöst wird, da er nicht durch Zeitzone oder Sprache. Die Echtzeituhr eignet sich besser für Alarme, die sind vom aktuellen Gebietsschema abhängig.

Beide Typen haben ein „Wakeup“- und besagt, dass die CPU des Geräts aktiviert werden soll, wenn der Bildschirm ist aus. Dadurch wird sichergestellt, dass der Alarm zum geplanten Zeitpunkt ausgelöst wird. Dies ist nützlich, wenn Ihre App zeitabhängig ist. Wenn beispielsweise bestimmte Operation auszuführen. Wenn Sie das Tag Wecker-Version deines Weckertyps aktiviert hast, werden alle wiederkehrenden Wecker ausgelöst. wenn das Gerät das nächste Mal aktiv ist.

Wenn der Alarm nur in einem bestimmten Intervall ausgelöst werden soll (z. B. jede halbe Stunde), verwenden Sie einen der verstrichenen Echtzeittypen. Im Allgemeinen ist die bessere Wahl.

Wenn der Wecker zu einer bestimmten Tageszeit ausgelöst werden soll, wähle eine aus der uhrbasierten Echtzeituhrtypen. Beachten Sie jedoch, dass dieser Ansatz haben einige Nachteile. Die App lässt sich möglicherweise nicht gut in andere Sprachen übersetzen. Wenn der Nutzer die Zeiteinstellung des Geräts ändert, kann dies zu unerwartetem Verhalten führen. in Ihrer App. Die Verwendung von Echtzeituhr-Weckern ist ebenfalls nicht gut skalierbar, wie oben beschrieben. Wir empfehlen, eine „Verstrichene Echtzeit“-Zeit zu verwenden Wecker wenn möglich.

Es gibt folgende Typen:

  • ELAPSED_REALTIME: Löst den ausstehenden Intent basierend auf der Zeit aus, die seit dem Start des Geräts vergangen ist gestartet, aber das Gerät nicht aktiviert. Die Verstrichene Zeit umfasst die Zeit, in der sich das Gerät im Ruhemodus befand.

  • ELAPSED_REALTIME_WAKEUP: Weckt das Gerät auf und löst den ausstehenden Intent nach der angegebenen Dauer aus der Zeit ist seit dem Booten des Geräts vergangen.

  • RTC: Löst den ausstehenden Intent zur angegebenen Zeit aus, aktiviert das Gerät jedoch nicht.

  • RTC_WAKEUP: Wake Gerät so einrichten, dass der ausstehende Intent zur angegebenen Zeit ausgelöst wird.

Beispiele für verstrichene Echtzeit-Alarme

Hier einige Beispiele für die Verwendung von ELAPSED_REALTIME_WAKEUP

Wecke das Gerät in 30 Minuten und alle 30 Minuten, um den Alarm auszulösen. Danach:

Kotlin

// Hopefully your alarm will have a lower frequency than this!
alarmMgr?.setInexactRepeating(
        AlarmManager.ELAPSED_REALTIME_WAKEUP,
        SystemClock.elapsedRealtime() + AlarmManager.INTERVAL_HALF_HOUR,
        AlarmManager.INTERVAL_HALF_HOUR,
        alarmIntent
)

Java

// Hopefully your alarm will have a lower frequency than this!
alarmMgr.setInexactRepeating(AlarmManager.ELAPSED_REALTIME_WAKEUP,
        SystemClock.elapsedRealtime() + AlarmManager.INTERVAL_HALF_HOUR,
        AlarmManager.INTERVAL_HALF_HOUR, alarmIntent);

Aktivieren Sie das Gerät, um in einer Minute einen einmaligen (sich nicht wiederholenden) Wecker auszulösen:

Kotlin

private var alarmMgr: AlarmManager? = null
private lateinit var alarmIntent: PendingIntent
...
alarmMgr = context.getSystemService(Context.ALARM_SERVICE) as AlarmManager
alarmIntent = Intent(context, AlarmReceiver::class.java).let { intent ->
    PendingIntent.getBroadcast(context, 0, intent, 0)
}

alarmMgr?.set(
        AlarmManager.ELAPSED_REALTIME_WAKEUP,
        SystemClock.elapsedRealtime() + 60 * 1000,
        alarmIntent
)

Java

private AlarmManager alarmMgr;
private PendingIntent alarmIntent;
...
alarmMgr = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmReceiver.class);
alarmIntent = PendingIntent.getBroadcast(context, 0, intent, 0);

alarmMgr.set(AlarmManager.ELAPSED_REALTIME_WAKEUP,
        SystemClock.elapsedRealtime() +
        60 * 1000, alarmIntent);

Beispiele für Echtzeit-Wecker

Hier sind einige Beispiele für die Verwendung RTC_WAKEUP

Wecke das Gerät auf, um gegen 14:00 Uhr den Alarm auszulösen. einmal täglich zur selben Zeit wiederholen:

Kotlin

// Set the alarm to start at approximately 2:00 p.m.
val calendar: Calendar = Calendar.getInstance().apply {
    timeInMillis = System.currentTimeMillis()
    set(Calendar.HOUR_OF_DAY, 14)
}

// With setInexactRepeating(), you have to use one of the AlarmManager interval
// constants--in this case, AlarmManager.INTERVAL_DAY.
alarmMgr?.setInexactRepeating(
        AlarmManager.RTC_WAKEUP,
        calendar.timeInMillis,
        AlarmManager.INTERVAL_DAY,
        alarmIntent
)

Java

// Set the alarm to start at approximately 2:00 p.m.
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.set(Calendar.HOUR_OF_DAY, 14);

// With setInexactRepeating(), you have to use one of the AlarmManager interval
// constants--in this case, AlarmManager.INTERVAL_DAY.
alarmMgr.setInexactRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(),
        AlarmManager.INTERVAL_DAY, alarmIntent);

Aktiviere das Gerät, damit der Alarm genau um 8:30 Uhr und alle 20 Minuten ausgelöst wird. Danach:

Kotlin

private var alarmMgr: AlarmManager? = null
private lateinit var alarmIntent: PendingIntent
...
alarmMgr = context.getSystemService(Context.ALARM_SERVICE) as AlarmManager
alarmIntent = Intent(context, AlarmReceiver::class.java).let { intent ->
    PendingIntent.getBroadcast(context, 0, intent, 0)
}

// Set the alarm to start at 8:30 a.m.
val calendar: Calendar = Calendar.getInstance().apply {
    timeInMillis = System.currentTimeMillis()
    set(Calendar.HOUR_OF_DAY, 8)
    set(Calendar.MINUTE, 30)
}

// setRepeating() lets you specify a precise custom interval--in this case,
// 20 minutes.
alarmMgr?.setRepeating(
        AlarmManager.RTC_WAKEUP,
        calendar.timeInMillis,
        1000 * 60 * 20,
        alarmIntent
)

Java

private AlarmManager alarmMgr;
private PendingIntent alarmIntent;
...
alarmMgr = (AlarmManager)context.getSystemService(Context.ALARM_SERVICE);
Intent intent = new Intent(context, AlarmReceiver.class);
alarmIntent = PendingIntent.getBroadcast(context, 0, intent, 0);

// Set the alarm to start at 8:30 a.m.
Calendar calendar = Calendar.getInstance();
calendar.setTimeInMillis(System.currentTimeMillis());
calendar.set(Calendar.HOUR_OF_DAY, 8);
calendar.set(Calendar.MINUTE, 30);

// setRepeating() lets you specify a precise custom interval--in this case,
// 20 minutes.
alarmMgr.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(),
        1000 * 60 * 20, alarmIntent);

Präzision des Weckers festlegen

Wie bereits beschrieben, ist die Auswahl des Alarmtyps oft der erste Schritt bei der Einrichtung. einen Alarm erstellen. Ein weiterer Unterschied ist, wie genau der Alarm ausgelöst werden soll. gesprochen. Bei den meisten Apps setInexactRepeating() ist die richtige Wahl. Bei dieser Methode synchronisiert Android mehrere sich genau wiederholende Alarme und Auslösungen. gleichzeitig. Dadurch wird der Akku geschont.

Verwende möglichst keine exakten Alarme. Für die seltene App mit starren können Sie einen genauen Alarm einstellen, indem Sie setRepeating()

Mit setInexactRepeating() Sie können kein benutzerdefiniertes Intervall festlegen, setRepeating() Sie müssen eine der Intervallkonstanten verwenden, z. B. INTERVAL_FIFTEEN_MINUTES, INTERVAL_DAY, und so weiter. Weitere Informationen finden Sie unter AlarmManager. finden Sie die vollständige Liste.

Einen Wecker ausschalten

Je nach App können Sie den Wecker auch abstellen. Wenn du einen Wecker ausschalten möchtest, ruf cancel() an im Alarm Manager an und übergeben die PendingIntent, die Sie nicht mehr benötigen zu feuern. Beispiel:

Kotlin

// If the alarm has been set, cancel it.
alarmMgr?.cancel(alarmIntent)

Java

// If the alarm has been set, cancel it.
if (alarmMgr!= null) {
    alarmMgr.cancel(alarmIntent);
}

Einen Wecker stellen, wenn das Gerät neu gestartet wird

Standardmäßig werden alle Alarme abgebrochen, wenn ein Gerät ausgeschaltet wird. Um dies zu verhindern, können Sie Ihre App , um einen sich wiederholenden Wecker automatisch neu zu starten, wenn der Nutzer das Gerät neu startet. Dieses sorgt dafür, dass der AlarmManager ohne dass der Benutzer den Alarm manuell neu starten muss.

Gehe dazu so vor:

  1. Legen Sie die RECEIVE_BOOT_COMPLETED fest. im Manifest Ihrer App angegeben. Dadurch kann deine App die ACTION_BOOT_COMPLETED die nach dem Systemstart gesendet wird. Dies funktioniert nur, App wurde bereits mindestens einmal vom Nutzer gestartet):

    <uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
  2. Implementieren Sie ein BroadcastReceiver um die Übertragung zu empfangen:

    Kotlin

    class SampleBootReceiver : BroadcastReceiver() {
    
        override fun onReceive(context: Context, intent: Intent) {
            if (intent.action == "android.intent.action.BOOT_COMPLETED") {
                // Set the alarm here.
            }
        }
    }
    

    Java

    public class SampleBootReceiver extends BroadcastReceiver {
    
        @Override
        public void onReceive(Context context, Intent intent) {
            if (intent.getAction().equals("android.intent.action.BOOT_COMPLETED")) {
                // Set the alarm here.
            }
        }
    }
    
  3. Fügen Sie den Empfänger mit einem Intent-Filter zur Manifestdatei Ihrer App hinzu, Filter auf der ACTION_BOOT_COMPLETED Aktion:

    <receiver android:name=".SampleBootReceiver"
            android:enabled="false">
        <intent-filter>
            <action android:name="android.intent.action.BOOT_COMPLETED"></action>
        </intent-filter>
    </receiver>

    Beachten Sie, dass der Bootempfänger im Manifest auf android:enabled="false" Das bedeutet, dass der Empfänger wird nur aufgerufen, wenn die Anwendung es explizit aktiviert. Dadurch wird verhindert, Boot-Receiver wird nicht unnötigerweise aufgerufen. Du kannst einen Empfänger aktivieren (z. B. wenn der Benutzer einen Alarm einstellt) wie folgt:

    Kotlin

    val receiver = ComponentName(context, SampleBootReceiver::class.java)
    
    context.packageManager.setComponentEnabledSetting(
            receiver,
            PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
            PackageManager.DONT_KILL_APP
    )
    

    Java

    ComponentName receiver = new ComponentName(context, SampleBootReceiver.class);
    PackageManager pm = context.getPackageManager();
    
    pm.setComponentEnabledSetting(receiver,
            PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
            PackageManager.DONT_KILL_APP);
    

    Wenn du den Receiver auf diese Weise aktivierst, bleibt er auch dann aktiviert, wenn der Nutzer startet das Gerät neu. Mit anderen Worten: Die programmatische Aktivierung des Empfängers überschreibt die Manifesteinstellung, auch bei Neustarts. Der Empfänger bleibt aktiviert, bis sie von Ihrer App deaktiviert wird. Sie können einen Empfänger deaktivieren, z. B. wenn der Benutzer einen Alarm abbricht) wie folgt:

    Kotlin

    val receiver = ComponentName(context, SampleBootReceiver::class.java)
    
    context.packageManager.setComponentEnabledSetting(
            receiver,
            PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
            PackageManager.DONT_KILL_APP
    )
    

    Java

    ComponentName receiver = new ComponentName(context, SampleBootReceiver.class);
    PackageManager pm = context.getPackageManager();
    
    pm.setComponentEnabledSetting(receiver,
            PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
            PackageManager.DONT_KILL_APP);
    

Alarme auslösen, während sich das Gerät im Stromsparmodus befindet

Geräte mit Android 6.0 (API-Level 23) werden unterstützt Stromsparmodus mit der Sie verlängert die Akkulaufzeit des Geräts. Alarme werden nicht ausgelöst, wenn das Gerät eingeschaltet ist Stromsparmodus Geplante Alarme werden verschoben, bis der Stromsparmodus des Geräts beendet wird. Bei Bedarf um die Arbeit zu erledigen, auch wenn das Gerät inaktiv ist, gibt es mehrere Möglichkeiten, verfügbar:

  • Stellen Sie einen exakten Wecker ein.

  • Nutzen Sie die WorkManager API, die für eine im Hintergrund. Sie können angeben, dass das System Ihre Arbeit beschleunigen soll, dass die Arbeit so schnell wie möglich abgeschlossen wird. Weitere Informationen finden Sie unter Aufgaben mit WorkManager planen

Best Practices

Jede Entscheidung, die du bei der Gestaltung eines sich wiederholenden Weckers triffst, kann Auswirkungen haben in der Art und Weise, wie deine App Systemressourcen nutzt (oder missbraucht). Stellen Sie sich zum Beispiel vor, beliebte App, die sich mit einem Server synchronisieren lässt. Wenn die Synchronisierung auf der Uhr basiert und jede Instanz der App um 23:00 Uhr synchronisiert wird, wird die Last auf der zu hoher Latenz oder sogar zu hoher „Denial of Service“. Befolge diese Best Practices bei der Verwendung von Alarmen:

  • Zufälligkeit (Jitter) zu allen Netzwerkanfragen hinzufügen, wird als Folge eines sich wiederholenden Weckers ausgelöst:

    • Erledige vor Ort Arbeit, wenn der Alarm ausgelöst wird. „Lokale Arbeit“ bedeutet alles, was keinen Server erreicht und keine Daten vom Server benötigt.

    • Stelle gleichzeitig den Alarm ein, der die Netzwerkanfragen an zufällig ausgelöst werden.

  • Beschränke die Alarmhäufigkeit auf ein Minimum.

  • Aktivieren Sie das Gerät nicht unnötig. Dieses Verhalten hängt vom Alarmtyp, wie unter Alarmtyp auswählen beschrieben.

  • Die Auslösungszeit deines Alarms darf nicht genauer sein, als es sein muss.

    Verwenden Sie setInexactRepeating() anstelle von setRepeating() Wenn Sie setInexactRepeating() verwenden, geschieht Folgendes: Android synchronisiert wiederkehrende Weckrufe von mehreren Apps und löst die Auslösung aus gleichzeitig. Dadurch verringert sich die Häufigkeit, mit der das System um den Akku zu schonen. Ab Android 4.4 (API-Ebene 19) werden alle wiederkehrenden Alarme als ungenauer Alarm ausgelöst. Hinweis während setInexactRepeating() ist eine Verbesserung gegenüber setRepeating(), Ein Server kann dennoch überlastet werden, wenn jede Instanz einer Anwendung den Server erreicht. etwa zur selben Zeit. Fügen Sie deshalb bei Netzwerkanfragen wie zuvor erwähnt.

  • Richte deinen Wecker nach Möglichkeit nicht auf die Uhrzeit zurück.

    Wiederholte Alarme, die auf einer genauen Auslösungszeit basieren, lassen sich nicht gut skalieren. Verwenden Sie ELAPSED_REALTIME wenn wie möglich. Der andere Wecker werden im folgenden Abschnitt ausführlicher beschrieben.