Merge pull request #707 from hiqua/dev

pull/718/head
Alinson S. Xavier 5 years ago committed by GitHub
commit 9a4aaf47bc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -5,4 +5,11 @@ plugins {
id "org.jetbrains.kotlin.android.extensions" version "$KOTLIN_VERSION" apply false
id "org.jetbrains.kotlin.multiplatform" version "1.4.21" apply false
id "org.jlleitschuh.gradle.ktlint" version "9.4.1"
}
// Needed for ktlint. Taken from: https://github.com/JLLeitschuh/ktlint-gradle/issues/181#issuecomment-443146206
allprojects {
repositories {
mavenCentral()
}
}

@ -38,7 +38,7 @@ public interface HabitsApplicationTestComponent
IntentScheduler getIntentScheduler();
}
@Module
@dagger.Module
class SingleThreadModule
{
@Provides

@ -100,12 +100,12 @@ class IntentSchedulerTest : BaseAndroidTest() {
assertThat(scheduler.scheduleShowReminder(reminderTime, habit, 0), equalTo(OK))
setSystemTime("America/Chicago", 2020, JUNE, 2, 22, 44)
assertNull(ReminderReceiver.getLastReceivedIntent())
assertNull(ReminderReceiver.lastReceivedIntent)
setSystemTime("America/Chicago", 2020, JUNE, 2, 22, 46)
val intent = ReminderReceiver.getLastReceivedIntent()
val intent = ReminderReceiver.lastReceivedIntent
assertNotNull(intent)
assertThat(parseId(intent.data!!), equalTo(habit.id))
assertThat(parseId(intent?.data!!), equalTo(habit.id))
}
@Test
@ -120,10 +120,10 @@ class IntentSchedulerTest : BaseAndroidTest() {
assertThat(scheduler.scheduleWidgetUpdate(updateTime), equalTo(OK))
setSystemTime("America/Chicago", 2020, JUNE, 2, 22, 44)
assertNull(WidgetReceiver.getLastReceivedIntent())
assertNull(WidgetReceiver.lastReceivedIntent)
setSystemTime("America/Chicago", 2020, JUNE, 2, 22, 46)
val intent = WidgetReceiver.getLastReceivedIntent()
val intent = WidgetReceiver.lastReceivedIntent
assertNotNull(intent)
}
}

@ -1,123 +0,0 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.notifications;
import android.app.*;
import android.graphics.*;
import android.os.*;
import androidx.annotation.Nullable;
import android.text.format.*;
import android.view.*;
import android.widget.*;
import androidx.fragment.app.FragmentActivity;
import com.android.datetimepicker.time.TimePickerDialog;
import org.isoron.uhabits.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.inject.*;
import org.isoron.uhabits.receivers.*;
import org.isoron.uhabits.utils.*;
import java.util.*;
import static android.content.ContentUris.parseId;
public class SnoozeDelayPickerActivity extends FragmentActivity
implements AdapterView.OnItemClickListener
{
private Habit habit;
private ReminderController reminderController;
@Nullable
private AlertDialog dialog;
@Override
protected void onCreate(@Nullable Bundle bundle)
{
super.onCreate(bundle);
if (getIntent() == null) finish();
if (getIntent().getData() == null) finish();
HabitsApplication app = (HabitsApplication) getApplicationContext();
HabitsApplicationComponent appComponent = app.getComponent();
reminderController = appComponent.getReminderController();
habit = appComponent.getHabitList().getById(parseId(getIntent().getData()));
if (habit == null) finish();
int theme = R.style.Theme_AppCompat_Light_Dialog_Alert;
dialog = new AlertDialog.Builder(new ContextThemeWrapper(this, theme))
.setTitle(R.string.select_snooze_delay)
.setItems(R.array.snooze_picker_names, null)
.create();
dialog.getListView().setOnItemClickListener(this);
dialog.setOnDismissListener(d -> finish());
dialog.show();
SystemUtils.unlockScreen(this);
}
private void showTimePicker()
{
final Calendar calendar = Calendar.getInstance();
TimePickerDialog dialog = TimePickerDialog.newInstance(
(view, hour, minute) -> {
reminderController.onSnoozeTimePicked(habit, hour, minute);
finish();
},
calendar.get(Calendar.HOUR_OF_DAY),
calendar.get(Calendar.MINUTE),
DateFormat.is24HourFormat(this),
Color.BLUE);
dialog.show(getSupportFragmentManager(), "timePicker");
}
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id)
{
int[] snoozeValues = getResources().getIntArray(R.array.snooze_picker_values);
if (snoozeValues[position] >= 0)
{
reminderController.onSnoozeDelayPicked(habit, snoozeValues[position]);
finish();
}
else showTimePicker();
}
@Override
public void finish()
{
super.finish();
overridePendingTransition(0, 0);
}
@Override
protected void onPause()
{
if (dialog != null) dialog.dismiss();
super.onPause();
}
}

@ -0,0 +1,96 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.notifications
import android.app.AlertDialog
import android.content.ContentUris
import android.graphics.Color
import android.os.Bundle
import android.text.format.DateFormat
import android.view.ContextThemeWrapper
import android.view.View
import android.widget.AdapterView
import android.widget.AdapterView.OnItemClickListener
import androidx.fragment.app.FragmentActivity
import com.android.datetimepicker.time.RadialPickerLayout
import com.android.datetimepicker.time.TimePickerDialog
import org.isoron.uhabits.HabitsApplication
import org.isoron.uhabits.R
import org.isoron.uhabits.core.models.Habit
import org.isoron.uhabits.receivers.ReminderController
import org.isoron.uhabits.utils.SystemUtils
import java.util.Calendar
class SnoozeDelayPickerActivity : FragmentActivity(), OnItemClickListener {
private var habit: Habit? = null
private var reminderController: ReminderController? = null
private var dialog: AlertDialog? = null
override fun onCreate(bundle: Bundle?) {
super.onCreate(bundle)
if (intent == null) finish()
if (intent.data == null) finish()
val app = applicationContext as HabitsApplication
val appComponent = app.component
reminderController = appComponent.reminderController
habit = appComponent.habitList.getById(ContentUris.parseId(intent.data))
if (habit == null) finish()
val theme = R.style.Theme_AppCompat_Light_Dialog_Alert
dialog = AlertDialog.Builder(ContextThemeWrapper(this, theme))
.setTitle(R.string.select_snooze_delay)
.setItems(R.array.snooze_picker_names, null)
.create()
dialog!!.listView.onItemClickListener = this
dialog!!.setOnDismissListener { finish() }
dialog!!.show()
SystemUtils.unlockScreen(this)
}
private fun showTimePicker() {
val calendar = Calendar.getInstance()
val dialog = TimePickerDialog.newInstance(
{ view: RadialPickerLayout?, hour: Int, minute: Int ->
reminderController!!.onSnoozeTimePicked(habit, hour, minute)
finish()
},
calendar[Calendar.HOUR_OF_DAY],
calendar[Calendar.MINUTE],
DateFormat.is24HourFormat(this),
Color.BLUE
)
dialog.show(supportFragmentManager, "timePicker")
}
override fun onItemClick(parent: AdapterView<*>?, view: View, position: Int, id: Long) {
val snoozeValues = resources.getIntArray(R.array.snooze_picker_values)
if (snoozeValues[position] >= 0) {
reminderController!!.onSnoozeDelayPicked(habit, snoozeValues[position])
finish()
} else showTimePicker()
}
override fun finish() {
super.finish()
overridePendingTransition(0, 0)
}
override fun onPause() {
if (dialog != null) dialog!!.dismiss()
super.onPause()
}
}

@ -16,10 +16,9 @@
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers
package org.isoron.uhabits.receivers;
import javax.inject.*;
import javax.inject.Scope
@Scope
public @interface ReceiverScope { }
annotation class ReceiverScope

@ -1,103 +0,0 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers;
import android.content.*;
import android.net.*;
import androidx.annotation.NonNull;
import org.isoron.uhabits.core.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.reminders.*;
import org.isoron.uhabits.core.ui.*;
import org.isoron.uhabits.core.utils.*;
import org.isoron.uhabits.notifications.*;
import javax.inject.*;
@AppScope
public class ReminderController
{
@NonNull
private final ReminderScheduler reminderScheduler;
@NonNull
private final NotificationTray notificationTray;
@NonNull
private Preferences preferences;
@Inject
public ReminderController(@NonNull ReminderScheduler reminderScheduler,
@NonNull NotificationTray notificationTray,
@NonNull Preferences preferences)
{
this.reminderScheduler = reminderScheduler;
this.notificationTray = notificationTray;
this.preferences = preferences;
}
public void onBootCompleted()
{
reminderScheduler.scheduleAll();
}
public void onShowReminder(@NonNull Habit habit,
Timestamp timestamp,
long reminderTime)
{
notificationTray.show(habit, timestamp, reminderTime);
reminderScheduler.scheduleAll();
}
public void onSnoozePressed(@NonNull Habit habit, final Context context)
{
showSnoozeDelayPicker(habit, context);
}
public void onSnoozeDelayPicked(Habit habit, int delayInMinutes)
{
reminderScheduler.snoozeReminder(habit, delayInMinutes);
notificationTray.cancel(habit);
}
public void onSnoozeTimePicked(Habit habit, int hour, int minute)
{
long time = DateUtils.getUpcomingTimeInMillis(hour, minute);
reminderScheduler.scheduleAtTime(habit, time);
notificationTray.cancel(habit);
}
public void onDismiss(@NonNull Habit habit)
{
notificationTray.cancel(habit);
}
private void showSnoozeDelayPicker(@NonNull Habit habit, Context context)
{
context.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS));
Intent intent = new Intent(context, SnoozeDelayPickerActivity.class);
intent.setData(Uri.parse(habit.getUriString()));
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
}
}

@ -0,0 +1,79 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers
import android.content.Context
import android.content.Intent
import android.net.Uri
import org.isoron.uhabits.core.AppScope
import org.isoron.uhabits.core.models.Habit
import org.isoron.uhabits.core.models.Timestamp
import org.isoron.uhabits.core.preferences.Preferences
import org.isoron.uhabits.core.reminders.ReminderScheduler
import org.isoron.uhabits.core.ui.NotificationTray
import org.isoron.uhabits.core.utils.DateUtils.Companion.getUpcomingTimeInMillis
import org.isoron.uhabits.notifications.SnoozeDelayPickerActivity
import javax.inject.Inject
@AppScope
class ReminderController @Inject constructor(
private val reminderScheduler: ReminderScheduler,
private val notificationTray: NotificationTray,
private val preferences: Preferences
) {
fun onBootCompleted() {
reminderScheduler.scheduleAll()
}
fun onShowReminder(
habit: Habit,
timestamp: Timestamp?,
reminderTime: Long
) {
notificationTray.show(habit, timestamp, reminderTime)
reminderScheduler.scheduleAll()
}
fun onSnoozePressed(habit: Habit, context: Context) {
showSnoozeDelayPicker(habit, context)
}
fun onSnoozeDelayPicked(habit: Habit?, delayInMinutes: Int) {
reminderScheduler.snoozeReminder(habit, delayInMinutes.toLong())
notificationTray.cancel(habit!!)
}
fun onSnoozeTimePicked(habit: Habit?, hour: Int, minute: Int) {
val time: Long = getUpcomingTimeInMillis(hour, minute)
reminderScheduler.scheduleAtTime(habit!!, time)
notificationTray.cancel(habit)
}
fun onDismiss(habit: Habit) {
notificationTray.cancel(habit)
}
private fun showSnoozeDelayPicker(habit: Habit, context: Context) {
context.sendBroadcast(Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS))
val intent = Intent(context, SnoozeDelayPickerActivity::class.java)
intent.data = Uri.parse(habit.uriString)
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
context.startActivity(intent)
}
}

@ -1,124 +0,0 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers;
import android.content.*;
import android.util.*;
import androidx.annotation.Nullable;
import org.isoron.uhabits.*;
import org.isoron.uhabits.core.models.*;
import org.isoron.uhabits.core.utils.*;
import org.isoron.uhabits.inject.*;
import static android.content.ContentUris.*;
/**
* The Android BroadcastReceiver for Loop Habit Tracker.
* <p>
* All broadcast messages are received and processed by this class.
*/
public class ReminderReceiver extends BroadcastReceiver
{
public static final String ACTION_DISMISS_REMINDER =
"org.isoron.uhabits.ACTION_DISMISS_REMINDER";
public static final String ACTION_SHOW_REMINDER =
"org.isoron.uhabits.ACTION_SHOW_REMINDER";
public static final String ACTION_SNOOZE_REMINDER =
"org.isoron.uhabits.ACTION_SNOOZE_REMINDER";
private static final String TAG = "ReminderReceiver";
private static Intent lastReceivedIntent = null;
@Override
public void onReceive(@Nullable final Context context, @Nullable Intent intent)
{
if (context == null || intent == null) return;
if (intent.getAction() == null) return;
lastReceivedIntent = intent;
HabitsApplication app = (HabitsApplication) context.getApplicationContext();
HabitsApplicationComponent appComponent = app.getComponent();
HabitList habits = appComponent.getHabitList();
ReminderController reminderController = appComponent.getReminderController();
Log.i(TAG, String.format("Received intent: %s", intent.toString()));
Habit habit = null;
long today = DateUtils.getStartOfTodayWithOffset();
if (intent.getData() != null)
habit = habits.getById(parseId(intent.getData()));
final long timestamp = intent.getLongExtra("timestamp", today);
final long reminderTime = intent.getLongExtra("reminderTime", today);
try
{
switch (intent.getAction())
{
case ACTION_SHOW_REMINDER:
if (habit == null) return;
Log.d("ReminderReceiver", String.format(
"onShowReminder habit=%d timestamp=%d reminderTime=%d",
habit.getId(),
timestamp,
reminderTime));
reminderController.onShowReminder(habit,
new Timestamp(timestamp), reminderTime);
break;
case ACTION_DISMISS_REMINDER:
if (habit == null) return;
Log.d("ReminderReceiver", String.format("onDismiss habit=%d", habit.getId()));
reminderController.onDismiss(habit);
break;
case ACTION_SNOOZE_REMINDER:
if (habit == null) return;
Log.d("ReminderReceiver", String.format("onSnoozePressed habit=%d", habit.getId()));
reminderController.onSnoozePressed(habit, context);
break;
case Intent.ACTION_BOOT_COMPLETED:
Log.d("ReminderReceiver", "onBootCompleted");
reminderController.onBootCompleted();
break;
}
}
catch (RuntimeException e)
{
Log.e(TAG, "could not process intent", e);
}
}
public static void clearLastReceivedIntent()
{
lastReceivedIntent = null;
}
public static Intent getLastReceivedIntent()
{
return lastReceivedIntent;
}
}

@ -0,0 +1,103 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers
import android.content.BroadcastReceiver
import android.content.ContentUris
import android.content.Context
import android.content.Intent
import android.util.Log
import org.isoron.uhabits.HabitsApplication
import org.isoron.uhabits.core.models.Habit
import org.isoron.uhabits.core.models.Timestamp
import org.isoron.uhabits.core.utils.DateUtils.Companion.getStartOfTodayWithOffset
/**
* The Android BroadcastReceiver for Loop Habit Tracker.
*
*
* All broadcast messages are received and processed by this class.
*/
class ReminderReceiver : BroadcastReceiver() {
override fun onReceive(context: Context?, intent: Intent?) {
if (context == null || intent == null) return
if (intent.action == null) return
lastReceivedIntent = intent
val app = context.applicationContext as HabitsApplication
val appComponent = app.component
val habits = appComponent.habitList
val reminderController = appComponent.reminderController
Log.i(TAG, String.format("Received intent: %s", intent.toString()))
var habit: Habit? = null
val today: Long = getStartOfTodayWithOffset()
if (intent.data != null) habit = habits.getById(ContentUris.parseId(intent.data))
val timestamp = intent.getLongExtra("timestamp", today)
val reminderTime = intent.getLongExtra("reminderTime", today)
try {
when (intent.action) {
ACTION_SHOW_REMINDER -> {
if (habit == null) return
Log.d(
"ReminderReceiver",
String.format(
"onShowReminder habit=%d timestamp=%d reminderTime=%d",
habit.id,
timestamp,
reminderTime
)
)
reminderController.onShowReminder(
habit,
Timestamp(timestamp),
reminderTime
)
}
ACTION_DISMISS_REMINDER -> {
if (habit == null) return
Log.d("ReminderReceiver", String.format("onDismiss habit=%d", habit.id))
reminderController.onDismiss(habit)
}
ACTION_SNOOZE_REMINDER -> {
if (habit == null) return
Log.d("ReminderReceiver", String.format("onSnoozePressed habit=%d", habit.id))
reminderController.onSnoozePressed(habit, context)
}
Intent.ACTION_BOOT_COMPLETED -> {
Log.d("ReminderReceiver", "onBootCompleted")
reminderController.onBootCompleted()
}
}
} catch (e: RuntimeException) {
Log.e(TAG, "could not process intent", e)
}
}
companion object {
const val ACTION_DISMISS_REMINDER = "org.isoron.uhabits.ACTION_DISMISS_REMINDER"
const val ACTION_SHOW_REMINDER = "org.isoron.uhabits.ACTION_SHOW_REMINDER"
const val ACTION_SNOOZE_REMINDER = "org.isoron.uhabits.ACTION_SNOOZE_REMINDER"
private const val TAG = "ReminderReceiver"
var lastReceivedIntent: Intent? = null
private set
fun clearLastReceivedIntent() {
lastReceivedIntent = null
}
}
}

@ -1,158 +0,0 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers;
import android.content.*;
import android.util.*;
import org.isoron.uhabits.*;
import org.isoron.uhabits.core.preferences.*;
import org.isoron.uhabits.core.ui.widgets.*;
import org.isoron.uhabits.inject.*;
import org.isoron.uhabits.intents.*;
import org.isoron.uhabits.widgets.*;
import org.isoron.uhabits.widgets.activities.*;
import dagger.*;
/**
* The Android BroadcastReceiver for Loop Habit Tracker.
* <p>
* All broadcast messages are received and processed by this class.
*/
public class WidgetReceiver extends BroadcastReceiver
{
public static final String ACTION_ADD_REPETITION =
"org.isoron.uhabits.ACTION_ADD_REPETITION";
public static final String ACTION_DISMISS_REMINDER =
"org.isoron.uhabits.ACTION_DISMISS_REMINDER";
public static final String ACTION_REMOVE_REPETITION =
"org.isoron.uhabits.ACTION_REMOVE_REPETITION";
public static final String ACTION_TOGGLE_REPETITION =
"org.isoron.uhabits.ACTION_TOGGLE_REPETITION";
public static final String ACTION_SET_NUMERICAL_VALUE =
"org.isoron.uhabits.ACTION_SET_NUMERICAL_VALUE";
public static final String ACTION_UPDATE_WIDGETS_VALUE =
"org.isoron.uhabits.ACTION_UPDATE_WIDGETS_VALUE";
private static final String TAG = "WidgetReceiver";
private static Intent lastReceivedIntent = null;
@Override
public void onReceive(final Context context, Intent intent)
{
HabitsApplication app =
(HabitsApplication) context.getApplicationContext();
WidgetComponent component = DaggerWidgetReceiver_WidgetComponent
.builder()
.habitsApplicationComponent(app.getComponent())
.build();
IntentParser parser = app.getComponent().getIntentParser();
WidgetBehavior controller = component.getWidgetController();
Preferences prefs = app.getComponent().getPreferences();
WidgetUpdater widgetUpdater = app.getComponent().getWidgetUpdater();
Log.i(TAG, String.format("Received intent: %s", intent.toString()));
lastReceivedIntent = intent;
try
{
IntentParser.CheckmarkIntentData data = null;
if (intent.getAction() != ACTION_UPDATE_WIDGETS_VALUE)
{
data = parser.parseCheckmarkIntent(intent);
}
switch (intent.getAction())
{
case ACTION_ADD_REPETITION:
Log.d(TAG, String.format(
"onAddRepetition habit=%d timestamp=%d",
data.getHabit().getId(),
data.getTimestamp().getUnixTime()));
controller.onAddRepetition(data.getHabit(),
data.getTimestamp());
break;
case ACTION_TOGGLE_REPETITION:
Log.d(TAG, String.format(
"onToggleRepetition habit=%d timestamp=%d",
data.getHabit().getId(),
data.getTimestamp().getUnixTime()));
controller.onToggleRepetition(data.getHabit(),
data.getTimestamp());
break;
case ACTION_REMOVE_REPETITION:
Log.d(TAG, String.format(
"onRemoveRepetition habit=%d timestamp=%d",
data.getHabit().getId(),
data.getTimestamp().getUnixTime()));
controller.onRemoveRepetition(data.getHabit(),
data.getTimestamp());
break;
case ACTION_SET_NUMERICAL_VALUE:
context.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS));
Intent numberSelectorIntent = new Intent(context, NumericalCheckmarkWidgetActivity.class);
numberSelectorIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
numberSelectorIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK);
numberSelectorIntent.setAction(NumericalCheckmarkWidgetActivity.ACTION_SHOW_NUMERICAL_VALUE_ACTIVITY);
parser.copyIntentData(intent,numberSelectorIntent);
context.startActivity(numberSelectorIntent);
break;
case ACTION_UPDATE_WIDGETS_VALUE:
widgetUpdater.updateWidgets();
widgetUpdater.scheduleStartDayWidgetUpdate();
break;
}
}
catch (RuntimeException e)
{
Log.e("WidgetReceiver", "could not process intent", e);
}
}
@ReceiverScope
@Component(dependencies = HabitsApplicationComponent.class)
interface WidgetComponent
{
WidgetBehavior getWidgetController();
}
public static Intent getLastReceivedIntent()
{
return lastReceivedIntent;
}
public static void clearLastReceivedIntent()
{
lastReceivedIntent = null;
}
}

@ -0,0 +1,139 @@
/*
* Copyright (C) 2016-2021 Álinson Santos Xavier <git@axavier.org>
*
* This file is part of Loop Habit Tracker.
*
* Loop Habit Tracker is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by the
* Free Software Foundation, either version 3 of the License, or (at your
* option) any later version.
*
* Loop Habit Tracker is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.isoron.uhabits.receivers
import android.content.BroadcastReceiver
import android.content.Context
import android.content.Intent
import android.util.Log
import dagger.Component
import org.isoron.uhabits.HabitsApplication
import org.isoron.uhabits.core.ui.widgets.WidgetBehavior
import org.isoron.uhabits.inject.HabitsApplicationComponent
import org.isoron.uhabits.intents.IntentParser.CheckmarkIntentData
import org.isoron.uhabits.widgets.activities.NumericalCheckmarkWidgetActivity
/**
* The Android BroadcastReceiver for Loop Habit Tracker.
*
*
* All broadcast messages are received and processed by this class.
*/
class WidgetReceiver : BroadcastReceiver() {
override fun onReceive(context: Context, intent: Intent) {
val app = context.applicationContext as HabitsApplication
val component = DaggerWidgetReceiver_WidgetComponent
.builder()
.habitsApplicationComponent(app.component)
.build()
val parser = app.component.intentParser
val controller = component.widgetController
val prefs = app.component.preferences
val widgetUpdater = app.component.widgetUpdater
Log.i(TAG, String.format("Received intent: %s", intent.toString()))
lastReceivedIntent = intent
try {
var data: CheckmarkIntentData? = null
if (intent.action !== ACTION_UPDATE_WIDGETS_VALUE) {
data = parser.parseCheckmarkIntent(intent)
}
when (intent.action) {
ACTION_ADD_REPETITION -> {
Log.d(
TAG,
String.format(
"onAddRepetition habit=%d timestamp=%d",
data!!.habit.id,
data.timestamp.unixTime
)
)
controller.onAddRepetition(
data.habit,
data.timestamp
)
}
ACTION_TOGGLE_REPETITION -> {
Log.d(
TAG,
String.format(
"onToggleRepetition habit=%d timestamp=%d",
data!!.habit.id,
data.timestamp.unixTime
)
)
controller.onToggleRepetition(
data.habit,
data.timestamp
)
}
ACTION_REMOVE_REPETITION -> {
Log.d(
TAG,
String.format(
"onRemoveRepetition habit=%d timestamp=%d",
data!!.habit.id,
data.timestamp.unixTime
)
)
controller.onRemoveRepetition(
data.habit,
data.timestamp
)
}
ACTION_SET_NUMERICAL_VALUE -> {
context.sendBroadcast(Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS))
val numberSelectorIntent = Intent(context, NumericalCheckmarkWidgetActivity::class.java)
numberSelectorIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
numberSelectorIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TASK)
numberSelectorIntent.action = NumericalCheckmarkWidgetActivity.ACTION_SHOW_NUMERICAL_VALUE_ACTIVITY
parser.copyIntentData(intent, numberSelectorIntent)
context.startActivity(numberSelectorIntent)
}
ACTION_UPDATE_WIDGETS_VALUE -> {
widgetUpdater.updateWidgets()
widgetUpdater.scheduleStartDayWidgetUpdate()
}
}
} catch (e: RuntimeException) {
Log.e("WidgetReceiver", "could not process intent", e)
}
}
@ReceiverScope
@Component(dependencies = [HabitsApplicationComponent::class])
internal interface WidgetComponent {
val widgetController: WidgetBehavior
}
companion object {
const val ACTION_ADD_REPETITION = "org.isoron.uhabits.ACTION_ADD_REPETITION"
const val ACTION_DISMISS_REMINDER = "org.isoron.uhabits.ACTION_DISMISS_REMINDER"
const val ACTION_REMOVE_REPETITION = "org.isoron.uhabits.ACTION_REMOVE_REPETITION"
const val ACTION_TOGGLE_REPETITION = "org.isoron.uhabits.ACTION_TOGGLE_REPETITION"
const val ACTION_SET_NUMERICAL_VALUE = "org.isoron.uhabits.ACTION_SET_NUMERICAL_VALUE"
const val ACTION_UPDATE_WIDGETS_VALUE = "org.isoron.uhabits.ACTION_UPDATE_WIDGETS_VALUE"
private const val TAG = "WidgetReceiver"
var lastReceivedIntent: Intent? = null
private set
fun clearLastReceivedIntent() {
lastReceivedIntent = null
}
}
}
Loading…
Cancel
Save