diff --git a/app/src/main/java/com/todoroo/astrid/subtasks/SubtasksHelper.kt b/app/src/main/java/com/todoroo/astrid/subtasks/SubtasksHelper.kt index 051fd7d56..722f88880 100644 --- a/app/src/main/java/com/todoroo/astrid/subtasks/SubtasksHelper.kt +++ b/app/src/main/java/com/todoroo/astrid/subtasks/SubtasksHelper.kt @@ -16,28 +16,32 @@ import org.tasks.data.TagDataDao import org.tasks.data.TaskListMetadata import org.tasks.data.TaskListMetadataDao import org.tasks.db.QueryUtils.showHiddenAndCompleted -import org.tasks.preferences.Preferences +import org.tasks.preferences.QueryPreferences import timber.log.Timber import java.util.* import javax.inject.Inject class SubtasksHelper @Inject constructor( @param:ApplicationContext private val context: Context, - private val preferences: Preferences, private val taskDao: TaskDao, private val tagDataDao: TagDataDao, private val taskListMetadataDao: TaskListMetadataDao) { - suspend fun applySubtasksToWidgetFilter(filter: Filter, query: String): String { - var query = query + suspend fun applySubtasksToWidgetFilter( + filter: Filter, + preferences: QueryPreferences, + originalQuery: String + ): String { + var query = originalQuery if (filter.supportsAstridSorting() && preferences.isAstridSort) { val tagData = tagDataDao.getTagByName(filter.listingTitle) - var tlm: TaskListMetadata? = null - if (tagData != null) { - tlm = taskListMetadataDao.fetchByTagOrFilter(tagData.remoteId!!) - } else if (isInbox(context, filter)) { - tlm = taskListMetadataDao.fetchByTagOrFilter(TaskListMetadata.FILTER_ID_ALL) - } else if (isTodayFilter(context, filter)) { - tlm = taskListMetadataDao.fetchByTagOrFilter(TaskListMetadata.FILTER_ID_TODAY) + val tlm = when { + tagData != null -> + taskListMetadataDao.fetchByTagOrFilter(tagData.remoteId!!) + isInbox(context, filter) -> + taskListMetadataDao.fetchByTagOrFilter(TaskListMetadata.FILTER_ID_ALL) + isTodayFilter(context, filter) -> + taskListMetadataDao.fetchByTagOrFilter(TaskListMetadata.FILTER_ID_TODAY) + else -> null } if (tlm != null) { query = query.replace("ORDER BY .*".toRegex(), "") diff --git a/app/src/main/java/org/tasks/dialogs/SortDialog.java b/app/src/main/java/org/tasks/dialogs/SortDialog.java index 3e41ab577..2afa13c7c 100644 --- a/app/src/main/java/org/tasks/dialogs/SortDialog.java +++ b/app/src/main/java/org/tasks/dialogs/SortDialog.java @@ -1,5 +1,7 @@ package org.tasks.dialogs; +import static android.app.Activity.RESULT_OK; + import android.app.Activity; import android.app.Dialog; import android.content.DialogInterface; @@ -8,6 +10,7 @@ import android.widget.Button; import androidx.annotation.NonNull; import androidx.appcompat.app.AlertDialog; import androidx.fragment.app.DialogFragment; +import androidx.fragment.app.Fragment; import com.todoroo.astrid.api.Filter; import com.todoroo.astrid.core.SortHelper; import dagger.hilt.android.AndroidEntryPoint; @@ -17,6 +20,7 @@ import javax.inject.Inject; import org.tasks.R; import org.tasks.preferences.Preferences; import org.tasks.preferences.QueryPreferences; +import org.tasks.widget.WidgetPreferences; import timber.log.Timber; @AndroidEntryPoint @@ -25,8 +29,12 @@ public class SortDialog extends DialogFragment { private static final String EXTRA_MANUAL_ENABLED = "extra_manual_enabled"; private static final String EXTRA_ASTRID_ENABLED = "extra_astrid_enabled"; private static final String EXTRA_SELECTED_INDEX = "extra_selected_index"; - @Inject Preferences preferences; + private static final String EXTRA_WIDGET_ID = "extra_widget_id"; + + @Inject Preferences appPreferences; @Inject DialogBuilder dialogBuilder; + + private QueryPreferences preferences; private boolean manualEnabled; private boolean astridEnabled; private int selectedIndex; @@ -42,14 +50,26 @@ public class SortDialog extends DialogFragment { return sortDialog; } + public static SortDialog newSortDialog(Fragment target, int rc, Filter filter, int widgetId) { + SortDialog dialog = newSortDialog(filter); + dialog.setTargetFragment(target, rc); + dialog.getArguments().putInt(EXTRA_WIDGET_ID, widgetId); + return dialog; + } + @NonNull @Override public Dialog onCreateDialog(Bundle savedInstanceState) { onCreate(savedInstanceState); Bundle arguments = getArguments(); + int widgetId = arguments.getInt(EXTRA_WIDGET_ID, -1); + preferences = widgetId < 0 + ? appPreferences + : new WidgetPreferences(getContext(), appPreferences, widgetId); manualEnabled = arguments.getBoolean(EXTRA_MANUAL_ENABLED); - astridEnabled = arguments.getBoolean(EXTRA_ASTRID_ENABLED) && preferences.getBoolean(R.string.p_astrid_sort_enabled, false); + astridEnabled = arguments.getBoolean(EXTRA_ASTRID_ENABLED) + && appPreferences.getBoolean(R.string.p_astrid_sort_enabled, false); if (savedInstanceState != null) { selectedIndex = savedInstanceState.getInt(EXTRA_SELECTED_INDEX); @@ -108,7 +128,9 @@ public class SortDialog extends DialogFragment { public void onAttach(Activity activity) { super.onAttach(activity); - callback = (SortDialogCallback) activity; + if (getTargetFragment() == null) { + callback = (SortDialogCallback) activity; + } } @Override @@ -139,7 +161,12 @@ public class SortDialog extends DialogFragment { preferences.setSortMode(getSortMode(manualEnabled || astridEnabled ? selectedIndex : selectedIndex + 1)); } - callback.sortChanged(wasManual != isManual || wasAstrid != isAstrid); + Fragment targetFragment = getTargetFragment(); + if (targetFragment == null) { + callback.sortChanged(wasManual != isManual || wasAstrid != isAstrid); + } else { + targetFragment.onActivityResult(getTargetRequestCode(), RESULT_OK, null); + } } private int getIndex(int sortMode) { diff --git a/app/src/main/java/org/tasks/preferences/fragments/ScrollableWidget.kt b/app/src/main/java/org/tasks/preferences/fragments/ScrollableWidget.kt index 30b163f3a..f81b29d96 100644 --- a/app/src/main/java/org/tasks/preferences/fragments/ScrollableWidget.kt +++ b/app/src/main/java/org/tasks/preferences/fragments/ScrollableWidget.kt @@ -7,6 +7,7 @@ import android.os.Bundle import androidx.lifecycle.lifecycleScope import androidx.preference.* import com.todoroo.astrid.api.Filter +import com.todoroo.astrid.core.SortHelper.* import dagger.hilt.android.AndroidEntryPoint import kotlinx.coroutines.launch import org.tasks.LocalBroadcastManager @@ -16,6 +17,7 @@ import org.tasks.dialogs.ColorPalettePicker import org.tasks.dialogs.ColorPalettePicker.Companion.newColorPalette import org.tasks.dialogs.ColorPickerAdapter.Palette import org.tasks.dialogs.ColorWheelPicker +import org.tasks.dialogs.SortDialog.newSortDialog import org.tasks.dialogs.ThemePickerDialog.Companion.newThemePickerDialog import org.tasks.injection.InjectingPreferenceFragment import org.tasks.locale.Locale @@ -27,6 +29,7 @@ import javax.inject.Inject private const val REQUEST_FILTER = 1005 private const val REQUEST_THEME_SELECTION = 1006 private const val REQUEST_COLOR_SELECTION = 1007 +private const val REQUEST_SORT = 1008 const val EXTRA_WIDGET_ID = "extra_widget_id" @@ -35,6 +38,7 @@ class ScrollableWidget : InjectingPreferenceFragment() { companion object { private const val FRAG_TAG_COLOR_PICKER = "frag_tag_color_picker" + private const val FRAG_TAG_SORT_DIALOG = "frag_tag_sort_dialog" fun newScrollableWidget(appWidgetId: Int): ScrollableWidget { val widget = ScrollableWidget() @@ -84,6 +88,8 @@ class ScrollableWidget : InjectingPreferenceFragment() { setupCheckbox(R.string.p_widget_show_tags) setupCheckbox(R.string.p_widget_show_full_task_title, false) setupCheckbox(R.string.p_widget_disable_groups, false) + setupCheckbox(R.string.p_widget_show_hidden, false) + setupCheckbox(R.string.p_widget_show_completed, false) val showDescription = setupCheckbox(R.string.p_widget_show_description, true) setupCheckbox(R.string.p_widget_show_full_description, false).dependency = showDescription.key setupList(R.string.p_widget_spacing) @@ -97,6 +103,14 @@ class ScrollableWidget : InjectingPreferenceFragment() { showMenu.dependency = showHeader.key header.dependency = showHeader.key + findPreference(R.string.p_widget_sort).setOnPreferenceClickListener { + lifecycleScope.launch { + newSortDialog(this@ScrollableWidget, REQUEST_SORT, getFilter(), appWidgetId) + .show(parentFragmentManager, FRAG_TAG_SORT_DIALOG) + } + false + } + findPreference(R.string.p_widget_filter) .setOnPreferenceClickListener { lifecycleScope.launch { @@ -149,11 +163,15 @@ class ScrollableWidget : InjectingPreferenceFragment() { } else if (requestCode == REQUEST_COLOR_SELECTION) { if (resultCode == Activity.RESULT_OK) { widgetPreferences.color = data!!.getIntExtra( - ColorWheelPicker.EXTRA_SELECTED, - 0 + ColorWheelPicker.EXTRA_SELECTED, + 0 ) updateColor() } + } else if (requestCode == REQUEST_SORT) { + if (resultCode == Activity.RESULT_OK) { + updateSort() + } } else { super.onActivityResult(requestCode, resultCode, data) } @@ -176,6 +194,26 @@ class ScrollableWidget : InjectingPreferenceFragment() { private fun updateFilter() = lifecycleScope.launch { findPreference(R.string.p_widget_filter).summary = getFilter().listingTitle + updateSort() + } + + private fun updateSort() = lifecycleScope.launch { + val filter = getFilter() + findPreference(R.string.p_widget_sort).setSummary( + if (filter.supportsManualSort() && widgetPreferences.isManualSort) { + R.string.SSD_sort_my_order + } else if (filter.supportsAstridSorting() && widgetPreferences.isAstridSort) { + R.string.astrid_sort_order + } else { + when (widgetPreferences.sortMode) { + SORT_DUE -> R.string.SSD_sort_due + SORT_IMPORTANCE -> R.string.SSD_sort_importance + SORT_ALPHA -> R.string.SSD_sort_alpha + SORT_MODIFIED -> R.string.SSD_sort_modified + SORT_CREATED -> R.string.sort_created + else -> R.string.SSD_sort_auto + } + }) } private suspend fun getFilter(): Filter { diff --git a/app/src/main/java/org/tasks/widget/ScrollableViewsFactory.kt b/app/src/main/java/org/tasks/widget/ScrollableViewsFactory.kt index 223292e24..9081937cd 100644 --- a/app/src/main/java/org/tasks/widget/ScrollableViewsFactory.kt +++ b/app/src/main/java/org/tasks/widget/ScrollableViewsFactory.kt @@ -36,7 +36,7 @@ import kotlin.math.max internal class ScrollableViewsFactory( private val subtasksHelper: SubtasksHelper, - private val preferences: Preferences, + preferences: Preferences, private val context: Context, private val widgetId: Int, private val taskDao: TaskDao, @@ -307,9 +307,10 @@ internal class ScrollableViewsFactory( private fun getTask(position: Int): TaskContainer? = tasks.getItem(position) private suspend fun getQuery(filter: Filter?, subtasks: SubtaskInfo): List { - val queries = getQuery(preferences, filter!!, subtasks) + val queries = getQuery(widgetPreferences, filter!!, subtasks) val last = queries.size - 1 - queries[last] = subtasksHelper.applySubtasksToWidgetFilter(filter, queries[last]) + queries[last] = + subtasksHelper.applySubtasksToWidgetFilter(filter, widgetPreferences, queries[last]) return queries } @@ -373,14 +374,14 @@ internal class ScrollableViewsFactory( showDividers = widgetPreferences.showDividers() disableGroups = widgetPreferences.disableGroups() || filter?.let { !it.supportsSorting() - || (it.supportsManualSort() && preferences.isManualSort) - || (it.supportsAstridSorting() && preferences.isAstridSort) + || (it.supportsManualSort() && widgetPreferences.isManualSort) + || (it.supportsAstridSorting() && widgetPreferences.isAstridSort) } == true showPlaces = widgetPreferences.showPlaces() showSubtasks = widgetPreferences.showSubtasks() showLists = widgetPreferences.showLists() showTags = widgetPreferences.showTags() - preferences.sortMode.takeIf { it != sortMode } + widgetPreferences.sortMode.takeIf { it != sortMode } ?.let { if (sortMode >= 0) { widgetPreferences.collapsed = HashSet() diff --git a/app/src/main/java/org/tasks/widget/WidgetPreferences.java b/app/src/main/java/org/tasks/widget/WidgetPreferences.java index 35a0a05b4..7bbdec289 100644 --- a/app/src/main/java/org/tasks/widget/WidgetPreferences.java +++ b/app/src/main/java/org/tasks/widget/WidgetPreferences.java @@ -3,14 +3,16 @@ package org.tasks.widget; import android.content.Context; import com.google.common.base.Joiner; import com.google.common.base.Splitter; +import com.todoroo.astrid.core.SortHelper; import com.todoroo.astrid.service.Upgrader; import java.util.HashSet; import org.tasks.R; import org.tasks.Strings; +import org.tasks.preferences.QueryPreferences; import org.tasks.preferences.Preferences; import timber.log.Timber; -public class WidgetPreferences { +public class WidgetPreferences implements QueryPreferences { private final Context context; private final Preferences preferences; @@ -209,4 +211,64 @@ public class WidgetPreferences { setString(R.string.p_widget_spacing, "1"); // compact setBoolean(R.string.p_widget_show_description, false); // no description } + + @Override + public int getSortMode() { + return getInt(R.string.p_widget_sort, SortHelper.SORT_AUTO); + } + + @Override + public boolean isManualSort() { + return getBoolean(R.string.p_widget_sort_manual, false); + } + + @Override + public boolean isAstridSort() { + return getBoolean(R.string.p_widget_sort_astrid, false); + } + + @Override + public boolean isReverseSort() { + return getBoolean(R.string.p_widget_sort_reverse, false); + } + + @Override + public boolean getShowHidden() { + return getBoolean(R.string.p_widget_show_hidden, false); + } + + @Override + public boolean getShowCompleted() { + return getBoolean(R.string.p_widget_show_completed, false); + } + + @Override + public boolean getShowCompletedTemporarily() { + return preferences.getShowCompletedTemporarily(); + } + + @Override + public boolean usePagedQueries() { + return preferences.usePagedQueries(); + } + + @Override + public void setSortMode(int sortMode) { + setInt(R.string.p_widget_sort, sortMode); + } + + @Override + public void setManualSort(boolean isManualSort) { + setBoolean(R.string.p_widget_sort_manual, isManualSort); + } + + @Override + public void setAstridSort(boolean isAstridSort) { + setBoolean(R.string.p_widget_sort_astrid, isAstridSort); + } + + @Override + public void setReverseSort(boolean isReverseSort) { + setBoolean(R.string.p_widget_sort_reverse, isReverseSort); + } } diff --git a/app/src/main/res/values/keys.xml b/app/src/main/res/values/keys.xml index ac1482add..6ebc8a009 100644 --- a/app/src/main/res/values/keys.xml +++ b/app/src/main/res/values/keys.xml @@ -298,6 +298,12 @@ widget-id- widget-theme-v2- + widget-sort- + widget-sort-reverse- + widget-sort-manual- + widget-sort-astrid- + widget-hidden- + widget-completed- widget-color- widget-color-v2 widget-opacity-v3- diff --git a/app/src/main/res/xml/preferences_widget.xml b/app/src/main/res/xml/preferences_widget.xml index a68267ebf..2b764612a 100644 --- a/app/src/main/res/xml/preferences_widget.xml +++ b/app/src/main/res/xml/preferences_widget.xml @@ -10,6 +10,18 @@ android:key="@string/p_widget_theme" android:title="@string/theme" /> + + + + + +