diff --git a/app/src/main/java/com/todoroo/astrid/activity/BeastModePreferences.java b/app/src/main/java/com/todoroo/astrid/activity/BeastModePreferences.java index de73d8358..cd9523563 100644 --- a/app/src/main/java/com/todoroo/astrid/activity/BeastModePreferences.java +++ b/app/src/main/java/com/todoroo/astrid/activity/BeastModePreferences.java @@ -27,7 +27,6 @@ import org.tasks.injection.ActivityComponent; import org.tasks.injection.ThemedInjectingAppCompatActivity; import org.tasks.preferences.Preferences; import org.tasks.preferences.beast.BeastModeRecyclerAdapter; -import org.tasks.ui.MenuColorizer; public class BeastModePreferences extends ThemedInjectingAppCompatActivity implements Toolbar.OnMenuItemClickListener { @@ -96,7 +95,7 @@ public class BeastModePreferences extends ThemedInjectingAppCompatActivity toolbar.setNavigationOnClickListener(v -> finish()); toolbar.inflateMenu(R.menu.beast_mode); toolbar.setOnMenuItemClickListener(this); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); adapter = new BeastModeRecyclerAdapter(this, constructOrderedControlList(preferences, this)); recyclerView.setHasFixedSize(true); diff --git a/app/src/main/java/com/todoroo/astrid/activity/MainActivity.java b/app/src/main/java/com/todoroo/astrid/activity/MainActivity.java index ac1c4dc2d..bf7919283 100644 --- a/app/src/main/java/com/todoroo/astrid/activity/MainActivity.java +++ b/app/src/main/java/com/todoroo/astrid/activity/MainActivity.java @@ -389,7 +389,10 @@ public class MainActivity extends InjectingAppCompatActivity private void openTask(Task task) { getSupportFragmentManager() .beginTransaction() - .replace(R.id.detail, newTaskEditFragment(task), TaskEditFragment.TAG_TASKEDIT_FRAGMENT) + .replace( + R.id.detail, + newTaskEditFragment(task, getFilterColor()), + TaskEditFragment.TAG_TASKEDIT_FRAGMENT) .addToBackStack(TaskEditFragment.TAG_TASKEDIT_FRAGMENT) .commit(); diff --git a/app/src/main/java/com/todoroo/astrid/activity/TaskEditFragment.java b/app/src/main/java/com/todoroo/astrid/activity/TaskEditFragment.java index acc9b0df0..019fda1cc 100755 --- a/app/src/main/java/com/todoroo/astrid/activity/TaskEditFragment.java +++ b/app/src/main/java/com/todoroo/astrid/activity/TaskEditFragment.java @@ -53,7 +53,7 @@ import org.tasks.injection.FragmentComponent; import org.tasks.injection.InjectingFragment; import org.tasks.notifications.NotificationManager; import org.tasks.preferences.Preferences; -import org.tasks.ui.MenuColorizer; +import org.tasks.themes.ThemeColor; import org.tasks.ui.SubtaskControlSet; import org.tasks.ui.TaskEditControlFragment; @@ -62,6 +62,8 @@ public final class TaskEditFragment extends InjectingFragment static final String TAG_TASKEDIT_FRAGMENT = "taskedit_fragment"; private static final String EXTRA_TASK = "extra_task"; + private static final String EXTRA_THEME = "extra_theme"; + @Inject TaskDao taskDao; @Inject UserActivityDao userActivityDao; @Inject TaskDeleter taskDeleter; @@ -75,12 +77,14 @@ public final class TaskEditFragment extends InjectingFragment @Inject TimerPlugin timerPlugin; Task model = null; + ThemeColor themeColor; private TaskEditFragmentCallbackHandler callback; - static TaskEditFragment newTaskEditFragment(Task task) { + static TaskEditFragment newTaskEditFragment(Task task, ThemeColor themeColor) { TaskEditFragment taskEditFragment = new TaskEditFragment(); Bundle arguments = new Bundle(); arguments.putParcelable(EXTRA_TASK, task); + arguments.putParcelable(EXTRA_THEME, themeColor); taskEditFragment.setArguments(arguments); return taskEditFragment; } @@ -105,6 +109,7 @@ public final class TaskEditFragment extends InjectingFragment Bundle arguments = getArguments(); model = arguments.getParcelable(EXTRA_TASK); + themeColor = arguments.getParcelable(EXTRA_THEME); Toolbar toolbar = binding.toolbar.toolbar; final boolean backButtonSavesTask = preferences.backButtonSavesTask(); @@ -126,7 +131,7 @@ public final class TaskEditFragment extends InjectingFragment toolbar.inflateMenu(R.menu.menu_task_edit_fragment); } toolbar.setOnMenuItemClickListener(this); - MenuColorizer.colorToolbar(context, toolbar); + themeColor.apply(toolbar); if (!model.isNew()) { notificationManager.cancel(model.getId()); @@ -137,7 +142,7 @@ public final class TaskEditFragment extends InjectingFragment FragmentManager fragmentManager = getChildFragmentManager(); List taskEditControlFragments = - taskEditControlSetFragmentManager.getOrCreateFragments(this, model); + taskEditControlSetFragmentManager.getOrCreateFragments(this, model, themeColor); FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); for (int i = 0; i < taskEditControlFragments.size(); i++) { diff --git a/app/src/main/java/com/todoroo/astrid/activity/TaskListFragment.java b/app/src/main/java/com/todoroo/astrid/activity/TaskListFragment.java index af0e5ca34..93a708139 100644 --- a/app/src/main/java/com/todoroo/astrid/activity/TaskListFragment.java +++ b/app/src/main/java/com/todoroo/astrid/activity/TaskListFragment.java @@ -102,7 +102,8 @@ import org.tasks.tasklist.DragAndDropRecyclerAdapter; import org.tasks.tasklist.PagedListRecyclerAdapter; import org.tasks.tasklist.TaskListRecyclerAdapter; import org.tasks.tasklist.ViewHolderFactory; -import org.tasks.ui.MenuColorizer; +import org.tasks.themes.ThemeCache; +import org.tasks.themes.ThemeColor; import org.tasks.ui.TaskListViewModel; import org.tasks.ui.Toaster; @@ -151,6 +152,8 @@ public final class TaskListFragment extends InjectingFragment @Inject TaskDuplicator taskDuplicator; @Inject TagDataDao tagDataDao; @Inject CaldavDao caldavDao; + @Inject ThemeCache themeCache; + @Inject ThemeColor defaultThemeColor; @BindView(R.id.swipe_layout) SwipeRefreshLayout swipeRefreshLayout; @@ -176,6 +179,7 @@ public final class TaskListFragment extends InjectingFragment private MenuItem search; private String searchQuery; private ActionMode mode = null; + private ThemeColor themeColor; private TaskListFragmentCallbackHandler callbacks; @@ -260,6 +264,8 @@ public final class TaskListFragment extends InjectingFragment filter = getFilter(); + themeColor = filter.tint >= 0 ? themeCache.getThemeColor(filter.tint) : defaultThemeColor; + filter.setFilterQueryOverride(null); // set up list adapters @@ -357,7 +363,7 @@ public final class TaskListFragment extends InjectingFragment search = menu.findItem(R.id.menu_search).setOnActionExpandListener(this); ((SearchView) search.getActionView()).setOnQueryTextListener(this); - MenuColorizer.colorToolbar(context, toolbar); + themeColor.apply(toolbar); } private void openFilter(@Nullable Filter filter) { @@ -676,7 +682,7 @@ public final class TaskListFragment extends InjectingFragment public boolean onCreateActionMode(ActionMode actionMode, Menu menu) { MenuInflater inflater = actionMode.getMenuInflater(); inflater.inflate(R.menu.menu_multi_select, menu); - MenuColorizer.colorMenu(context, menu); + themeColor.colorMenu(menu); return true; } diff --git a/app/src/main/java/com/todoroo/astrid/core/CustomFilterActivity.java b/app/src/main/java/com/todoroo/astrid/core/CustomFilterActivity.java index 54454114e..df2adfeab 100644 --- a/app/src/main/java/com/todoroo/astrid/core/CustomFilterActivity.java +++ b/app/src/main/java/com/todoroo/astrid/core/CustomFilterActivity.java @@ -49,7 +49,6 @@ import org.tasks.filters.FilterCriteriaProvider; import org.tasks.injection.ActivityComponent; import org.tasks.injection.ThemedInjectingAppCompatActivity; import org.tasks.locale.Locale; -import org.tasks.ui.MenuColorizer; /** * Activity that allows users to build custom filters @@ -119,7 +118,7 @@ public class CustomFilterActivity extends ThemedInjectingAppCompatActivity toolbar.inflateMenu(R.menu.menu_custom_filter_activity); toolbar.setOnMenuItemClickListener(this); toolbar.setNavigationOnClickListener(view -> discard()); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); listView = findViewById(android.R.id.list); List startingCriteria = new ArrayList<>(); diff --git a/app/src/main/java/org/tasks/activities/BaseListSettingsActivity.java b/app/src/main/java/org/tasks/activities/BaseListSettingsActivity.java index 4be8f5c4f..e869efbe7 100644 --- a/app/src/main/java/org/tasks/activities/BaseListSettingsActivity.java +++ b/app/src/main/java/org/tasks/activities/BaseListSettingsActivity.java @@ -24,7 +24,6 @@ import org.tasks.injection.ThemedInjectingAppCompatActivity; import org.tasks.themes.CustomIcons; import org.tasks.themes.ThemeCache; import org.tasks.themes.ThemeColor; -import org.tasks.ui.MenuColorizer; public abstract class BaseListSettingsActivity extends ThemedInjectingAppCompatActivity implements IconPickerCallback, OnMenuItemClickListener { @@ -70,7 +69,7 @@ public abstract class BaseListSettingsActivity extends ThemedInjectingAppCompatA toolbar.inflateMenu(R.menu.menu_tag_settings); } toolbar.setOnMenuItemClickListener(this); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); } @Override diff --git a/app/src/main/java/org/tasks/caldav/BaseCaldavAccountSettingsActivity.java b/app/src/main/java/org/tasks/caldav/BaseCaldavAccountSettingsActivity.java index f3b6d3817..535ac6b5e 100644 --- a/app/src/main/java/org/tasks/caldav/BaseCaldavAccountSettingsActivity.java +++ b/app/src/main/java/org/tasks/caldav/BaseCaldavAccountSettingsActivity.java @@ -38,7 +38,6 @@ import org.tasks.dialogs.DialogBuilder; import org.tasks.injection.ThemedInjectingAppCompatActivity; import org.tasks.security.Encryption; import org.tasks.ui.DisplayableException; -import org.tasks.ui.MenuColorizer; import timber.log.Timber; public abstract class BaseCaldavAccountSettingsActivity extends ThemedInjectingAppCompatActivity @@ -100,7 +99,7 @@ public abstract class BaseCaldavAccountSettingsActivity extends ThemedInjectingA toolbar.inflateMenu(R.menu.menu_caldav_account_settings); toolbar.setOnMenuItemClickListener(this); toolbar.showOverflowMenu(); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); if (caldavAccount == null) { toolbar.getMenu().findItem(R.id.remove).setVisible(false); diff --git a/app/src/main/java/org/tasks/etesync/EncryptionSettingsActivity.java b/app/src/main/java/org/tasks/etesync/EncryptionSettingsActivity.java index f53b7f13d..757f815c4 100644 --- a/app/src/main/java/org/tasks/etesync/EncryptionSettingsActivity.java +++ b/app/src/main/java/org/tasks/etesync/EncryptionSettingsActivity.java @@ -30,7 +30,6 @@ import org.tasks.injection.ActivityComponent; import org.tasks.injection.ThemedInjectingAppCompatActivity; import org.tasks.security.Encryption; import org.tasks.ui.DisplayableException; -import org.tasks.ui.MenuColorizer; import timber.log.Timber; public class EncryptionSettingsActivity extends ThemedInjectingAppCompatActivity @@ -75,7 +74,7 @@ public class EncryptionSettingsActivity extends ThemedInjectingAppCompatActivity toolbar.setNavigationOnClickListener(v -> save()); toolbar.inflateMenu(R.menu.menu_etesync_encryption_settings); toolbar.setOnMenuItemClickListener(this); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); createUserInfoViewModel.observe(this, this::returnDerivedKey, this::requestFailed); diff --git a/app/src/main/java/org/tasks/fragments/TaskEditControlSetFragmentManager.java b/app/src/main/java/org/tasks/fragments/TaskEditControlSetFragmentManager.java index 5f896946e..0a63c7209 100644 --- a/app/src/main/java/org/tasks/fragments/TaskEditControlSetFragmentManager.java +++ b/app/src/main/java/org/tasks/fragments/TaskEditControlSetFragmentManager.java @@ -22,6 +22,7 @@ import org.tasks.BuildConfig; import org.tasks.R; import org.tasks.injection.ForActivity; import org.tasks.preferences.Preferences; +import org.tasks.themes.ThemeColor; import org.tasks.ui.CalendarControlSet; import org.tasks.ui.DeadlineControlSet; import org.tasks.ui.DescriptionControlSet; @@ -113,10 +114,11 @@ public class TaskEditControlSetFragmentManager { } public List getOrCreateFragments( - TaskEditFragment taskEditFragment, Task task) { + TaskEditFragment taskEditFragment, Task task, ThemeColor themeColor) { Bundle arguments = new Bundle(); arguments.putParcelable(TaskEditControlFragment.EXTRA_TASK, task); arguments.putBoolean(TaskEditControlFragment.EXTRA_IS_NEW, task.isNew()); + arguments.putParcelable(TaskEditControlFragment.EXTRA_THEME, themeColor); List fragments = new ArrayList<>(); FragmentManager fragmentManager = taskEditFragment.getChildFragmentManager(); diff --git a/app/src/main/java/org/tasks/injection/ThemedInjectingAppCompatActivity.java b/app/src/main/java/org/tasks/injection/ThemedInjectingAppCompatActivity.java index 8d1a1645f..a742e07ab 100644 --- a/app/src/main/java/org/tasks/injection/ThemedInjectingAppCompatActivity.java +++ b/app/src/main/java/org/tasks/injection/ThemedInjectingAppCompatActivity.java @@ -5,11 +5,14 @@ import androidx.appcompat.app.AppCompatActivity; import javax.inject.Inject; import org.tasks.locale.Locale; import org.tasks.themes.Theme; +import org.tasks.themes.ThemeColor; public abstract class ThemedInjectingAppCompatActivity extends AppCompatActivity implements InjectingActivity { @Inject Theme theme; + @Inject protected ThemeColor themeColor; + private ActivityComponent activityComponent; protected ThemedInjectingAppCompatActivity() { diff --git a/app/src/main/java/org/tasks/locale/ui/activity/TaskerCreateTaskActivity.java b/app/src/main/java/org/tasks/locale/ui/activity/TaskerCreateTaskActivity.java index 459ed5f65..7d9a93c5e 100755 --- a/app/src/main/java/org/tasks/locale/ui/activity/TaskerCreateTaskActivity.java +++ b/app/src/main/java/org/tasks/locale/ui/activity/TaskerCreateTaskActivity.java @@ -14,11 +14,9 @@ import org.tasks.LocalBroadcastManager; import org.tasks.R; import org.tasks.billing.Inventory; import org.tasks.databinding.ActivityTaskerCreateBinding; -import org.tasks.databinding.ToolbarBinding; import org.tasks.injection.ActivityComponent; import org.tasks.locale.bundle.TaskCreationBundle; import org.tasks.preferences.Preferences; -import org.tasks.ui.MenuColorizer; public final class TaskerCreateTaskActivity extends AbstractFragmentPluginAppCompatActivity implements Toolbar.OnMenuItemClickListener { @@ -59,7 +57,7 @@ public final class TaskerCreateTaskActivity extends AbstractFragmentPluginAppCom }); toolbar.setOnMenuItemClickListener(this); toolbar.inflateMenu(R.menu.menu_tasker_create_task); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); if (savedInstanceState != null) { previousBundle = savedInstanceState.getParcelable(TaskCreationBundle.EXTRA_BUNDLE); diff --git a/app/src/main/java/org/tasks/location/LocationPickerActivity.java b/app/src/main/java/org/tasks/location/LocationPickerActivity.java index c5e2749b9..dfc5db7cf 100644 --- a/app/src/main/java/org/tasks/location/LocationPickerActivity.java +++ b/app/src/main/java/org/tasks/location/LocationPickerActivity.java @@ -65,7 +65,6 @@ import org.tasks.preferences.PermissionChecker; import org.tasks.preferences.PermissionRequestor; import org.tasks.themes.Theme; import org.tasks.themes.ThemeColor; -import org.tasks.ui.MenuColorizer; import org.tasks.ui.Toaster; import timber.log.Timber; @@ -166,11 +165,11 @@ public class LocationPickerActivity extends InjectingAppCompatActivity ((SearchView) search.getActionView()).setOnQueryTextListener(this); toolbar.setOnMenuItemClickListener(this); - MenuColorizer.colorToolbar(this, toolbar); ThemeColor themeColor = theme.getThemeColor(); themeColor.applyToStatusBarIcons(this); themeColor.applyToNavigationBar(this); themeColor.setStatusBarColor(toolbarLayout); + themeColor.apply(toolbar); boolean dark = theme.getThemeBase().isDarkTheme(this); map.init(getSupportFragmentManager(), this, dark); diff --git a/app/src/main/java/org/tasks/preferences/AttributionActivity.java b/app/src/main/java/org/tasks/preferences/AttributionActivity.java index e8175edc4..5efbb8026 100644 --- a/app/src/main/java/org/tasks/preferences/AttributionActivity.java +++ b/app/src/main/java/org/tasks/preferences/AttributionActivity.java @@ -29,7 +29,6 @@ import java.util.List; import org.tasks.R; import org.tasks.injection.ActivityComponent; import org.tasks.injection.ThemedInjectingAppCompatActivity; -import org.tasks.ui.MenuColorizer; import timber.log.Timber; public class AttributionActivity extends ThemedInjectingAppCompatActivity { @@ -51,7 +50,7 @@ public class AttributionActivity extends ThemedInjectingAppCompatActivity { toolbar.setTitle(R.string.third_party_licenses); toolbar.setNavigationIcon(R.drawable.ic_outline_arrow_back_24px); toolbar.setNavigationOnClickListener(v -> finish()); - MenuColorizer.colorToolbar(this, toolbar); + themeColor.apply(toolbar); recyclerView.setLayoutManager(new LinearLayoutManager(this)); } diff --git a/app/src/main/java/org/tasks/preferences/BasePreferences.kt b/app/src/main/java/org/tasks/preferences/BasePreferences.kt index 4a6cdce5f..97aedc9d4 100644 --- a/app/src/main/java/org/tasks/preferences/BasePreferences.kt +++ b/app/src/main/java/org/tasks/preferences/BasePreferences.kt @@ -12,7 +12,6 @@ import org.tasks.R import org.tasks.databinding.ActivityPreferencesBinding import org.tasks.injection.InjectingPreferenceFragment import org.tasks.injection.ThemedInjectingAppCompatActivity -import org.tasks.ui.MenuColorizer private const val EXTRA_TITLE = "extra_title" @@ -48,7 +47,7 @@ abstract class BasePreferences : ThemedInjectingAppCompatActivity(), ContextCompat.getDrawable(this, R.drawable.ic_outline_arrow_back_24px) toolbar.setNavigationOnClickListener { onBackPressed() } toolbar.setOnMenuItemClickListener(this) - MenuColorizer.colorToolbar(this, toolbar) + themeColor.apply(toolbar) } private fun setupMenu() = setupMenu(supportFragmentManager.findFragmentById(R.id.settings)) diff --git a/app/src/main/java/org/tasks/tags/TagPickerActivity.java b/app/src/main/java/org/tasks/tags/TagPickerActivity.java index b5af2e885..2669b0b2f 100644 --- a/app/src/main/java/org/tasks/tags/TagPickerActivity.java +++ b/app/src/main/java/org/tasks/tags/TagPickerActivity.java @@ -22,7 +22,6 @@ import org.tasks.tags.CheckBoxTriStates.State; import org.tasks.themes.Theme; import org.tasks.themes.ThemeCache; import org.tasks.themes.ThemeColor; -import org.tasks.ui.MenuColorizer; public class TagPickerActivity extends ThemedInjectingAppCompatActivity { @@ -65,10 +64,10 @@ public class TagPickerActivity extends ThemedInjectingAppCompatActivity { toolbar.setNavigationIcon(R.drawable.ic_outline_arrow_back_24px); toolbar.setNavigationOnClickListener(v -> onBackPressed()); - MenuColorizer.colorToolbar(this, toolbar); ThemeColor themeColor = theme.getThemeColor(); themeColor.applyToStatusBarIcons(this); themeColor.applyToNavigationBar(this); + themeColor.apply(toolbar); TagRecyclerAdapter recyclerAdapter = new TagRecyclerAdapter(this, viewModel, themeCache, inventory, this::onToggle); diff --git a/app/src/main/java/org/tasks/themes/ColorUtil.java b/app/src/main/java/org/tasks/themes/ColorUtil.java new file mode 100644 index 000000000..77be56cb3 --- /dev/null +++ b/app/src/main/java/org/tasks/themes/ColorUtil.java @@ -0,0 +1,109 @@ +package org.tasks.themes; + +import android.graphics.Color; + +public class ColorUtil { + + /** + * https://stackoverflow.com/a/40964456 + * Darkens a given color + * @param base base color + * @param amount amount between 0 and 100 + * @return darken color + */ + static int darken(int base, int amount) { + if (base == 0 || base == -1) { + return base; + } + + float[] hsv = new float[3]; + Color.colorToHSV(base, hsv); + float[] hsl = hsv2hsl(hsv); + hsl[2] -= amount / 100f; + if (hsl[2] < 0) + hsl[2] = 0f; + hsv = hsl2hsv(hsl); + return Color.HSVToColor(hsv); + } + + /** + * lightens a given color + * @param base base color + * @param amount amount between 0 and 100 + * @return lightened + */ + public static int lighten(int base, int amount) { + float[] hsv = new float[3]; + Color.colorToHSV(base, hsv); + float[] hsl = hsv2hsl(hsv); + hsl[2] += amount / 100f; + if (hsl[2] > 1) + hsl[2] = 1f; + hsv = hsl2hsv(hsl); + return Color.HSVToColor(hsv); + } + + + /** + * Converts HSV (Hue, Saturation, Value) color to HSL (Hue, Saturation, Lightness) + * Credit goes to xpansive + * https://gist.github.com/xpansive/1337890 + * @param hsv HSV color array + * @return hsl + */ + private static float[] hsv2hsl(float[] hsv) { + float hue = hsv[0]; + float sat = hsv[1]; + float val = hsv[2]; + + //Saturation is very different between the two color spaces + //If (2-sat)*val < 1 set it to sat*val/((2-sat)*val) + //Otherwise sat*val/(2-(2-sat)*val) + //Conditional is not operating with hue, it is reassigned! + // sat*val/((hue=(2-sat)*val)<1?hue:2-hue) + float nhue = (2f - sat) * val; + float nsat = sat * val / (nhue < 1f ? nhue : 2f - nhue); + if (nsat > 1f) + nsat = 1f; + + return new float[]{ + //[hue, saturation, lightness] + //Range should be between 0 - 1 + hue, //Hue stays the same + + // check nhue and nsat logic + nsat, + + nhue / 2f //Lightness is (2-sat)*val/2 + //See reassignment of hue above + }; + } + + /** + * Reverses hsv2hsl + * Credit goes to xpansive + * https://gist.github.com/xpansive/1337890 + * @param hsl HSL color array + * @return hsv color array + */ + private static float[] hsl2hsv(float[] hsl) { + float hue = hsl[0]; + float sat = hsl[1]; + float light = hsl[2]; + + sat *= light < .5 ? light : 1 - light; + + return new float[]{ + //[hue, saturation, value] + //Range should be between 0 - 1 + + hue, //Hue stays the same + 2f * sat / (light + sat), //Saturation + light + sat //Value + }; + } + + public static String colorToHex(int color) { + return String.format("#%06X", (0xFFFFFF & color)); + } +} \ No newline at end of file diff --git a/app/src/main/java/org/tasks/themes/ThemeCache.java b/app/src/main/java/org/tasks/themes/ThemeCache.java index 32a448473..5d6df2c4d 100644 --- a/app/src/main/java/org/tasks/themes/ThemeCache.java +++ b/app/src/main/java/org/tasks/themes/ThemeCache.java @@ -8,6 +8,7 @@ import android.content.res.Resources; import android.util.TypedValue; import android.view.ContextThemeWrapper; import androidx.appcompat.app.AppCompatDelegate; +import androidx.core.content.ContextCompat; import java.util.ArrayList; import java.util.List; import javax.inject.Inject; @@ -61,14 +62,9 @@ public class ThemeCache { String[] colorNames = resources.getStringArray(R.array.colors); for (int i = 0; i < ThemeColor.COLORS.length; i++) { - Resources.Theme theme = new ContextThemeWrapper(context, ThemeColor.COLORS[i]).getTheme(); colors.add( new ThemeColor( - context, - colorNames[i], - i, - resolveAttribute(theme, R.attr.colorPrimary), - resolveAttribute(theme, R.attr.colorPrimaryVariant))); + context, colorNames[i], i, ContextCompat.getColor(context, ThemeColor.COLORS[i]))); } String[] accentNames = resources.getStringArray(R.array.accents); for (int i = 0; i < ThemeAccent.ACCENTS.length; i++) { @@ -86,7 +82,7 @@ public class ThemeCache { getColor(context, i == 0 ? R.color.black_54 : R.color.white_70))); } untaggedColor = - new ThemeColor(context, null, 19, getColor(context, R.color.tag_color_none_background), 0); + new ThemeColor(context, null, 19, getColor(context, R.color.tag_color_none_background)); } private static int resolveAttribute(Resources.Theme theme, int attribute) { diff --git a/app/src/main/java/org/tasks/themes/ThemeColor.java b/app/src/main/java/org/tasks/themes/ThemeColor.java index 11dd702c1..17cfa6591 100644 --- a/app/src/main/java/org/tasks/themes/ThemeColor.java +++ b/app/src/main/java/org/tasks/themes/ThemeColor.java @@ -8,9 +8,14 @@ import android.app.Activity; import android.app.ActivityManager; import android.content.Context; import android.content.res.Resources; +import android.graphics.PorterDuff; +import android.graphics.drawable.Drawable; import android.os.Build.VERSION_CODES; import android.os.Parcel; import android.os.Parcelable; +import android.view.Menu; +import android.view.MenuItem; +import android.view.SubMenu; import android.view.View; import androidx.annotation.RequiresApi; import androidx.appcompat.widget.Toolbar; @@ -19,7 +24,6 @@ import androidx.drawerlayout.widget.DrawerLayout; import com.google.android.material.appbar.CollapsingToolbarLayout; import org.tasks.R; import org.tasks.dialogs.ColorPickerDialog; -import org.tasks.ui.MenuColorizer; public class ThemeColor implements ColorPickerDialog.Pickable { @@ -73,27 +77,27 @@ public class ThemeColor implements ColorPickerDialog.Pickable { static final int[] COLORS = new int[] { - R.style.BlueGrey, - R.style.DarkGrey, - R.style.Red, - R.style.Pink, - R.style.Purple, - R.style.DeepPurple, - R.style.Indigo, - R.style.Blue, - R.style.LightBlue, - R.style.Cyan, - R.style.Teal, - R.style.Green, - R.style.LightGreen, - R.style.Lime, - R.style.Yellow, - R.style.Amber, - R.style.Orange, - R.style.DeepOrange, - R.style.Brown, - R.style.Grey, - R.style.White + R.color.blue_grey_500, + R.color.grey_900, + R.color.red_500, + R.color.pink_500, + R.color.purple_500, + R.color.deep_purple_500, + R.color.indigo_500, + R.color.blue_500, + R.color.light_blue_500, + R.color.cyan_500, + R.color.teal_500, + R.color.green_500, + R.color.light_green_500, + R.color.lime_500, + R.color.yellow_500, + R.color.amber_500, + R.color.orange_500, + R.color.deep_orange_500, + R.color.brown_500, + R.color.grey_500, + R.color.white_100 }; public static final Parcelable.Creator CREATOR = @@ -111,22 +115,35 @@ public class ThemeColor implements ColorPickerDialog.Pickable { private final String name; private final int index; private final int colorOnPrimary; - private final int style; + private final int color; private final int colorPrimary; private final int colorPrimaryVariant; private final boolean isDark; + public ThemeColor(Context context, int color) { + name = null; + index = -1; + this.color = -1; + colorPrimary = color; + colorPrimaryVariant = ColorUtil.darken(colorPrimary, 12); + + int whiteText = context.getResources().getColor(R.color.white_100); + double contrast = ColorUtils.calculateContrast(whiteText, colorPrimary); + this.isDark = contrast < 3; + colorOnPrimary = isDark ? context.getResources().getColor(R.color.black_87) : whiteText; + } + public ThemeColor( Context context, String name, int index, - int colorPrimary, - int colorPrimaryVariant) { + int colorPrimary) { this.name = name; this.index = index; - this.style = COLORS[index]; + this.color = COLORS[index]; this.colorPrimary = colorPrimary; - this.colorPrimaryVariant = colorPrimaryVariant; + this.colorPrimaryVariant = ColorUtil.darken(colorPrimary, 12); + int whiteText = context.getResources().getColor(R.color.white_100); double contrast = ColorUtils.calculateContrast(whiteText, colorPrimary); this.isDark = contrast < 3; @@ -137,7 +154,7 @@ public class ThemeColor implements ColorPickerDialog.Pickable { name = source.readString(); index = source.readInt(); colorOnPrimary = source.readInt(); - style = source.readInt(); + color = source.readInt(); colorPrimary = source.readInt(); colorPrimaryVariant = source.readInt(); isDark = source.readInt() == 1; @@ -207,7 +224,6 @@ public class ThemeColor implements ColorPickerDialog.Pickable { } void applyStyle(Resources.Theme theme) { - theme.applyStyle(style, true); theme.applyStyle(isDark ? R.style.BlackToolbarTheme : R.style.WhiteToolbarTheme, true); } @@ -230,10 +246,10 @@ public class ThemeColor implements ColorPickerDialog.Pickable { @Override public boolean isFree() { - switch (style) { - case R.style.Blue: - case R.style.BlueGrey: - case R.style.DarkGrey: + switch (color) { + case R.color.blue_500: + case R.color.blue_grey_500: + case R.color.grey_900: return true; default: return false; @@ -255,7 +271,9 @@ public class ThemeColor implements ColorPickerDialog.Pickable { public void apply(Toolbar toolbar) { toolbar.setBackgroundColor(getPrimaryColor()); - MenuColorizer.colorToolbar(toolbar, colorOnPrimary); + toolbar.setNavigationIcon(colorDrawable(toolbar.getNavigationIcon(), colorOnPrimary)); + toolbar.setTitleTextColor(colorOnPrimary); + colorMenu(toolbar.getMenu(), colorOnPrimary); } @Override @@ -268,9 +286,38 @@ public class ThemeColor implements ColorPickerDialog.Pickable { dest.writeString(name); dest.writeInt(index); dest.writeInt(colorOnPrimary); - dest.writeInt(style); + dest.writeInt(color); dest.writeInt(colorPrimary); dest.writeInt(colorPrimaryVariant); dest.writeInt(isDark ? 1 : 0); } + + public void colorMenu(Menu menu) { + colorMenu(menu, colorOnPrimary); + } + + private static void colorMenu(Menu menu, int color) { + for (int i = 0, size = menu.size(); i < size; i++) { + final MenuItem menuItem = menu.getItem(i); + colorMenuItem(menuItem, color); + if (menuItem.hasSubMenu()) { + final SubMenu subMenu = menuItem.getSubMenu(); + for (int j = 0; j < subMenu.size(); j++) { + colorMenuItem(subMenu.getItem(j), color); + } + } + } + } + + private static void colorMenuItem(final MenuItem menuItem, final int color) { + colorDrawable(menuItem.getIcon(), color); + } + + private static Drawable colorDrawable(Drawable drawable, int color) { + if (drawable != null) { + drawable.mutate(); + drawable.setColorFilter(color, PorterDuff.Mode.SRC_IN); + } + return drawable; + } } diff --git a/app/src/main/java/org/tasks/ui/MenuColorizer.java b/app/src/main/java/org/tasks/ui/MenuColorizer.java deleted file mode 100644 index 2fe739e19..000000000 --- a/app/src/main/java/org/tasks/ui/MenuColorizer.java +++ /dev/null @@ -1,96 +0,0 @@ -/* - * Copyright (C) 2014 Jared Rummler - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package org.tasks.ui; - -import android.content.Context; -import android.graphics.PorterDuff; -import android.graphics.drawable.Drawable; -import android.util.TypedValue; -import android.view.Menu; -import android.view.MenuItem; -import android.view.SubMenu; -import androidx.appcompat.widget.Toolbar; -import org.tasks.R; - -/** - * Helper class to set the color and transparency for menu icons in an ActionBar/Toolbar. Example - * usage: - * - *
- * 
- * public boolean onCreateOptionsMenu(Menu menu) {
- *     ...
- *     int color = getResources().getColor(R.color.your_awesome_color);
- *     int alpha = 204; // 80% alpha
- *     MenuColorizer.colorMenu(this, menu, color, alpha);
- *     ...
- * }
- * 
- * 
- * - * @author Jared Rummler - * @since Dec 11, 2014 - */ -public class MenuColorizer { - - private MenuColorizer() {} - - public static void colorToolbar(Context context, Toolbar toolbar) { - TypedValue typedValue = new TypedValue(); - context.getTheme().resolveAttribute(R.attr.colorOnPrimary, typedValue, true); - colorToolbar(toolbar, typedValue.data); - } - - public static void colorToolbar(Toolbar toolbar, int color) { - toolbar.setNavigationIcon(colorDrawable(toolbar.getNavigationIcon(), color)); - toolbar.setTitleTextColor(color); - colorMenu(toolbar.getMenu(), color); - } - - public static void colorMenu(Context context, Menu menu) { - TypedValue typedValue = new TypedValue(); - context.getTheme().resolveAttribute(R.attr.colorOnPrimary, typedValue, true); - colorMenu(menu, typedValue.data); - } - - /** Sets a color filter on all menu icons, including the overflow button (if it exists) */ - private static void colorMenu(final Menu menu, final int color) { - for (int i = 0, size = menu.size(); i < size; i++) { - final MenuItem menuItem = menu.getItem(i); - colorMenuItem(menuItem, color); - if (menuItem.hasSubMenu()) { - final SubMenu subMenu = menuItem.getSubMenu(); - for (int j = 0; j < subMenu.size(); j++) { - colorMenuItem(subMenu.getItem(j), color); - } - } - } - } - - /** Sets a color filter on a {@link MenuItem} */ - private static void colorMenuItem(final MenuItem menuItem, final int color) { - colorDrawable(menuItem.getIcon(), color); - } - - private static Drawable colorDrawable(Drawable drawable, int color) { - if (drawable != null) { - drawable.mutate(); - drawable.setColorFilter(color, PorterDuff.Mode.SRC_IN); - } - return drawable; - } -} diff --git a/app/src/main/java/org/tasks/ui/TaskEditControlFragment.java b/app/src/main/java/org/tasks/ui/TaskEditControlFragment.java index b5f37f7d8..5aee383ff 100644 --- a/app/src/main/java/org/tasks/ui/TaskEditControlFragment.java +++ b/app/src/main/java/org/tasks/ui/TaskEditControlFragment.java @@ -12,14 +12,17 @@ import butterknife.ButterKnife; import com.todoroo.astrid.data.Task; import org.tasks.R; import org.tasks.injection.InjectingFragment; +import org.tasks.themes.ThemeColor; public abstract class TaskEditControlFragment extends InjectingFragment { public static final String EXTRA_TASK = "extra_task"; public static final String EXTRA_IS_NEW = "extra_is_new"; + public static final String EXTRA_THEME = "extra_theme"; protected Task task; private boolean isNew; + protected ThemeColor themeColor; @Nullable @Override @@ -42,6 +45,7 @@ public abstract class TaskEditControlFragment extends InjectingFragment { if (arguments != null) { task = arguments.getParcelable(EXTRA_TASK); isNew = arguments.getBoolean(EXTRA_IS_NEW); + themeColor = arguments.getParcelable(EXTRA_THEME); } } diff --git a/app/src/main/java/org/tasks/widget/ShortcutConfigActivity.java b/app/src/main/java/org/tasks/widget/ShortcutConfigActivity.java index 693389884..bd4206967 100644 --- a/app/src/main/java/org/tasks/widget/ShortcutConfigActivity.java +++ b/app/src/main/java/org/tasks/widget/ShortcutConfigActivity.java @@ -26,7 +26,6 @@ import org.tasks.intents.TaskIntents; import org.tasks.preferences.DefaultFilterProvider; import org.tasks.themes.ThemeCache; import org.tasks.themes.ThemeColor; -import org.tasks.ui.MenuColorizer; public class ShortcutConfigActivity extends InjectingAppCompatActivity { @@ -68,7 +67,6 @@ public class ShortcutConfigActivity extends InjectingAppCompatActivity { toolbar.setTitle(R.string.FSA_label); toolbar.setNavigationIcon(ContextCompat.getDrawable(this, R.drawable.ic_outline_save_24px)); toolbar.setNavigationOnClickListener(v -> save()); - MenuColorizer.colorToolbar(this, toolbar); if (icicle == null) { selectedFilter = defaultFilterProvider.getDefaultFilter(); diff --git a/app/src/main/res/layout/toolbar.xml b/app/src/main/res/layout/toolbar.xml index e7c694436..953213f19 100644 --- a/app/src/main/res/layout/toolbar.xml +++ b/app/src/main/res/layout/toolbar.xml @@ -4,7 +4,6 @@ android:id="@+id/toolbar" android:layout_width="match_parent" android:layout_height="?attr/actionBarSize" - android:background="?attr/colorPrimary" android:elevation="@dimen/elevation_toolbar" android:theme="?attr/overlay_theme" app:popupTheme="@style/popup_overlay" diff --git a/app/src/main/res/values/accents.xml b/app/src/main/res/values/accents.xml new file mode 100644 index 000000000..fbf96ec8b --- /dev/null +++ b/app/src/main/res/values/accents.xml @@ -0,0 +1,72 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/app/src/main/res/values/colors.xml b/app/src/main/res/values/colors.xml index 1ef95d1ff..dc265f25c 100644 --- a/app/src/main/res/values/colors.xml +++ b/app/src/main/res/values/colors.xml @@ -7,82 +7,63 @@ #f44336 - #d32f2f #ff1744 #e91e63 - #c2185b #f50057 #9c27b0 - #7b1fa2 #d500f9 #673ab7 - #512da8 #651fff #3f51b5 - #303f9f #3d5afe #2196f3 - #1976d2 #2979ff #03a9f4 - #0288d1 #00b0ff #00bcd4 - #0097a7 #00e5ff #009688 - #00796b #1de9b6 #4caf50 - #388e3c #00e676 #8bc34a - #689f38 #76ff03 #cddc39 - #afb42b #c6ff00 #ffeb3b - #fbc02d #ffea00 #ffc107 - #ffa000 #ffc400 #ff9800 - #f57c00 #ff9100 #ff5722 - #e64a19 #ff3d00 #795548 - #5d4037 #fafafa #9e9e9e - #616161 #424242 #212121 #111111 #78909c #607d8b - #455a64 #de000000 #8a000000 diff --git a/app/src/main/res/values/theme_amber.xml b/app/src/main/res/values/theme_amber.xml deleted file mode 100644 index 50e2d2b50..000000000 --- a/app/src/main/res/values/theme_amber.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_blue.xml b/app/src/main/res/values/theme_blue.xml deleted file mode 100644 index 4dee2f20e..000000000 --- a/app/src/main/res/values/theme_blue.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_blue_grey.xml b/app/src/main/res/values/theme_blue_grey.xml deleted file mode 100644 index 510d9a78b..000000000 --- a/app/src/main/res/values/theme_blue_grey.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_brown.xml b/app/src/main/res/values/theme_brown.xml deleted file mode 100644 index 59e4933a1..000000000 --- a/app/src/main/res/values/theme_brown.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_cyan.xml b/app/src/main/res/values/theme_cyan.xml deleted file mode 100644 index 99d44e06e..000000000 --- a/app/src/main/res/values/theme_cyan.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_dark_grey.xml b/app/src/main/res/values/theme_dark_grey.xml deleted file mode 100644 index a305054aa..000000000 --- a/app/src/main/res/values/theme_dark_grey.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_deep_orange.xml b/app/src/main/res/values/theme_deep_orange.xml deleted file mode 100644 index 8c4ec5748..000000000 --- a/app/src/main/res/values/theme_deep_orange.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_deep_purple.xml b/app/src/main/res/values/theme_deep_purple.xml deleted file mode 100644 index d402af132..000000000 --- a/app/src/main/res/values/theme_deep_purple.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_green.xml b/app/src/main/res/values/theme_green.xml deleted file mode 100644 index 248cc7883..000000000 --- a/app/src/main/res/values/theme_green.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_grey.xml b/app/src/main/res/values/theme_grey.xml deleted file mode 100644 index 162e0e2e1..000000000 --- a/app/src/main/res/values/theme_grey.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_indigo.xml b/app/src/main/res/values/theme_indigo.xml deleted file mode 100644 index 4dbeda3bf..000000000 --- a/app/src/main/res/values/theme_indigo.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_light_blue.xml b/app/src/main/res/values/theme_light_blue.xml deleted file mode 100644 index 5a24582d5..000000000 --- a/app/src/main/res/values/theme_light_blue.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_light_green.xml b/app/src/main/res/values/theme_light_green.xml deleted file mode 100644 index 54f012384..000000000 --- a/app/src/main/res/values/theme_light_green.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_lime.xml b/app/src/main/res/values/theme_lime.xml deleted file mode 100644 index 7bdeea0b2..000000000 --- a/app/src/main/res/values/theme_lime.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_orange.xml b/app/src/main/res/values/theme_orange.xml deleted file mode 100644 index 499d49a26..000000000 --- a/app/src/main/res/values/theme_orange.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_pink.xml b/app/src/main/res/values/theme_pink.xml deleted file mode 100644 index 068cda5c5..000000000 --- a/app/src/main/res/values/theme_pink.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_purple.xml b/app/src/main/res/values/theme_purple.xml deleted file mode 100644 index 3bd57b844..000000000 --- a/app/src/main/res/values/theme_purple.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_red.xml b/app/src/main/res/values/theme_red.xml deleted file mode 100644 index b044ca4c3..000000000 --- a/app/src/main/res/values/theme_red.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_teal.xml b/app/src/main/res/values/theme_teal.xml deleted file mode 100644 index c86d62f36..000000000 --- a/app/src/main/res/values/theme_teal.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_white.xml b/app/src/main/res/values/theme_white.xml deleted file mode 100644 index 2c70e0e13..000000000 --- a/app/src/main/res/values/theme_white.xml +++ /dev/null @@ -1,9 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/app/src/main/res/values/theme_yellow.xml b/app/src/main/res/values/theme_yellow.xml deleted file mode 100644 index 0ef72f7f1..000000000 --- a/app/src/main/res/values/theme_yellow.xml +++ /dev/null @@ -1,13 +0,0 @@ - - - - - - - - \ No newline at end of file