|
|
|
@ -9,11 +9,14 @@ import android.app.DatePickerDialog;
|
|
|
|
|
import android.app.NotificationChannel; |
|
|
|
|
import android.app.NotificationManager; |
|
|
|
|
import android.app.PendingIntent; |
|
|
|
|
import android.app.job.JobInfo; |
|
|
|
|
import android.app.job.JobScheduler; |
|
|
|
|
import android.appwidget.AppWidgetManager; |
|
|
|
|
import android.content.ComponentName; |
|
|
|
|
import android.content.Context; |
|
|
|
|
import android.content.DialogInterface; |
|
|
|
|
import android.content.Intent; |
|
|
|
|
import android.content.IntentFilter; |
|
|
|
|
import android.content.SharedPreferences; |
|
|
|
|
import android.content.pm.PackageInfo; |
|
|
|
|
import android.content.pm.PackageManager; |
|
|
|
@ -98,8 +101,12 @@ public class MeditationAssistant extends Application {
|
|
|
|
|
public static String ACTION_REMINDER = "sh.ftp.rocketninelabs.meditationassistant.DAILY_NOTIFICATION"; |
|
|
|
|
public static String ACTION_UPDATED = "sh.ftp.rocketninelabs.meditationassistant.DAILY_NOTIFICATION_UPDATED"; |
|
|
|
|
|
|
|
|
|
public static String LOG_TAG = "MeditationAssistant"; |
|
|
|
|
|
|
|
|
|
public static int CSV_COLUMN_COUNT = 5; |
|
|
|
|
|
|
|
|
|
public static int dailyReminderJobID = 108; |
|
|
|
|
public static int dailyReminderNotificationID = 1946; // Terence McKenna's year of birth
|
|
|
|
|
public static int sessionNotificationID = 1990; |
|
|
|
|
public static int bellNotificationID = 1991; |
|
|
|
|
|
|
|
|
@ -169,6 +176,8 @@ public class MeditationAssistant extends Application {
|
|
|
|
|
private Button sessionDialogCompletedTimeButton = null; |
|
|
|
|
private Button sessionDialogLengthButton = null; |
|
|
|
|
private EditText sessionDialogMessage = null; |
|
|
|
|
private DailyReminderReceiver dailyReminderReceiver = null; |
|
|
|
|
private JobScheduler jobScheduler = null; |
|
|
|
|
private DatePickerDialog.OnDateSetListener sessionDialogDateSetListener = |
|
|
|
|
new DatePickerDialog.OnDateSetListener() { |
|
|
|
|
@Override |
|
|
|
@ -1201,6 +1210,16 @@ public class MeditationAssistant extends Application {
|
|
|
|
|
+ Build.VERSION.SDK_INT |
|
|
|
|
); |
|
|
|
|
|
|
|
|
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { |
|
|
|
|
jobScheduler = (JobScheduler) getSystemService(Context.JOB_SCHEDULER_SERVICE); |
|
|
|
|
|
|
|
|
|
dailyReminderReceiver = new DailyReminderReceiver(); |
|
|
|
|
IntentFilter reminderFilter = new IntentFilter(); |
|
|
|
|
reminderFilter.addAction(ACTION_REMINDER); |
|
|
|
|
reminderFilter.addAction(ACTION_UPDATED); |
|
|
|
|
registerReceiver(dailyReminderReceiver, reminderFilter); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (Build.VERSION.SDK_INT >= 23) { |
|
|
|
|
PackageManager pm = getPackageManager(); |
|
|
|
|
pm.setComponentEnabledSetting(new ComponentName(this, FilePickerActivity.class), |
|
|
|
@ -1251,15 +1270,87 @@ public class MeditationAssistant extends Application {
|
|
|
|
|
|
|
|
|
|
db = DatabaseHandler.getInstance(getApplicationContext()); |
|
|
|
|
|
|
|
|
|
setDailyReminder(getApplicationContext()); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
@RequiresApi(api = Build.VERSION_CODES.LOLLIPOP) |
|
|
|
|
public JobInfo.Builder buildDailyReminderJob(Context context, Calendar calendar) { |
|
|
|
|
long delay = calendar.getTimeInMillis() - System.currentTimeMillis(); |
|
|
|
|
|
|
|
|
|
JobInfo.Builder builder = new JobInfo.Builder(dailyReminderJobID, new ComponentName(context, DailyReminderService.class)); |
|
|
|
|
builder.setPersisted(true); |
|
|
|
|
builder.setMinimumLatency(delay); |
|
|
|
|
builder.setOverrideDeadline(delay); |
|
|
|
|
return builder; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public void setDailyReminder(Context context) { |
|
|
|
|
String reminderTime = getPrefs().getString("pref_daily_reminder_time", "19:00"); |
|
|
|
|
String[] reminderTimeSplit = ((reminderTime != null && reminderTime != "") ? reminderTime : "19:00").split(":"); |
|
|
|
|
Integer reminderHour = Integer.valueOf(reminderTimeSplit[0]); |
|
|
|
|
Integer reminderMinute = Integer.valueOf(reminderTimeSplit[1]); |
|
|
|
|
|
|
|
|
|
Calendar calendar = Calendar.getInstance(); |
|
|
|
|
calendar.set(Calendar.HOUR_OF_DAY, reminderHour); |
|
|
|
|
calendar.set(Calendar.MINUTE, reminderMinute); |
|
|
|
|
calendar.set(Calendar.SECOND, 0); |
|
|
|
|
|
|
|
|
|
if (Calendar.getInstance().getTimeInMillis() > calendar.getTimeInMillis()) { |
|
|
|
|
calendar.add(Calendar.DATE, 1); // Tomorrow
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { |
|
|
|
|
/* Send the daily notification updated intent just in case the receiver hasn't been called yet */ |
|
|
|
|
Log.d("MeditationAssistant", "Sending initial daily notification updated intent"); |
|
|
|
|
Intent intent = new Intent(); |
|
|
|
|
intent.setAction(MeditationAssistant.ACTION_UPDATED); |
|
|
|
|
sendBroadcast(intent); |
|
|
|
|
cancelDailyReminder(context); |
|
|
|
|
|
|
|
|
|
reminderPendingIntent = PendingIntent.getBroadcast(context, dailyReminderNotificationID, new Intent(MeditationAssistant.ACTION_REMINDER), PendingIntent.FLAG_CANCEL_CURRENT); |
|
|
|
|
|
|
|
|
|
/* Don't use setAlarmClock here as it will always place an alarm icon in the status bar */ |
|
|
|
|
setAlarm(false, calendar.getTimeInMillis(), reminderPendingIntent); |
|
|
|
|
} else { |
|
|
|
|
long lastJobScheduled = getPrefs().getLong("last_job_scheduled", 0); |
|
|
|
|
if (System.currentTimeMillis() - lastJobScheduled < 250) { |
|
|
|
|
Log.d("MeditationAssistant", "Rate limiting daily reminder job scheduling"); |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
JobInfo.Builder builder = buildDailyReminderJob(context, calendar); |
|
|
|
|
int result = jobScheduler.schedule(builder.build()); |
|
|
|
|
|
|
|
|
|
getPrefs().edit().putLong("last_job_scheduled", System.currentTimeMillis()).apply(); |
|
|
|
|
|
|
|
|
|
String resultLabel = (result == JobScheduler.RESULT_SUCCESS) ? "successfully" : "unsuccessfully"; |
|
|
|
|
Log.d("MeditationAssistant", "Scheduled daily reminder job " + resultLabel); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
Log.d("MeditationAssistant", "Set daily reminder alarm for " + calendar); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public void cancelDailyReminder(Context context) { |
|
|
|
|
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.O) { |
|
|
|
|
if (reminderPendingIntent == null) { |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
try { |
|
|
|
|
getAlarmManager().cancel(reminderPendingIntent); |
|
|
|
|
} catch (Exception e) { |
|
|
|
|
Log.e("MeditationAssistant", "AlarmManager update was not canceled. " + e.toString()); |
|
|
|
|
} |
|
|
|
|
try { |
|
|
|
|
PendingIntent.getBroadcast(context, 0, new Intent(MeditationAssistant.ACTION_REMINDER), PendingIntent.FLAG_CANCEL_CURRENT).cancel(); |
|
|
|
|
} catch (Exception e) { |
|
|
|
|
Log.e("MeditationAssistant", "PendingIntent broadcast was not canceled. " + e.toString()); |
|
|
|
|
} |
|
|
|
|
try { |
|
|
|
|
reminderPendingIntent.cancel(); |
|
|
|
|
} catch (Exception e) { |
|
|
|
|
Log.e("MeditationAssistant", "PendingIntent was not canceled. " + e.toString()); |
|
|
|
|
} |
|
|
|
|
} else { |
|
|
|
|
jobScheduler.cancel(dailyReminderJobID); |
|
|
|
|
Log.d("MeditationAssistant", "Canceled daily reminder job"); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
public String getPostDataString(HashMap<String, String> params) throws UnsupportedEncodingException { |
|
|
|
|
StringBuilder result = new StringBuilder(); |
|
|
|
|
boolean first = true; |
|
|
|
@ -1451,9 +1542,14 @@ public class MeditationAssistant extends Application {
|
|
|
|
|
bellChannel.enableLights(false); |
|
|
|
|
bellChannel.enableVibration(false); |
|
|
|
|
|
|
|
|
|
NotificationChannel reminderChannel = new NotificationChannel("reminder", getString(R.string.pref_daily_reminder), NotificationManager.IMPORTANCE_DEFAULT); |
|
|
|
|
reminderChannel.enableLights(true); |
|
|
|
|
reminderChannel.enableVibration(true); |
|
|
|
|
|
|
|
|
|
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE); |
|
|
|
|
notificationManager.createNotificationChannel(sessionChannel); |
|
|
|
|
notificationManager.createNotificationChannel(bellChannel); |
|
|
|
|
notificationManager.createNotificationChannel(reminderChannel); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public void showMindfulnessBellNotification() { |
|
|
|
|