调度重复的闹钟

本文详细介绍了Android中不同类型的闹钟设置,包括ELAPSED_REALTIME_WAKEUP、RTC、RTC_WAKEUP的使用案例,以及如何取消闹钟和在设备启动后启用闹钟的方法。同时,提供了Manifest文件中配置接收器的示例。


闹钟的具体类型:

  • ELAPSED_REALTIME:从设备启动之后开始算起,度过了某一段特定时间后,激活 Pending Intent,但不会唤醒设备。其中设备睡眠的时间也会包含在内。
  • ELAPSED_REALTIME_WAKEUP:从设备启动之后开始算起,度过了某一段特定时间后唤醒设备。
  • RTC:在某一个特定时刻激活 Pending Intent,但不会唤醒设备。
  • RTC_WAKEUP:在某一个特定时刻唤醒设备并激活 Pending Intent。

ELAPSED_REALTIME_WAKEUP 案例

每隔在 30 分钟后唤醒设备以激活闹钟:

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

在一分钟后唤醒设备并激活一个一次性(无重复)闹钟:

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);

RTC 案例

在大约下午 2 点唤醒设备并激活闹钟,并不断重复:

// 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);

让设备精确地在上午 8 点半被唤醒并激活闹钟,自此之后每 20 分钟唤醒一次:

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);
使用 setRepeating() 时,你可以制定一个自定义的时间间隔,但在使用 setInexactRepeating() 时不支持这么做。此时你只能选择一些时间间隔常量,例如: INTERVAL_FIFTEEN_MINUTES  , INTERVAL_DAY  等。完整的常量列表,可以查看  AlarmManager


取消闹钟

你可能希望在应用中添加取消闹钟的功能。要取消闹钟,可以调用 AlarmManager 的cancel()方法,并把你不想激活的 PendingIntent 传递进去,例如:

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

在设备启动后启用闹钟

1. 在应用的 Manifest 文件中设置 RECEIVE_BOOT_CMPLETED 权限,这将允许你的应用接收系统启动完成后发出的 ACTION_BOOT_COMPLETED 广播(只有在用户至少将你的应用启动了一次后,这样做才有效):

<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>

2. 实现 BoradcastReceiver 用于接收广播:

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. 在你的 Manifest 文件中添加一个接收器,其 Intent-Filter 接收 ACTION_BOOT_COMPLETED 这一 Action:

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

注意 Manifest 文件中,对接收器设置了android:enabled="false"属性。这意味着除非应用显式地启用它,不然该接收器将不被调用。这可以防止接收器被不必要地调用。你可以像下面这样启动接收器(比如用户设置了一个闹钟):

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

pm.setComponentEnabledSetting(receiver,
        PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
        PackageManager.DONT_KILL_APP);

一旦你像上面那样启动了接收器,它将一直保持启动状态,即使用户重启了设备也不例外。换句话说,通过代码设置的启用配置将会覆盖掉 Manifest 文件中的现有配置,即使重启也不例外。接收器将保持启动状态,直到你的应用将其禁用。你可以像下面这样禁用接收器(比如用户取消了一个闹钟):

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

pm.setComponentEnabledSetting(receiver,
        PackageManager.COMPONENT_ENABLED_STATE_DISABLED,
        PackageManager.DONT_KILL_APP);

参考:

http://hukai.me/android-training-course-in-chinese/background-jobs/scheduling/alarms.html




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值