package za.org.treehouse.HypoAlarm; import android.app.Notification; import android.app.NotificationManager; import android.app.PendingIntent; import android.app.Service; import android.content.Context; import android.content.Intent; import android.content.SharedPreferences; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.os.Build; import android.os.IBinder; import android.preference.PreferenceManager; import android.support.v4.app.NotificationCompat; import android.util.Log; public class AlarmNotify extends Service { private static final int notifyID = 1; private volatile boolean notificationRunning = false; @Override public IBinder onBind(Intent intent) { return null; } @Override public void onDestroy() { // If the notification is cancelled, stop updating. notificationRunning = false; // Remove the notification in the notification bar NotificationManager nm = (NotificationManager) getSystemService(NOTIFICATION_SERVICE); nm.cancel(notifyID); Log.d("AlarmNotify", "Notification stopped."); } @Override public int onStartCommand(Intent intent, int flags, int startId) { final int UPDATE_INTERVAL = 10*1000; // Timer is updated six times a minute SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(this); Log.d("AlarmNotify", "Notification started."); //final String phoneNumber = sharedPref.getString(getString(R.string.PhoneNumberPref), null); final int gracePeriod = sharedPref.getInt(getString(R.string.GracePeriodPref), MainActivity.defaultGracePeriod); Bitmap bm = BitmapFactory.decodeResource(getResources(), R.drawable.ic_launcher_grey); final NotificationManager nm = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE); final NotificationCompat.Builder notification = new NotificationCompat.Builder(this) .setContentTitle(getString(R.string.app_name)) .setContentText(String.format(getString(R.string.notificationText), MainActivity.MinutesToGracePeriodStr(gracePeriod))) .setSmallIcon(R.drawable.alarm_notification) .setLargeIcon(bm) .setOnlyAlertOnce(true) .setAutoCancel(false); if (Build.VERSION.SDK_INT >= 16) { notification.setPriority(Notification.PRIORITY_HIGH); } // Set up dismiss action Intent cancellerIntent = new Intent(getBaseContext(), CancelGraceReceiver.class); PendingIntent cancellerPendingIntent = PendingIntent.getBroadcast(getBaseContext(), MainActivity.CANCEL_GRACE_REQUEST, cancellerIntent, PendingIntent.FLAG_CANCEL_CURRENT); // Cancel the grace period if the user clears the notification notification.setDeleteIntent(cancellerPendingIntent); // Allow the user to cancel by clicking a "Cancel" button notification.addAction(android.R.drawable.ic_menu_close_clear_cancel, getString(R.string.notificationCancellation), cancellerPendingIntent); // Allow the user to cancel by selecting the ContentText or ContentTitle notification.setContentIntent(cancellerPendingIntent); nm.cancel(notifyID); nm.notify(notifyID, notification.build()); new Thread(new Runnable() { @Override public void run() { notificationRunning = true; // Make progress out of 1000 and not just 100, for greater resolution int max = 1000; // Count in milliseconds for greater progress resolution long graceEndTime = AlarmService.graceEndTime; long milliSecondsLeft = ((graceEndTime - System.currentTimeMillis())); long gracePeriodMilliSeconds = gracePeriod * 60 * 1000; int progress = (int) (((gracePeriodMilliSeconds - milliSecondsLeft) * max) / gracePeriodMilliSeconds); while (progress < max) { // Stop the thread if the notification is cancelled elsewhere if (!notificationRunning) { return; } // Recalculate milliSecondsLeft so that progress gets updated correctly. milliSecondsLeft = ((graceEndTime - System.currentTimeMillis())); // Recalculate the progress progress = (int) (((gracePeriodMilliSeconds - milliSecondsLeft) * max) / gracePeriodMilliSeconds); int minutesLeft = (int) ((milliSecondsLeft / 1000) / 60); if (Build.VERSION.SDK_INT >= 11) { notification.setContentText(String.format(getString(R.string.notificationText), MainActivity.MinutesToGracePeriodStr(minutesLeft))); notification.setProgress(max, progress, false); // Update the notification nm.notify(notifyID, notification.build()); } //Log.d("AlarmNotify", "milliSecondsLeft is " + milliSecondsLeft + " and gracePeriodMilliSeconds is " + gracePeriodMilliSeconds); //Log.d("AlarmNotify", "progress is " + progress + "; max is " + max); // Sleep until we need to update again try { Thread.sleep(UPDATE_INTERVAL); } catch (InterruptedException e) { Log.d("AlarmNotify", "sleep failure: " + e.toString()); } } stopSelf(); // stop notification service } }).start(); return super.onStartCommand(intent, flags, startId); } }