Home | History | Annotate | Download | only in alarms
      1 /*
      2  * Copyright (C) 2013 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 package com.android.deskclock.alarms;
     17 
     18 import android.app.Notification;
     19 import android.app.NotificationManager;
     20 import android.app.PendingIntent;
     21 import android.content.Context;
     22 import android.content.Intent;
     23 import android.content.res.Resources;
     24 import android.provider.Settings;
     25 
     26 import com.android.deskclock.AlarmClockFragment;
     27 import com.android.deskclock.AlarmUtils;
     28 import com.android.deskclock.DeskClock;
     29 import com.android.deskclock.Log;
     30 import com.android.deskclock.R;
     31 import com.android.deskclock.provider.Alarm;
     32 import com.android.deskclock.provider.AlarmInstance;
     33 
     34 import java.util.Calendar;
     35 
     36 public final class AlarmNotifications {
     37     // System intent action to notify that we change the alarm text.
     38     public static final String SYSTEM_ALARM_CHANGE_ACTION = "android.intent.action.ALARM_CHANGED";
     39 
     40     public static void broadcastNextAlarm(Context context, AlarmInstance instance)  {
     41         String timeString = "";
     42         boolean showStatusIcon = false;
     43         if (instance != null) {
     44             timeString = AlarmUtils.getFormattedTime(context, instance.getAlarmTime());
     45             showStatusIcon = true;
     46         }
     47 
     48         // Set and notify next alarm text to system
     49         Log.i("Displaying next alarm time: \'" + timeString + '\'');
     50         Settings.System.putString(context.getContentResolver(),
     51                 Settings.System.NEXT_ALARM_FORMATTED,
     52                 timeString);
     53         Intent alarmChanged = new Intent(SYSTEM_ALARM_CHANGE_ACTION);
     54         alarmChanged.putExtra("alarmSet", showStatusIcon);
     55         context.sendBroadcast(alarmChanged);
     56     }
     57 
     58     public static void showLowPriorityNotification(Context context, AlarmInstance instance) {
     59         Log.v("Displaying low priority notification for alarm instance: " + instance.mId);
     60         NotificationManager nm = (NotificationManager)
     61                 context.getSystemService(Context.NOTIFICATION_SERVICE);
     62 
     63         Resources resources = context.getResources();
     64         Notification.Builder notification = new Notification.Builder(context)
     65                 .setContentTitle(resources.getString(R.string.alarm_alert_predismiss_title))
     66                 .setContentText(AlarmUtils.getAlarmText(context, instance))
     67                 .setSmallIcon(R.drawable.stat_notify_alarm)
     68                 .setOngoing(false)
     69                 .setAutoCancel(false)
     70                 .setPriority(Notification.PRIORITY_DEFAULT);
     71 
     72         // Setup up hide notification
     73         Intent hideIntent = AlarmStateManager.createStateChangeIntent(context, "DELETE_TAG",
     74                 instance, AlarmInstance.HIDE_NOTIFICATION_STATE);
     75         notification.setDeleteIntent(PendingIntent.getBroadcast(context, instance.hashCode(),
     76                 hideIntent, PendingIntent.FLAG_UPDATE_CURRENT));
     77 
     78         // Setup up dismiss action
     79         Intent dismissIntent = AlarmStateManager.createStateChangeIntent(context, "DISMISS_TAG",
     80                 instance, AlarmInstance.DISMISSED_STATE);
     81         notification.addAction(android.R.drawable.ic_menu_close_clear_cancel,
     82                 resources.getString(R.string.alarm_alert_dismiss_now_text),
     83                 PendingIntent.getBroadcast(context, instance.hashCode(),
     84                         dismissIntent, PendingIntent.FLAG_UPDATE_CURRENT));
     85 
     86         // Setup content action if instance is owned by alarm
     87         long alarmId = instance.mAlarmId == null ? Alarm.INVALID_ID : instance.mAlarmId;
     88         Intent viewAlarmIntent = Alarm.createIntent(context, DeskClock.class, alarmId);
     89         viewAlarmIntent.putExtra(DeskClock.SELECT_TAB_INTENT_EXTRA, DeskClock.ALARM_TAB_INDEX);
     90         viewAlarmIntent.putExtra(AlarmClockFragment.SCROLL_TO_ALARM_INTENT_EXTRA, alarmId);
     91         viewAlarmIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
     92         notification.setContentIntent(PendingIntent.getActivity(context, instance.hashCode(),
     93                 viewAlarmIntent, PendingIntent.FLAG_UPDATE_CURRENT));
     94 
     95         nm.cancel(instance.hashCode());
     96         nm.notify(instance.hashCode(), notification.build());
     97     }
     98 
     99     public static void showHighPriorityNotification(Context context, AlarmInstance instance) {
    100         Log.v("Displaying high priority notification for alarm instance: " + instance.mId);
    101         NotificationManager nm = (NotificationManager)
    102                 context.getSystemService(Context.NOTIFICATION_SERVICE);
    103 
    104         Resources resources = context.getResources();
    105         Notification.Builder notification = new Notification.Builder(context)
    106                 .setContentTitle(resources.getString(R.string.alarm_alert_predismiss_title))
    107                 .setContentText(AlarmUtils.getAlarmText(context, instance))
    108                 .setSmallIcon(R.drawable.stat_notify_alarm)
    109                 .setOngoing(true)
    110                 .setAutoCancel(false)
    111                 .setPriority(Notification.PRIORITY_HIGH);
    112 
    113         // Setup up dismiss action
    114         Intent dismissIntent = AlarmStateManager.createStateChangeIntent(context, "DISMISS_TAG",
    115                 instance, AlarmInstance.DISMISSED_STATE);
    116         notification.addAction(android.R.drawable.ic_menu_close_clear_cancel,
    117                 resources.getString(R.string.alarm_alert_dismiss_now_text),
    118                 PendingIntent.getBroadcast(context, instance.hashCode(),
    119                         dismissIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    120 
    121         // Setup content action if instance is owned by alarm
    122         long alarmId = instance.mAlarmId == null ? Alarm.INVALID_ID : instance.mAlarmId;
    123         Intent viewAlarmIntent = Alarm.createIntent(context, DeskClock.class, alarmId);
    124         viewAlarmIntent.putExtra(DeskClock.SELECT_TAB_INTENT_EXTRA, DeskClock.ALARM_TAB_INDEX);
    125         viewAlarmIntent.putExtra(AlarmClockFragment.SCROLL_TO_ALARM_INTENT_EXTRA, alarmId);
    126         viewAlarmIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    127         notification.setContentIntent(PendingIntent.getActivity(context, instance.hashCode(),
    128                 viewAlarmIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    129 
    130         nm.cancel(instance.hashCode());
    131         nm.notify(instance.hashCode(), notification.build());
    132     }
    133 
    134     public static void showSnoozeNotification(Context context, AlarmInstance instance) {
    135         Log.v("Displaying snoozed notification for alarm instance: " + instance.mId);
    136         NotificationManager nm = (NotificationManager)
    137                 context.getSystemService(Context.NOTIFICATION_SERVICE);
    138 
    139         Resources resources = context.getResources();
    140         Notification.Builder notification = new Notification.Builder(context)
    141                 .setContentTitle(instance.getLabelOrDefault(context))
    142                 .setContentText(resources.getString(R.string.alarm_alert_snooze_until,
    143                         AlarmUtils.getFormattedTime(context, instance.getAlarmTime())))
    144                 .setSmallIcon(R.drawable.stat_notify_alarm)
    145                 .setOngoing(true)
    146                 .setAutoCancel(false)
    147                 .setPriority(Notification.PRIORITY_MAX);
    148 
    149         // Setup up dismiss action
    150         Intent dismissIntent = AlarmStateManager.createStateChangeIntent(context, "DISMISS_TAG",
    151                 instance, AlarmInstance.DISMISSED_STATE);
    152         notification.addAction(android.R.drawable.ic_menu_close_clear_cancel,
    153                 resources.getString(R.string.alarm_alert_dismiss_text),
    154                 PendingIntent.getBroadcast(context, instance.hashCode(),
    155                         dismissIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    156 
    157         // Setup content action if instance is owned by alarm
    158         long alarmId = instance.mAlarmId == null ? Alarm.INVALID_ID : instance.mAlarmId;
    159         Intent viewAlarmIntent = Alarm.createIntent(context, DeskClock.class, alarmId);
    160         viewAlarmIntent.putExtra(DeskClock.SELECT_TAB_INTENT_EXTRA, DeskClock.ALARM_TAB_INDEX);
    161         viewAlarmIntent.putExtra(AlarmClockFragment.SCROLL_TO_ALARM_INTENT_EXTRA, alarmId);
    162         viewAlarmIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    163         notification.setContentIntent(PendingIntent.getActivity(context, instance.hashCode(),
    164                 viewAlarmIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    165         nm.cancel(instance.hashCode());
    166         nm.notify(instance.hashCode(), notification.build());
    167     }
    168 
    169     public static void showMissedNotification(Context context, AlarmInstance instance) {
    170         Log.v("Displaying missed notification for alarm instance: " + instance.mId);
    171         NotificationManager nm = (NotificationManager)
    172                 context.getSystemService(Context.NOTIFICATION_SERVICE);
    173 
    174         String label = instance.mLabel;
    175         String alarmTime = AlarmUtils.getFormattedTime(context, instance.getAlarmTime());
    176         String contextText = instance.mLabel.isEmpty() ? alarmTime :
    177                 context.getString(R.string.alarm_missed_text, alarmTime, label);
    178         Notification.Builder notification = new Notification.Builder(context)
    179                 .setContentTitle(context.getString(R.string.alarm_missed_title))
    180                 .setContentText(contextText)
    181                 .setSmallIcon(R.drawable.stat_notify_alarm)
    182                 .setPriority(Notification.PRIORITY_HIGH);
    183 
    184         // Setup dismiss intent
    185         Intent dismissIntent = AlarmStateManager.createStateChangeIntent(context, "DISMISS_TAG",
    186                 instance, AlarmInstance.DISMISSED_STATE);
    187         notification.setDeleteIntent(PendingIntent.getBroadcast(context, instance.hashCode(),
    188                 dismissIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    189 
    190         // Setup content intent
    191         Intent showAndDismiss = AlarmInstance.createIntent(context, AlarmStateManager.class,
    192                 instance.mId);
    193         showAndDismiss.setAction(AlarmStateManager.SHOW_AND_DISMISS_ALARM_ACTION);
    194         notification.setContentIntent(PendingIntent.getBroadcast(context, instance.hashCode(),
    195                 showAndDismiss, PendingIntent.FLAG_UPDATE_CURRENT));
    196 
    197         nm.cancel(instance.hashCode());
    198         nm.notify(instance.hashCode(), notification.build());
    199     }
    200 
    201     public static void showAlarmNotification(Context context, AlarmInstance instance) {
    202         Log.v("Displaying alarm notification for alarm instance: " + instance.mId);
    203         NotificationManager nm = (NotificationManager)
    204                 context.getSystemService(Context.NOTIFICATION_SERVICE);
    205 
    206         // Close dialogs and window shade, so this will display
    207         context.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS));
    208 
    209         Resources resources = context.getResources();
    210         Notification.Builder notification = new Notification.Builder(context)
    211                 .setContentTitle(instance.getLabelOrDefault(context))
    212                 .setContentText(AlarmUtils.getFormattedTime(context, instance.getAlarmTime()))
    213                 .setSmallIcon(R.drawable.stat_notify_alarm)
    214                 .setOngoing(true)
    215                 .setAutoCancel(false)
    216                 .setDefaults(Notification.DEFAULT_LIGHTS)
    217                 .setWhen(0);
    218 
    219         // Setup Snooze Action
    220         Intent snoozeIntent = AlarmStateManager.createStateChangeIntent(context, "SNOOZE_TAG",
    221                 instance, AlarmInstance.SNOOZE_STATE);
    222         PendingIntent snoozePendingIntent = PendingIntent.getBroadcast(context, instance.hashCode(),
    223                 snoozeIntent,
    224                 PendingIntent.FLAG_UPDATE_CURRENT);
    225         notification.addAction(R.drawable.stat_notify_alarm,
    226                 resources.getString(R.string.alarm_alert_snooze_text), snoozePendingIntent);
    227 
    228         // Setup Dismiss Action
    229         Intent dismissIntent = AlarmStateManager.createStateChangeIntent(context, "DISMISS_TAG",
    230                 instance, AlarmInstance.DISMISSED_STATE);
    231         PendingIntent dismissPendingIntent = PendingIntent.getBroadcast(context,
    232                 instance.hashCode(), dismissIntent, PendingIntent.FLAG_UPDATE_CURRENT);
    233         notification.addAction(android.R.drawable.ic_menu_close_clear_cancel,
    234                 resources.getString(R.string.alarm_alert_dismiss_text),
    235                 dismissPendingIntent);
    236 
    237         // Setup Content Action
    238         Intent contentIntent = AlarmInstance.createIntent(context, AlarmActivity.class,
    239                 instance.mId);
    240         notification.setContentIntent(PendingIntent.getActivity(context,
    241                 instance.hashCode(), contentIntent, PendingIntent.FLAG_UPDATE_CURRENT));
    242 
    243         // Setup fullscreen intent
    244         Intent fullScreenIntent = AlarmInstance.createIntent(context, AlarmActivity.class,
    245                 instance.mId);
    246         // set action, so we can be different then content pending intent
    247         fullScreenIntent.setAction("fullscreen_activity");
    248         fullScreenIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
    249                 Intent.FLAG_ACTIVITY_NO_USER_ACTION);
    250         notification.setFullScreenIntent(PendingIntent.getActivity(context,
    251                 instance.hashCode(), fullScreenIntent, PendingIntent.FLAG_UPDATE_CURRENT), true);
    252         notification.setPriority(Notification.PRIORITY_MAX);
    253 
    254         nm.cancel(instance.hashCode());
    255         nm.notify(instance.hashCode(), notification.build());
    256     }
    257 
    258     public static void clearNotification(Context context, AlarmInstance instance) {
    259         Log.v("Clearing notifications for alarm instance: " + instance.mId);
    260         NotificationManager nm = (NotificationManager)
    261                 context.getSystemService(Context.NOTIFICATION_SERVICE);
    262         nm.cancel(instance.hashCode());
    263     }
    264 }
    265