diff --git a/core/java/android/app/Notification.java b/core/java/android/app/Notification.java index 420ec0846fda..42aa3347021a 100644 --- a/core/java/android/app/Notification.java +++ b/core/java/android/app/Notification.java @@ -3701,7 +3701,6 @@ public class Notification implements Parcelable private boolean mRebuildStyledRemoteViews; private boolean mTintActionButtons; - private boolean mTintWithThemeAccent; private boolean mInNightMode; /** @@ -3737,7 +3736,6 @@ public class Notification implements Parcelable mContext = context; Resources res = mContext.getResources(); mTintActionButtons = res.getBoolean(R.bool.config_tintNotificationActionButtons); - mTintWithThemeAccent = res.getBoolean(R.bool.config_tintNotificationsWithTheme); if (res.getBoolean(R.bool.config_enableNightMode)) { Configuration currentConfig = res.getConfiguration(); @@ -5132,15 +5130,21 @@ public class Notification implements Parcelable || mSecondaryTextColor == COLOR_INVALID || mTextColorsAreForBackground != backgroundColor) { mTextColorsAreForBackground = backgroundColor; - mPrimaryTextColor = ContrastColorUtil.resolvePrimaryColor(mContext, + int defaultPrimaryTextColor = ContrastColorUtil.resolvePrimaryColor(mContext, backgroundColor, mInNightMode); - mSecondaryTextColor = ContrastColorUtil.resolveSecondaryColor(mContext, + int defaultSecondaryTextColor = ContrastColorUtil.resolveSecondaryColor(mContext, backgroundColor, mInNightMode); - if (backgroundColor != COLOR_DEFAULT && isColorized(p)) { + boolean colorized = backgroundColor != COLOR_DEFAULT; + if (colorized) { mPrimaryTextColor = ContrastColorUtil.findAlphaToMeetContrast( - mPrimaryTextColor, backgroundColor, 4.5); + defaultPrimaryTextColor, backgroundColor, 4.5); mSecondaryTextColor = ContrastColorUtil.findAlphaToMeetContrast( - mSecondaryTextColor, backgroundColor, 4.5); + defaultSecondaryTextColor, backgroundColor, 4.5); + } else { + mPrimaryTextColor = obtainThemeColor(R.attr.textColorPrimary, + defaultPrimaryTextColor); + mSecondaryTextColor = obtainThemeColor(R.attr.textColorSecondary, + defaultSecondaryTextColor); } } } @@ -5167,11 +5171,9 @@ public class Notification implements Parcelable contentView.setProgressBar(R.id.progress, max, progress, ind); contentView.setProgressBackgroundTintList(R.id.progress, mContext.getColorStateList(R.color.notification_progress_background_color)); - if (mTintWithThemeAccent || getRawColor(p) != COLOR_DEFAULT) { - ColorStateList progressTint = ColorStateList.valueOf(getAccentColor(p)); - contentView.setProgressTintList(R.id.progress, progressTint); - contentView.setProgressIndeterminateTintList(R.id.progress, progressTint); - } + ColorStateList progressTint = ColorStateList.valueOf(getAccentColor(p)); + contentView.setProgressTintList(R.id.progress, progressTint); + contentView.setProgressIndeterminateTintList(R.id.progress, progressTint); return true; } else { contentView.setViewVisibility(R.id.progress, View.GONE); @@ -6002,8 +6004,7 @@ public class Notification implements Parcelable background = outResultColor[0].getDefaultColor(); textColor = ContrastColorUtil.resolvePrimaryColor(mContext, background, mInNightMode); - } else if (mTintActionButtons && !mInNightMode - && getRawColor(p) != COLOR_DEFAULT && !isColorized(p)) { + } else if (mTintActionButtons && !mInNightMode && !isColorized(p)) { textColor = getAccentColor(p); } else { textColor = getPrimaryTextColor(p); @@ -6181,7 +6182,7 @@ public class Notification implements Parcelable * is the primary text color, otherwise it's the contrast-adjusted app-provided color. */ private @ColorInt int getSmallIconColor(StandardTemplateParams p) { - return isColorized(p) ? getPrimaryTextColor(p) : getContrastColor(p); + return getContrastColor(p); } /** @@ -6193,11 +6194,9 @@ public class Notification implements Parcelable if (isColorized(p)) { return getPrimaryTextColor(p); } - if (mTintWithThemeAccent) { - int color = obtainThemeColor(R.attr.colorAccent, COLOR_INVALID); - if (color != COLOR_INVALID) { - return color; - } + int color = obtainThemeColor(R.attr.colorAccent, COLOR_INVALID); + if (color != COLOR_INVALID) { + return color; } return getContrastColor(p); } @@ -6207,7 +6206,7 @@ public class Notification implements Parcelable * color when colorized, or when not using theme color tints. */ private @ColorInt int getProtectionColor(StandardTemplateParams p) { - if (mTintWithThemeAccent && !isColorized(p)) { + if (!isColorized(p)) { int color = obtainThemeColor(R.attr.colorBackgroundFloating, COLOR_INVALID); if (color != COLOR_INVALID) { return color; @@ -6226,12 +6225,10 @@ public class Notification implements Parcelable if (isColorized(p)) { return getPrimaryTextColor(p); } - if (mTintWithThemeAccent) { - int color = obtainThemeColor(com.android.internal.R.attr.colorAccentTertiary, - COLOR_INVALID); - if (color != COLOR_INVALID) { - return color; - } + int color = obtainThemeColor(com.android.internal.R.attr.colorAccentTertiary, + COLOR_INVALID); + if (color != COLOR_INVALID) { + return color; } return getContrastColor(p); } @@ -6261,6 +6258,9 @@ public class Notification implements Parcelable * Gets the contrast-adjusted version of the color provided by the app. */ private @ColorInt int getContrastColor(StandardTemplateParams p) { + if (isColorized(p)) { + return getPrimaryTextColor(p); + } int rawColor = getRawColor(p); if (mCachedContrastColorIsFor == rawColor && mCachedContrastColor != COLOR_INVALID) { return mCachedContrastColor; @@ -6271,9 +6271,10 @@ public class Notification implements Parcelable int background = getDefaultBackgroundColor(); if (rawColor == COLOR_DEFAULT) { ensureColors(p); - color = ContrastColorUtil.resolveDefaultColor(mContext, background, mInNightMode); - if (mTintWithThemeAccent) { - color = obtainThemeColor(R.attr.colorAccent, color); + color = obtainThemeColor(R.attr.colorAccent, COLOR_INVALID); + if (color == COLOR_INVALID) { + color = ContrastColorUtil.resolveDefaultColor(mContext, background, + mInNightMode); } } else { color = ContrastColorUtil.resolveContrastColor(mContext, rawColor, @@ -6294,11 +6295,6 @@ public class Notification implements Parcelable * @param p the template params to inflate this with */ private @ColorInt int getRawColor(StandardTemplateParams p) { - // When notifications are theme-tinted, the raw color is only used for the icon, so go - // ahead and keep that color instead of changing the color for minimized notifs. - if (p.mReduceHighlights && !mTintWithThemeAccent) { - return COLOR_DEFAULT; - } return mN.color; } @@ -6405,6 +6401,7 @@ public class Notification implements Parcelable + " notification: " + mN.mShortcutId + " vs bubble: " + mN.mBubbleMetadata.getShortcutId()); } + validateColorizedHasColor(); // first, add any extras from the calling code if (mUserExtras != null) { @@ -6458,6 +6455,21 @@ public class Notification implements Parcelable return mN; } + // This code is executed on behalf of other apps' notifications, sometimes even by 3p apps, + // a use case that is not supported by the Compat Framework library. + @SuppressWarnings("AndroidFrameworkCompatChange") + private void validateColorizedHasColor() { + if (mN.color == COLOR_DEFAULT && mN.extras.getBoolean(EXTRA_COLORIZED)) { + if (mContext.getApplicationInfo().targetSdkVersion >= Build.VERSION_CODES.S) { + throw new IllegalArgumentException( + "Colorized notifications must set a color (other than COLOR_DEFAULT)."); + } else { + Log.w(TAG, "Colorized notifications must set a color (other than " + + "COLOR_DEFAULT). This is required for apps targeting S."); + } + } + } + /** * Returns the color for the given Theme.DeviceDefault.DayNight attribute, or * defValue if that could not be completed @@ -6470,13 +6482,9 @@ public class Notification implements Parcelable } theme = new ContextThemeWrapper(mContext, R.style.Theme_DeviceDefault_DayNight) .getTheme(); - TypedArray ta = theme.obtainStyledAttributes(new int[]{attrRes}); - if (ta == null) { - return defaultColor; + try (TypedArray ta = theme.obtainStyledAttributes(new int[]{attrRes})) { + return ta.getColor(0, defaultColor); } - int background = ta.getColor(0, defaultColor); - ta.recycle(); - return background; } /** @@ -6590,11 +6598,7 @@ public class Notification implements Parcelable * which must be resolved by the caller before being used. */ private @ColorInt int getUnresolvedBackgroundColor(StandardTemplateParams p) { - if (isColorized(p)) { - return getRawColor(p); - } else { - return COLOR_DEFAULT; - } + return isColorized(p) ? getRawColor(p) : COLOR_DEFAULT; } /** @@ -6768,7 +6772,7 @@ public class Notification implements Parcelable * @hide */ public boolean isColorized() { - return extras.getBoolean(EXTRA_COLORIZED) + return color != COLOR_DEFAULT && extras.getBoolean(EXTRA_COLORIZED) && (hasColorizedPermission() || isForegroundService()); } diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml index b6c22bb68086..e69c4be1fb71 100644 --- a/core/res/res/values/config.xml +++ b/core/res/res/values/config.xml @@ -3943,10 +3943,6 @@ color supplied by the Notification.Builder if present. --> true - - true - false diff --git a/core/res/res/values/symbols.xml b/core/res/res/values/symbols.xml index b924ecd3f301..16a6d841ce8d 100644 --- a/core/res/res/values/symbols.xml +++ b/core/res/res/values/symbols.xml @@ -1890,7 +1890,6 @@ - diff --git a/core/tests/coretests/src/android/app/NotificationTest.java b/core/tests/coretests/src/android/app/NotificationTest.java index 0ea63643d24e..0f8c9e2de826 100644 --- a/core/tests/coretests/src/android/app/NotificationTest.java +++ b/core/tests/coretests/src/android/app/NotificationTest.java @@ -28,6 +28,7 @@ import android.content.Context; import android.content.Intent; import android.content.LocusId; import android.graphics.BitmapFactory; +import android.graphics.Color; import android.graphics.drawable.Icon; import android.media.session.MediaSession; import android.os.Build; @@ -60,7 +61,7 @@ public class NotificationTest { public void testColorizedByPermission() { Notification n = new Notification.Builder(mContext, "test") .setFlag(Notification.FLAG_CAN_COLORIZE, true) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .build(); assertTrue(n.isColorized()); @@ -71,7 +72,7 @@ public class NotificationTest { n = new Notification.Builder(mContext, "test") .setFlag(Notification.FLAG_CAN_COLORIZE, false) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .build(); assertFalse(n.isColorized()); } @@ -80,7 +81,7 @@ public class NotificationTest { public void testColorizedByForeground() { Notification n = new Notification.Builder(mContext, "test") .setFlag(Notification.FLAG_FOREGROUND_SERVICE, true) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .build(); assertTrue(n.isColorized()); @@ -91,7 +92,7 @@ public class NotificationTest { n = new Notification.Builder(mContext, "test") .setFlag(Notification.FLAG_FOREGROUND_SERVICE, false) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .build(); assertFalse(n.isColorized()); } diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationChildrenContainer.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationChildrenContainer.java index 1d307364d661..5f3933b827c4 100644 --- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationChildrenContainer.java +++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/NotificationChildrenContainer.java @@ -105,7 +105,6 @@ public class NotificationChildrenContainer extends ViewGroup { private ViewGroup mCurrentHeader; private boolean mIsConversation; - private boolean mTintWithThemeAccent; private boolean mShowGroupCountInExpander; private boolean mShowDividersWhenExpanded; private boolean mHideDividersDuringExpand; @@ -149,8 +148,6 @@ public class NotificationChildrenContainer extends ViewGroup { com.android.internal.R.dimen.notification_content_margin); mEnableShadowOnChildNotifications = res.getBoolean(R.bool.config_enableShadowOnChildNotifications); - mTintWithThemeAccent = - res.getBoolean(com.android.internal.R.bool.config_tintNotificationsWithTheme); mShowGroupCountInExpander = res.getBoolean(R.bool.config_showNotificationGroupCountInExpander); mShowDividersWhenExpanded = @@ -1223,14 +1220,11 @@ public class NotificationChildrenContainer extends ViewGroup { return; } int color = mContainingNotification.getNotificationColor(); - if (mTintWithThemeAccent) { - // We're using the theme accent, color with the accent color instead of the notif color - Resources.Theme theme = new ContextThemeWrapper(mContext, - com.android.internal.R.style.Theme_DeviceDefault_DayNight).getTheme(); - TypedArray ta = theme.obtainStyledAttributes( - new int[]{com.android.internal.R.attr.colorAccent}); + Resources.Theme theme = new ContextThemeWrapper(mContext, + com.android.internal.R.style.Theme_DeviceDefault_DayNight).getTheme(); + try (TypedArray ta = theme.obtainStyledAttributes( + new int[]{com.android.internal.R.attr.colorAccent})) { color = ta.getColor(0, color); - ta.recycle(); } mHybridGroupManager.setOverflowNumberColor(mOverflowNumber, color); } diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/AppOpsCoordinatorTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/AppOpsCoordinatorTest.java index 278456859735..f2e7081e096b 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/AppOpsCoordinatorTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/collection/coordinator/AppOpsCoordinatorTest.java @@ -28,8 +28,7 @@ import static org.mockito.Mockito.times; import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; -import android.app.Notification; -import android.os.Bundle; +import android.graphics.Color; import android.os.UserHandle; import android.service.notification.StatusBarNotification; import android.testing.AndroidTestingRunner; @@ -120,7 +119,8 @@ public class AppOpsCoordinatorTest extends SysuiTestCase { mEntryBuilder .setFlag(mContext, FLAG_FOREGROUND_SERVICE, true) .setImportance(IMPORTANCE_DEFAULT) - .modifyNotification(mContext).setColorized(true); + .modifyNotification(mContext) + .setColorized(true).setColor(Color.WHITE); // THEN the entry is in the fgs section assertTrue(mFgsSection.isInSection(mEntryBuilder.build())); @@ -132,7 +132,8 @@ public class AppOpsCoordinatorTest extends SysuiTestCase { mEntryBuilder .setFlag(mContext, FLAG_FOREGROUND_SERVICE, true) .setImportance(IMPORTANCE_MIN) - .modifyNotification(mContext).setColorized(true); + .modifyNotification(mContext) + .setColorized(true).setColor(Color.WHITE); // THEN the entry is NOT in the fgs section assertFalse(mFgsSection.isInSection(mEntryBuilder.build())); diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java index 18481bca1aa6..bfce2a568c78 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java @@ -51,6 +51,7 @@ import android.content.Intent; import android.content.pm.LauncherApps; import android.content.pm.PackageManager; import android.content.pm.ShortcutManager; +import android.graphics.Color; import android.os.Binder; import android.os.Handler; import android.provider.Settings; @@ -486,7 +487,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase { Notification.Builder nb = new Notification.Builder(mContext, mTestNotificationChannel.getId()) .setContentTitle("foo") - .setColorized(true) + .setColorized(true).setColor(Color.RED) .setFlag(Notification.FLAG_CAN_COLORIZE, true) .setSmallIcon(android.R.drawable.sym_def_app_icon); diff --git a/services/tests/uiservicestests/src/com/android/server/notification/NotificationComparatorTest.java b/services/tests/uiservicestests/src/com/android/server/notification/NotificationComparatorTest.java index a37d5c8a956a..9433bf28e237 100644 --- a/services/tests/uiservicestests/src/com/android/server/notification/NotificationComparatorTest.java +++ b/services/tests/uiservicestests/src/com/android/server/notification/NotificationComparatorTest.java @@ -31,6 +31,7 @@ import android.app.NotificationManager; import android.content.Context; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; +import android.graphics.Color; import android.os.Build; import android.os.UserHandle; import android.provider.Settings; @@ -193,7 +194,7 @@ public class NotificationComparatorTest extends UiServiceTestCase { Notification n11 = new Notification.Builder(mContext, TEST_CHANNEL_ID) .setCategory(Notification.CATEGORY_MESSAGE) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .build(); mRecordCheaterColorized = new NotificationRecord(mContext, new StatusBarNotification(pkg2, pkg2, 1, "cheater", uid2, uid2, n11, new UserHandle(userId), @@ -202,7 +203,7 @@ public class NotificationComparatorTest extends UiServiceTestCase { Notification n12 = new Notification.Builder(mContext, TEST_CHANNEL_ID) .setCategory(Notification.CATEGORY_MESSAGE) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .setStyle(new Notification.MediaStyle()) .build(); mNoMediaSessionMedia = new NotificationRecord(mContext, new StatusBarNotification( @@ -212,7 +213,7 @@ public class NotificationComparatorTest extends UiServiceTestCase { Notification n13 = new Notification.Builder(mContext, TEST_CHANNEL_ID) .setFlag(Notification.FLAG_FOREGROUND_SERVICE, true) - .setColorized(true /* colorized */) + .setColorized(true).setColor(Color.WHITE) .build(); mRecordColorized = new NotificationRecord(mContext, new StatusBarNotification(pkg2, pkg2, 1, "colorized", uid2, uid2, n13, @@ -221,7 +222,7 @@ public class NotificationComparatorTest extends UiServiceTestCase { Notification n14 = new Notification.Builder(mContext, TEST_CHANNEL_ID) .setCategory(Notification.CATEGORY_CALL) - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .setFlag(Notification.FLAG_FOREGROUND_SERVICE, true) .build(); mRecordColorizedCall = new NotificationRecord(mContext, new StatusBarNotification(callPkg, diff --git a/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java b/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java index 55ebe11e4ca8..6e2219b14376 100755 --- a/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java +++ b/services/tests/uiservicestests/src/com/android/server/notification/NotificationManagerServiceTest.java @@ -3284,7 +3284,7 @@ public class NotificationManagerServiceTest extends UiServiceTestCase { Notification.Builder nb = new Notification.Builder(mContext, mTestNotificationChannel.getId()) .setContentTitle("foo") - .setColorized(true) + .setColorized(true).setColor(Color.WHITE) .setFlag(Notification.FLAG_CAN_COLORIZE, true) .setSmallIcon(android.R.drawable.sym_def_app_icon); StatusBarNotification sbn = new StatusBarNotification(PKG, PKG, 1, diff --git a/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java b/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java index 429e676155f8..ef324e7c1377 100644 --- a/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java +++ b/tests/StatusBar/src/com/android/statusbartest/NotificationTestList.java @@ -25,27 +25,22 @@ import android.app.Notification; import android.app.NotificationChannel; import android.app.NotificationManager; import android.app.PendingIntent; -import android.content.Context; import android.content.ContentResolver; +import android.content.Context; import android.content.Intent; import android.graphics.Bitmap; -import android.graphics.BitmapFactory; import android.graphics.Color; import android.graphics.drawable.BitmapDrawable; import android.graphics.drawable.Icon; import android.media.AudioAttributes; -import android.os.Bundle; -import android.os.Vibrator; -import android.os.Handler; -import android.os.UserHandle; -import android.util.Log; import android.net.Uri; -import android.os.SystemClock; -import android.widget.RemoteViews; +import android.os.Bundle; +import android.os.Handler; import android.os.PowerManager; - -// private NM API -import android.app.INotificationManager; +import android.os.SystemClock; +import android.os.Vibrator; +import android.util.Log; +import android.widget.RemoteViews; import android.widget.Toast; public class NotificationTestList extends TestActivity @@ -185,6 +180,7 @@ public class NotificationTestList extends TestActivity .setContentTitle("default priority group 1") .setGroup("group1") .setOngoing(true) + .setColor(Color.WHITE) .setColorized(true) .build(); mNM.notify(6002, n);