packages/apps/Launcher3
Revision | ed358c89c81370019215d9e81748afca877396e5 (tree) |
---|---|
Time | 2017-06-11 16:16:10 |
Author | android-build-team Robot <android-build-team-robot@goog...> |
Commiter | android-build-team Robot |
release-request-276f9f52-87fd-4915-bd79-9a2f0ee77433-for-git_oc-release-4090213 snap-temp-L31600000073091223
Change-Id: I9888956d3dbb66f8de012ef2e61395075ff4fa72
@@ -82,7 +82,8 @@ | ||
82 | 82 | |
83 | 83 | <service android:name="com.android.launcher3.dynamicui.ColorExtractionService" |
84 | 84 | android:exported="false" |
85 | - android:process=":wallpaper_chooser"> | |
85 | + android:process=":wallpaper_chooser" | |
86 | + android:permission="android.permission.BIND_JOB_SERVICE"> | |
86 | 87 | </service> |
87 | 88 | |
88 | 89 | <service android:name="com.android.launcher3.notification.NotificationListener" |
@@ -120,7 +120,7 @@ | ||
120 | 120 | <string name="widget_resized" msgid="9130327887929620">"ウィジェットのサイズを幅<xliff:g id="NUMBER_0">%1$s</xliff:g>、高さ<xliff:g id="NUMBER_1">%2$s</xliff:g>に変更しました"</string> |
121 | 121 | <string name="action_deep_shortcut" msgid="2864038805849372848">"ショートカット"</string> |
122 | 122 | <string name="shortcuts_menu_description" msgid="406159963824238648">"<xliff:g id="APP_NAME">%2$s</xliff:g>用の <xliff:g id="NUMBER_OF_SHORTCUTS">%1$d</xliff:g> 件のショートカット"</string> |
123 | - <string name="shortcuts_menu_with_notifications_description" msgid="8985659504915468840">"<xliff:g id="APP_NAME">%3$s</xliff:g>: <xliff:g id="NUMBER_OF_SHORTCUTS">%1$d</xliff:g> 件のショートカットと <xliff:g id="NUMBER_OF_NOTIFICATIONS">%2$d</xliff:g> 件の通知"</string> | |
123 | + <string name="shortcuts_menu_with_notifications_description" msgid="8985659504915468840">"<xliff:g id="APP_NAME">%3$s</xliff:g>: <xliff:g id="NUMBER_OF_SHORTCUTS">%1$d</xliff:g> 個のショートカットと <xliff:g id="NUMBER_OF_NOTIFICATIONS">%2$d</xliff:g> 件の通知"</string> | |
124 | 124 | <string name="action_dismiss_notification" msgid="5909461085055959187">"表示しない"</string> |
125 | 125 | <string name="notification_dismissed" msgid="6002233469409822874">"通知を非表示にしました"</string> |
126 | 126 | </resources> |
@@ -42,6 +42,7 @@ | ||
42 | 42 | <color name="notification_color_beneath">#E0E0E0</color> <!-- Gray 300 --> |
43 | 43 | |
44 | 44 | <color name="badge_color">#1DE9B6</color> <!-- Teal A400 --> |
45 | + <color name="folder_badge_color">#1DE9B6</color> <!-- Teal A400 --> | |
45 | 46 | |
46 | 47 | <!-- System shortcuts --> |
47 | 48 | <color name="system_shortcuts_icon_color">@android:color/tertiary_text_light</color> |
@@ -172,12 +172,12 @@ | ||
172 | 172 | <string name="allow_rotation_desc">When phone is rotated</string> |
173 | 173 | <!-- Text explaining that rotation is disabled in Display settings. 'Display' refers to the Display section in system settings [CHAR LIMIT=100] --> |
174 | 174 | <string name="allow_rotation_blocked_desc">Current Display setting doesn\'t permit rotation</string> |
175 | - <!-- Title for Icon Badging setting. Tapping this will link to the system Notifications Settings screen where the user can turn off badging globally. [CHAR LIMIT=50] --> | |
176 | - <string name="icon_badging_title">Icon badging</string> | |
175 | + <!-- Title for Notification dots setting. Tapping this will link to the system Notifications settings screen where the user can turn off notification dots globally. [CHAR LIMIT=50] --> | |
176 | + <string name="icon_badging_title">Notification dots</string> | |
177 | 177 | <!-- Text to indicate that the system icon badging setting is on [CHAR LIMIT=100] --> |
178 | - <string name="icon_badging_desc_on">On for all apps</string> | |
178 | + <string name="icon_badging_desc_on">On</string> | |
179 | 179 | <!-- Text to indicate that the system icon badging setting is off [CHAR LIMIT=100] --> |
180 | - <string name="icon_badging_desc_off">Off for all apps</string> | |
180 | + <string name="icon_badging_desc_off">Off</string> | |
181 | 181 | |
182 | 182 | <!-- Label for the setting that allows the automatic placement of launcher shortcuts for applications and games installed on the device [CHAR LIMIT=40] --> |
183 | 183 | <string name="auto_add_shortcuts_label">Add icon to Home screen</string> |
@@ -96,7 +96,7 @@ public class BubbleTextView extends TextView implements ItemInfoUpdateReceiver { | ||
96 | 96 | |
97 | 97 | private BadgeInfo mBadgeInfo; |
98 | 98 | private BadgeRenderer mBadgeRenderer; |
99 | - private IconPalette mIconPalette; | |
99 | + private IconPalette mBadgePalette; | |
100 | 100 | private float mBadgeScale; |
101 | 101 | private boolean mForceHideBadge; |
102 | 102 | private Point mTempSpaceForBadgeOffset = new Point(); |
@@ -453,7 +453,7 @@ public class BubbleTextView extends TextView implements ItemInfoUpdateReceiver { | ||
453 | 453 | final int scrollX = getScrollX(); |
454 | 454 | final int scrollY = getScrollY(); |
455 | 455 | canvas.translate(scrollX, scrollY); |
456 | - mBadgeRenderer.draw(canvas, mBadgeInfo, mTempIconBounds, mBadgeScale, | |
456 | + mBadgeRenderer.draw(canvas, mBadgePalette, mBadgeInfo, mTempIconBounds, mBadgeScale, | |
457 | 457 | mTempSpaceForBadgeOffset); |
458 | 458 | canvas.translate(-scrollX, -scrollY); |
459 | 459 | } |
@@ -578,7 +578,10 @@ public class BubbleTextView extends TextView implements ItemInfoUpdateReceiver { | ||
578 | 578 | float newBadgeScale = isBadged ? 1f : 0; |
579 | 579 | mBadgeRenderer = mLauncher.getDeviceProfile().mBadgeRenderer; |
580 | 580 | if (wasBadged || isBadged) { |
581 | - mIconPalette = ((FastBitmapDrawable) mIcon).getIconPalette(); | |
581 | + mBadgePalette = IconPalette.getBadgePalette(getResources()); | |
582 | + if (mBadgePalette == null) { | |
583 | + mBadgePalette = ((FastBitmapDrawable) mIcon).getIconPalette(); | |
584 | + } | |
582 | 585 | // Animate when a badge is first added or when it is removed. |
583 | 586 | if (animate && (wasBadged ^ isBadged) && isShown()) { |
584 | 587 | ObjectAnimator.ofFloat(this, BADGE_SCALE_PROPERTY, newBadgeScale).start(); |
@@ -590,6 +593,10 @@ public class BubbleTextView extends TextView implements ItemInfoUpdateReceiver { | ||
590 | 593 | } |
591 | 594 | } |
592 | 595 | |
596 | + public IconPalette getBadgePalette() { | |
597 | + return mBadgePalette; | |
598 | + } | |
599 | + | |
593 | 600 | /** |
594 | 601 | * Sets the icon for this view based on the layout direction. |
595 | 602 | */ |
@@ -124,7 +124,7 @@ public class FastBitmapDrawable extends Drawable { | ||
124 | 124 | public IconPalette getIconPalette() { |
125 | 125 | if (mIconPalette == null) { |
126 | 126 | mIconPalette = IconPalette.fromDominantColor(Utilities |
127 | - .findDominantColorByHue(mBitmap, 20)); | |
127 | + .findDominantColorByHue(mBitmap, 20), true /* desaturateBackground */); | |
128 | 128 | } |
129 | 129 | return mIconPalette; |
130 | 130 | } |
@@ -61,7 +61,6 @@ import java.lang.reflect.Method; | ||
61 | 61 | import java.util.Collection; |
62 | 62 | import java.util.HashSet; |
63 | 63 | import java.util.Locale; |
64 | -import java.util.Set; | |
65 | 64 | import java.util.concurrent.Executor; |
66 | 65 | import java.util.concurrent.LinkedBlockingQueue; |
67 | 66 | import java.util.concurrent.ThreadPoolExecutor; |
@@ -110,6 +109,8 @@ public final class Utilities { | ||
110 | 109 | // An intent extra to indicate the horizontal scroll of the wallpaper. |
111 | 110 | public static final String EXTRA_WALLPAPER_OFFSET = "com.android.launcher3.WALLPAPER_OFFSET"; |
112 | 111 | |
112 | + public static final int COLOR_EXTRACTION_JOB_ID = 1; | |
113 | + | |
113 | 114 | // These values are same as that in {@link AsyncTask}. |
114 | 115 | private static final int CPU_COUNT = Runtime.getRuntime().availableProcessors(); |
115 | 116 | private static final int CORE_POOL_SIZE = CPU_COUNT + 1; |
@@ -63,7 +63,6 @@ public class BadgeRenderer { | ||
63 | 63 | private final Paint mBackgroundPaint = new Paint(Paint.ANTI_ALIAS_FLAG |
64 | 64 | | Paint.FILTER_BITMAP_FLAG); |
65 | 65 | private final SparseArray<Bitmap> mBackgroundsWithShadow; |
66 | - private final IconPalette mIconPalette; | |
67 | 66 | |
68 | 67 | public BadgeRenderer(Context context, int iconSizePx) { |
69 | 68 | mContext = context; |
@@ -83,25 +82,24 @@ public class BadgeRenderer { | ||
83 | 82 | mTextHeight = tempTextHeight.height(); |
84 | 83 | |
85 | 84 | mBackgroundsWithShadow = new SparseArray<>(3); |
86 | - | |
87 | - mIconPalette = IconPalette.fromDominantColor(context.getColor(R.color.badge_color)); | |
88 | 85 | } |
89 | 86 | |
90 | 87 | /** |
91 | 88 | * Draw a circle in the top right corner of the given bounds, and draw |
92 | 89 | * {@link BadgeInfo#getNotificationCount()} on top of the circle. |
90 | + * @param palette The colors (based on the icon) to use for the badge. | |
93 | 91 | * @param badgeInfo Contains data to draw on the badge. Could be null if we are animating out. |
94 | 92 | * @param iconBounds The bounds of the icon being badged. |
95 | 93 | * @param badgeScale The progress of the animation, from 0 to 1. |
96 | 94 | * @param spaceForOffset How much space is available to offset the badge up and to the right. |
97 | 95 | */ |
98 | - public void draw(Canvas canvas, @Nullable BadgeInfo badgeInfo, | |
96 | + public void draw(Canvas canvas, IconPalette palette, @Nullable BadgeInfo badgeInfo, | |
99 | 97 | Rect iconBounds, float badgeScale, Point spaceForOffset) { |
100 | - mTextPaint.setColor(mIconPalette.textColor); | |
98 | + mTextPaint.setColor(palette.textColor); | |
101 | 99 | IconDrawer iconDrawer = badgeInfo != null && badgeInfo.isIconLarge() |
102 | 100 | ? mLargeIconDrawer : mSmallIconDrawer; |
103 | 101 | Shader icon = badgeInfo == null ? null : badgeInfo.getNotificationIconForBadge( |
104 | - mContext, mIconPalette.backgroundColor, mSize, iconDrawer.mPadding); | |
102 | + mContext, palette.backgroundColor, mSize, iconDrawer.mPadding); | |
105 | 103 | String notificationCount = badgeInfo == null ? "0" |
106 | 104 | : String.valueOf(badgeInfo.getNotificationCount()); |
107 | 105 | int numChars = notificationCount.length(); |
@@ -127,7 +125,7 @@ public class BadgeRenderer { | ||
127 | 125 | canvas.translate(badgeCenterX + offsetX, badgeCenterY - offsetY); |
128 | 126 | canvas.scale(badgeScale, badgeScale); |
129 | 127 | // Prepare the background and shadow and possible stacking effect. |
130 | - mBackgroundPaint.setColorFilter(mIconPalette.backgroundColorMatrixFilter); | |
128 | + mBackgroundPaint.setColorFilter(palette.backgroundColorMatrixFilter); | |
131 | 129 | int backgroundWithShadowSize = backgroundWithShadow.getHeight(); // Same as width. |
132 | 130 | boolean shouldStack = !isDot && badgeInfo != null |
133 | 131 | && badgeInfo.getNotificationKeys().size() > 1; |
@@ -149,7 +147,7 @@ public class BadgeRenderer { | ||
149 | 147 | -backgroundWithShadowSize / 2, mBackgroundPaint); |
150 | 148 | iconDrawer.drawIcon(icon, canvas); |
151 | 149 | } else if (isDot) { |
152 | - mBackgroundPaint.setColorFilter(mIconPalette.saturatedBackgroundColorMatrixFilter); | |
150 | + mBackgroundPaint.setColorFilter(palette.saturatedBackgroundColorMatrixFilter); | |
153 | 151 | canvas.drawBitmap(backgroundWithShadow, -backgroundWithShadowSize / 2, |
154 | 152 | -backgroundWithShadowSize / 2, mBackgroundPaint); |
155 | 153 | } |
@@ -17,15 +17,17 @@ | ||
17 | 17 | package com.android.launcher3.dynamicui; |
18 | 18 | |
19 | 19 | import android.annotation.TargetApi; |
20 | -import android.app.IntentService; | |
21 | 20 | import android.app.WallpaperManager; |
22 | -import android.content.Intent; | |
21 | +import android.app.job.JobParameters; | |
22 | +import android.app.job.JobService; | |
23 | 23 | import android.graphics.Bitmap; |
24 | 24 | import android.graphics.BitmapRegionDecoder; |
25 | 25 | import android.graphics.Rect; |
26 | 26 | import android.graphics.drawable.BitmapDrawable; |
27 | 27 | import android.os.Build; |
28 | 28 | import android.os.Bundle; |
29 | +import android.os.Handler; | |
30 | +import android.os.HandlerThread; | |
29 | 31 | import android.os.ParcelFileDescriptor; |
30 | 32 | import android.support.v7.graphics.Palette; |
31 | 33 | import android.util.Log; |
@@ -41,45 +43,76 @@ import java.io.IOException; | ||
41 | 43 | /** |
42 | 44 | * Extracts colors from the wallpaper, and saves results to {@link LauncherProvider}. |
43 | 45 | */ |
44 | -public class ColorExtractionService extends IntentService { | |
46 | +public class ColorExtractionService extends JobService { | |
45 | 47 | |
46 | 48 | private static final String TAG = "ColorExtractionService"; |
49 | + private static final boolean DEBUG = false; | |
47 | 50 | |
48 | 51 | /** The fraction of the wallpaper to extract colors for use on the hotseat. */ |
49 | 52 | private static final float HOTSEAT_FRACTION = 1f / 4; |
50 | 53 | |
51 | - public ColorExtractionService() { | |
52 | - super("ColorExtractionService"); | |
54 | + private HandlerThread mWorkerThread; | |
55 | + private Handler mWorkerHandler; | |
56 | + | |
57 | + @Override | |
58 | + public void onCreate() { | |
59 | + super.onCreate(); | |
60 | + mWorkerThread = new HandlerThread("ColorExtractionService"); | |
61 | + mWorkerThread.start(); | |
62 | + mWorkerHandler = new Handler(mWorkerThread.getLooper()); | |
53 | 63 | } |
54 | 64 | |
55 | 65 | @Override |
56 | - protected void onHandleIntent(Intent intent) { | |
57 | - WallpaperManager wallpaperManager = WallpaperManager.getInstance(this); | |
58 | - int wallpaperId = ExtractionUtils.getWallpaperId(wallpaperManager); | |
59 | - | |
60 | - ExtractedColors extractedColors = new ExtractedColors(); | |
61 | - if (wallpaperManager.getWallpaperInfo() != null) { | |
62 | - // We can't extract colors from live wallpapers, so just use the default color always. | |
63 | - extractedColors.updateHotseatPalette(null); | |
64 | - } else { | |
65 | - // We extract colors for the hotseat and status bar separately, | |
66 | - // since they only consider part of the wallpaper. | |
67 | - extractedColors.updateHotseatPalette(getHotseatPalette()); | |
68 | - | |
69 | - if (FeatureFlags.LIGHT_STATUS_BAR) { | |
70 | - extractedColors.updateStatusBarPalette(getStatusBarPalette()); | |
66 | + public void onDestroy() { | |
67 | + super.onDestroy(); | |
68 | + mWorkerThread.quit(); | |
69 | + } | |
70 | + | |
71 | + @Override | |
72 | + public boolean onStartJob(final JobParameters jobParameters) { | |
73 | + if (DEBUG) Log.d(TAG, "onStartJob"); | |
74 | + mWorkerHandler.post(new Runnable() { | |
75 | + @Override | |
76 | + public void run() { | |
77 | + WallpaperManager wallpaperManager = WallpaperManager.getInstance( | |
78 | + ColorExtractionService.this); | |
79 | + int wallpaperId = ExtractionUtils.getWallpaperId(wallpaperManager); | |
80 | + | |
81 | + ExtractedColors extractedColors = new ExtractedColors(); | |
82 | + if (wallpaperManager.getWallpaperInfo() != null) { | |
83 | + // We can't extract colors from live wallpapers; always use the default color. | |
84 | + extractedColors.updateHotseatPalette(null); | |
85 | + } else { | |
86 | + // We extract colors for the hotseat and status bar separately, | |
87 | + // since they only consider part of the wallpaper. | |
88 | + extractedColors.updateHotseatPalette(getHotseatPalette()); | |
89 | + | |
90 | + if (FeatureFlags.LIGHT_STATUS_BAR) { | |
91 | + extractedColors.updateStatusBarPalette(getStatusBarPalette()); | |
92 | + } | |
93 | + } | |
94 | + | |
95 | + // Save the extracted colors and wallpaper id to LauncherProvider. | |
96 | + String colorsString = extractedColors.encodeAsString(); | |
97 | + Bundle extras = new Bundle(); | |
98 | + extras.putInt(LauncherSettings.Settings.EXTRA_WALLPAPER_ID, wallpaperId); | |
99 | + extras.putString(LauncherSettings.Settings.EXTRA_EXTRACTED_COLORS, colorsString); | |
100 | + getContentResolver().call( | |
101 | + LauncherSettings.Settings.CONTENT_URI, | |
102 | + LauncherSettings.Settings.METHOD_SET_EXTRACTED_COLORS_AND_WALLPAPER_ID, | |
103 | + null, extras); | |
104 | + jobFinished(jobParameters, false /* needsReschedule */); | |
105 | + if (DEBUG) Log.d(TAG, "job finished!"); | |
71 | 106 | } |
72 | - } | |
107 | + }); | |
108 | + return true; | |
109 | + } | |
73 | 110 | |
74 | - // Save the extracted colors and wallpaper id to LauncherProvider. | |
75 | - String colorsString = extractedColors.encodeAsString(); | |
76 | - Bundle extras = new Bundle(); | |
77 | - extras.putInt(LauncherSettings.Settings.EXTRA_WALLPAPER_ID, wallpaperId); | |
78 | - extras.putString(LauncherSettings.Settings.EXTRA_EXTRACTED_COLORS, colorsString); | |
79 | - getContentResolver().call( | |
80 | - LauncherSettings.Settings.CONTENT_URI, | |
81 | - LauncherSettings.Settings.METHOD_SET_EXTRACTED_COLORS_AND_WALLPAPER_ID, | |
82 | - null, extras); | |
111 | + @Override | |
112 | + public boolean onStopJob(JobParameters jobParameters) { | |
113 | + if (DEBUG) Log.d(TAG, "onStopJob"); | |
114 | + mWorkerHandler.removeCallbacksAndMessages(null); | |
115 | + return true; | |
83 | 116 | } |
84 | 117 | |
85 | 118 | @TargetApi(Build.VERSION_CODES.N) |
@@ -18,8 +18,10 @@ package com.android.launcher3.dynamicui; | ||
18 | 18 | |
19 | 19 | import android.annotation.TargetApi; |
20 | 20 | import android.app.WallpaperManager; |
21 | +import android.app.job.JobInfo; | |
22 | +import android.app.job.JobScheduler; | |
23 | +import android.content.ComponentName; | |
21 | 24 | import android.content.Context; |
22 | -import android.content.Intent; | |
23 | 25 | import android.content.SharedPreferences; |
24 | 26 | import android.graphics.Color; |
25 | 27 | import android.os.Build; |
@@ -58,7 +60,11 @@ public class ExtractionUtils { | ||
58 | 60 | |
59 | 61 | /** Starts the {@link ColorExtractionService} without checking the wallpaper id */ |
60 | 62 | public static void startColorExtractionService(Context context) { |
61 | - context.startService(new Intent(context, ColorExtractionService.class)); | |
63 | + JobScheduler jobScheduler = (JobScheduler) context.getSystemService( | |
64 | + Context.JOB_SCHEDULER_SERVICE); | |
65 | + jobScheduler.schedule(new JobInfo.Builder(Utilities.COLOR_EXTRACTION_JOB_ID, | |
66 | + new ComponentName(context, ColorExtractionService.class)) | |
67 | + .setMinimumLatency(0).build()); | |
62 | 68 | } |
63 | 69 | |
64 | 70 | private static boolean hasWallpaperIdChanged(Context context) { |
@@ -75,6 +75,7 @@ import com.android.launcher3.badge.FolderBadgeInfo; | ||
75 | 75 | import com.android.launcher3.config.FeatureFlags; |
76 | 76 | import com.android.launcher3.dragndrop.DragLayer; |
77 | 77 | import com.android.launcher3.dragndrop.DragView; |
78 | +import com.android.launcher3.graphics.IconPalette; | |
78 | 79 | import com.android.launcher3.util.Thunk; |
79 | 80 | |
80 | 81 | import java.util.ArrayList; |
@@ -885,7 +886,8 @@ public class FolderIcon extends FrameLayout implements FolderListener { | ||
885 | 886 | // If we are animating to the accepting state, animate the badge out. |
886 | 887 | float badgeScale = Math.max(0, mBadgeScale - mBackground.getScaleProgress()); |
887 | 888 | mTempSpaceForBadgeOffset.set(getWidth() - mTempBounds.right, mTempBounds.top); |
888 | - mBadgeRenderer.draw(canvas, mBadgeInfo, mTempBounds, | |
889 | + IconPalette badgePalette = IconPalette.getFolderBadgePalette(getResources()); | |
890 | + mBadgeRenderer.draw(canvas, badgePalette, mBadgeInfo, mTempBounds, | |
889 | 891 | badgeScale, mTempSpaceForBadgeOffset); |
890 | 892 | } |
891 | 893 | } |
@@ -18,9 +18,12 @@ package com.android.launcher3.graphics; | ||
18 | 18 | |
19 | 19 | import android.app.Notification; |
20 | 20 | import android.content.Context; |
21 | +import android.content.res.Resources; | |
21 | 22 | import android.graphics.Color; |
22 | 23 | import android.graphics.ColorMatrix; |
23 | 24 | import android.graphics.ColorMatrixColorFilter; |
25 | +import android.support.annotation.NonNull; | |
26 | +import android.support.annotation.Nullable; | |
24 | 27 | import android.support.v4.graphics.ColorUtils; |
25 | 28 | import android.util.Log; |
26 | 29 |
@@ -35,11 +38,12 @@ public class IconPalette { | ||
35 | 38 | private static final boolean DEBUG = false; |
36 | 39 | private static final String TAG = "IconPalette"; |
37 | 40 | |
38 | - public static final IconPalette FOLDER_ICON_PALETTE = new IconPalette(Color.parseColor("#BDC1C6")); | |
39 | - | |
40 | 41 | private static final float MIN_PRELOAD_COLOR_SATURATION = 0.2f; |
41 | 42 | private static final float MIN_PRELOAD_COLOR_LIGHTNESS = 0.6f; |
42 | 43 | |
44 | + private static IconPalette sBadgePalette; | |
45 | + private static IconPalette sFolderBadgePalette; | |
46 | + | |
43 | 47 | public final int dominantColor; |
44 | 48 | public final int backgroundColor; |
45 | 49 | public final ColorMatrixColorFilter backgroundColorMatrixFilter; |
@@ -47,15 +51,19 @@ public class IconPalette { | ||
47 | 51 | public final int textColor; |
48 | 52 | public final int secondaryColor; |
49 | 53 | |
50 | - private IconPalette(int color) { | |
54 | + private IconPalette(int color, boolean desaturateBackground) { | |
51 | 55 | dominantColor = color; |
52 | - backgroundColor = dominantColor; | |
56 | + backgroundColor = desaturateBackground ? getMutedColor(dominantColor, 0.87f) : dominantColor; | |
53 | 57 | ColorMatrix backgroundColorMatrix = new ColorMatrix(); |
54 | 58 | Themes.setColorScaleOnMatrix(backgroundColor, backgroundColorMatrix); |
55 | 59 | backgroundColorMatrixFilter = new ColorMatrixColorFilter(backgroundColorMatrix); |
56 | - // Get slightly more saturated background color. | |
57 | - Themes.setColorScaleOnMatrix(getMutedColor(dominantColor, 0.54f), backgroundColorMatrix); | |
58 | - saturatedBackgroundColorMatrixFilter = new ColorMatrixColorFilter(backgroundColorMatrix); | |
60 | + if (!desaturateBackground) { | |
61 | + saturatedBackgroundColorMatrixFilter = backgroundColorMatrixFilter; | |
62 | + } else { | |
63 | + // Get slightly more saturated background color. | |
64 | + Themes.setColorScaleOnMatrix(getMutedColor(dominantColor, 0.54f), backgroundColorMatrix); | |
65 | + saturatedBackgroundColorMatrixFilter = new ColorMatrixColorFilter(backgroundColorMatrix); | |
66 | + } | |
59 | 67 | textColor = getTextColorForBackground(backgroundColor); |
60 | 68 | secondaryColor = getLowContrastColor(backgroundColor); |
61 | 69 | } |
@@ -78,8 +86,35 @@ public class IconPalette { | ||
78 | 86 | return result; |
79 | 87 | } |
80 | 88 | |
81 | - public static IconPalette fromDominantColor(int dominantColor) { | |
82 | - return new IconPalette(dominantColor); | |
89 | + public static IconPalette fromDominantColor(int dominantColor, boolean desaturateBackground) { | |
90 | + return new IconPalette(dominantColor, desaturateBackground); | |
91 | + } | |
92 | + | |
93 | + /** | |
94 | + * Returns an IconPalette based on the badge_color in colors.xml. | |
95 | + * If that color is Color.TRANSPARENT, then returns null instead. | |
96 | + */ | |
97 | + public static @Nullable IconPalette getBadgePalette(Resources resources) { | |
98 | + int badgeColor = resources.getColor(R.color.badge_color); | |
99 | + if (badgeColor == Color.TRANSPARENT) { | |
100 | + // Colors will be extracted per app icon, so a static palette won't work. | |
101 | + return null; | |
102 | + } | |
103 | + if (sBadgePalette == null) { | |
104 | + sBadgePalette = fromDominantColor(badgeColor, false); | |
105 | + } | |
106 | + return sBadgePalette; | |
107 | + } | |
108 | + | |
109 | + /** | |
110 | + * Returns an IconPalette based on the folder_badge_color in colors.xml. | |
111 | + */ | |
112 | + public static @NonNull IconPalette getFolderBadgePalette(Resources resources) { | |
113 | + if (sFolderBadgePalette == null) { | |
114 | + int badgeColor = resources.getColor(R.color.folder_badge_color); | |
115 | + sFolderBadgePalette = fromDominantColor(badgeColor, false); | |
116 | + } | |
117 | + return sFolderBadgePalette; | |
83 | 118 | } |
84 | 119 | |
85 | 120 | /** |
@@ -266,9 +266,10 @@ public class LauncherIcons { | ||
266 | 266 | |
267 | 267 | sOldBounds.set(icon.getBounds()); |
268 | 268 | if (Utilities.isAtLeastO() && icon instanceof AdaptiveIconDrawable) { |
269 | - int offset = Math.min(left, top); | |
269 | + int offset = Math.max((int)(ShadowGenerator.BLUR_FACTOR * iconBitmapSize), | |
270 | + Math.min(left, top)); | |
270 | 271 | int size = Math.max(width, height); |
271 | - icon.setBounds(offset, offset, offset + size, offset + size); | |
272 | + icon.setBounds(offset, offset, size, size); | |
272 | 273 | } else { |
273 | 274 | icon.setBounds(left, top, left+width, top+height); |
274 | 275 | } |
@@ -35,7 +35,7 @@ public class ShadowGenerator { | ||
35 | 35 | |
36 | 36 | // Percent of actual icon size |
37 | 37 | private static final float HALF_DISTANCE = 0.5f; |
38 | - private static final float BLUR_FACTOR = 0.5f/48; | |
38 | + public static final float BLUR_FACTOR = 0.5f/48; | |
39 | 39 | |
40 | 40 | // Percent of actual icon size |
41 | 41 | private static final float KEY_SHADOW_DISTANCE = 1f/48; |
@@ -47,7 +47,6 @@ import com.android.launcher3.AbstractFloatingView; | ||
47 | 47 | import com.android.launcher3.BubbleTextView; |
48 | 48 | import com.android.launcher3.DragSource; |
49 | 49 | import com.android.launcher3.DropTarget; |
50 | -import com.android.launcher3.FastBitmapDrawable; | |
51 | 50 | import com.android.launcher3.ItemInfo; |
52 | 51 | import com.android.launcher3.Launcher; |
53 | 52 | import com.android.launcher3.LauncherAnimUtils; |
@@ -579,9 +578,7 @@ public class PopupContainerWithArrow extends AbstractFloatingView implements Dra | ||
579 | 578 | ItemInfo itemInfo = (ItemInfo) mOriginalIcon.getTag(); |
580 | 579 | BadgeInfo badgeInfo = mLauncher.getPopupDataProvider().getBadgeInfoForItem(itemInfo); |
581 | 580 | if (mNotificationItemView != null && badgeInfo != null) { |
582 | - IconPalette palette = mOriginalIcon.getIcon() instanceof FastBitmapDrawable | |
583 | - ? ((FastBitmapDrawable) mOriginalIcon.getIcon()).getIconPalette() | |
584 | - : null; | |
581 | + IconPalette palette = mOriginalIcon.getBadgePalette(); | |
585 | 582 | mNotificationItemView.updateHeader(badgeInfo.getNotificationCount(), palette); |
586 | 583 | } |
587 | 584 | } |