Merge "Don't allow background apps to change theme" into sc-dev

This commit is contained in:
TreeHugger Robot
2021-12-21 23:23:06 +00:00
committed by Android (Google) Code Review
4 changed files with 63 additions and 5 deletions

View File

@@ -226,6 +226,14 @@ public class WallpaperManager {
*/ */
public static final String EXTRA_NEW_WALLPAPER_ID = "android.service.wallpaper.extra.ID"; public static final String EXTRA_NEW_WALLPAPER_ID = "android.service.wallpaper.extra.ID";
/**
* Extra passed on {@link Intent.ACTION_WALLPAPER_CHANGED} indicating if wallpaper was set from
* a foreground app.
* @hide
*/
public static final String EXTRA_FROM_FOREGROUND_APP =
"android.service.wallpaper.extra.FROM_FOREGROUND_APP";
// flags for which kind of wallpaper to act on // flags for which kind of wallpaper to act on
/** @hide */ /** @hide */

View File

@@ -253,8 +253,13 @@ public class ThemeOverlayController extends SystemUI implements Dumpable {
if (DEBUG) Log.d(TAG, "Updating overlays for user switch / profile added."); if (DEBUG) Log.d(TAG, "Updating overlays for user switch / profile added.");
reevaluateSystemTheme(true /* forceReload */); reevaluateSystemTheme(true /* forceReload */);
} else if (Intent.ACTION_WALLPAPER_CHANGED.equals(intent.getAction())) { } else if (Intent.ACTION_WALLPAPER_CHANGED.equals(intent.getAction())) {
mAcceptColorEvents = true; if (intent.getBooleanExtra(WallpaperManager.EXTRA_FROM_FOREGROUND_APP, false)) {
Log.i(TAG, "Allowing color events again"); mAcceptColorEvents = true;
Log.i(TAG, "Wallpaper changed, allowing color events again");
} else {
Log.i(TAG, "Wallpaper changed from background app, "
+ "keep deferring color events. Accepting: " + mAcceptColorEvents);
}
} }
} }
}; };

View File

@@ -152,7 +152,7 @@ public class ThemeOverlayControllerTest extends SysuiTestCase {
} }
@Test @Test
public void onWallpaperColorsChanged_setsTheme() { public void onWallpaperColorsChanged_setsTheme_whenForeground() {
// Should ask for a new theme when wallpaper colors change // Should ask for a new theme when wallpaper colors change
WallpaperColors mainColors = new WallpaperColors(Color.valueOf(Color.RED), WallpaperColors mainColors = new WallpaperColors(Color.valueOf(Color.RED),
Color.valueOf(Color.BLUE), null); Color.valueOf(Color.BLUE), null);
@@ -180,12 +180,42 @@ public class ThemeOverlayControllerTest extends SysuiTestCase {
// But should change theme after changing wallpapers // But should change theme after changing wallpapers
clearInvocations(mThemeOverlayApplier); clearInvocations(mThemeOverlayApplier);
mBroadcastReceiver.getValue().onReceive(null, new Intent(Intent.ACTION_WALLPAPER_CHANGED)); Intent intent = new Intent(Intent.ACTION_WALLPAPER_CHANGED);
intent.putExtra(WallpaperManager.EXTRA_FROM_FOREGROUND_APP, true);
mBroadcastReceiver.getValue().onReceive(null, intent);
mColorsListener.getValue().onColorsChanged(new WallpaperColors(Color.valueOf(Color.BLACK), mColorsListener.getValue().onColorsChanged(new WallpaperColors(Color.valueOf(Color.BLACK),
null, null), WallpaperManager.FLAG_SYSTEM); null, null), WallpaperManager.FLAG_SYSTEM);
verify(mThemeOverlayApplier).applyCurrentUserOverlays(any(), any(), anyInt(), any()); verify(mThemeOverlayApplier).applyCurrentUserOverlays(any(), any(), anyInt(), any());
} }
@Test
public void onWallpaperColorsChanged_setsTheme_skipWhenBackground() {
// Should ask for a new theme when wallpaper colors change
WallpaperColors mainColors = new WallpaperColors(Color.valueOf(Color.RED),
Color.valueOf(Color.BLUE), null);
mColorsListener.getValue().onColorsChanged(mainColors, WallpaperManager.FLAG_SYSTEM);
ArgumentCaptor<Map<String, OverlayIdentifier>> themeOverlays =
ArgumentCaptor.forClass(Map.class);
verify(mThemeOverlayApplier)
.applyCurrentUserOverlays(themeOverlays.capture(), any(), anyInt(), any());
// Assert that we received the colors that we were expecting
assertThat(themeOverlays.getValue().get(OVERLAY_CATEGORY_SYSTEM_PALETTE))
.isEqualTo(new OverlayIdentifier("ffff0000"));
assertThat(themeOverlays.getValue().get(OVERLAY_CATEGORY_ACCENT_COLOR))
.isEqualTo(new OverlayIdentifier("ffff0000"));
// Should not change theme after changing wallpapers, if intent doesn't have
// WallpaperManager.EXTRA_FROM_FOREGROUND_APP set to true.
clearInvocations(mThemeOverlayApplier);
mBroadcastReceiver.getValue().onReceive(null, new Intent(Intent.ACTION_WALLPAPER_CHANGED));
mColorsListener.getValue().onColorsChanged(new WallpaperColors(Color.valueOf(Color.BLACK),
null, null), WallpaperManager.FLAG_SYSTEM);
verify(mThemeOverlayApplier, never())
.applyCurrentUserOverlays(any(), any(), anyInt(), any());
}
@Test @Test
public void onWallpaperColorsChanged_preservesWallpaperPickerTheme() { public void onWallpaperColorsChanged_preservesWallpaperPickerTheme() {
// Should ask for a new theme when wallpaper colors change // Should ask for a new theme when wallpaper colors change
@@ -455,7 +485,9 @@ public class ThemeOverlayControllerTest extends SysuiTestCase {
// Regression test: null events should not reset the internal state and allow colors to be // Regression test: null events should not reset the internal state and allow colors to be
// applied again. // applied again.
clearInvocations(mThemeOverlayApplier); clearInvocations(mThemeOverlayApplier);
mBroadcastReceiver.getValue().onReceive(null, new Intent(Intent.ACTION_WALLPAPER_CHANGED)); Intent intent = new Intent(Intent.ACTION_WALLPAPER_CHANGED);
intent.putExtra(WallpaperManager.EXTRA_FROM_FOREGROUND_APP, true);
mBroadcastReceiver.getValue().onReceive(null, intent);
mColorsListener.getValue().onColorsChanged(null, WallpaperManager.FLAG_SYSTEM); mColorsListener.getValue().onColorsChanged(null, WallpaperManager.FLAG_SYSTEM);
verify(mThemeOverlayApplier, never()).applyCurrentUserOverlays(any(), any(), anyInt(), verify(mThemeOverlayApplier, never()).applyCurrentUserOverlays(any(), any(), anyInt(),
any()); any());

View File

@@ -16,6 +16,7 @@
package com.android.server.wallpaper; package com.android.server.wallpaper;
import static android.app.ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND;
import static android.app.WallpaperManager.COMMAND_REAPPLY; import static android.app.WallpaperManager.COMMAND_REAPPLY;
import static android.app.WallpaperManager.FLAG_LOCK; import static android.app.WallpaperManager.FLAG_LOCK;
import static android.app.WallpaperManager.FLAG_SYSTEM; import static android.app.WallpaperManager.FLAG_SYSTEM;
@@ -775,6 +776,7 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
private final Context mContext; private final Context mContext;
private final WindowManagerInternal mWindowManagerInternal; private final WindowManagerInternal mWindowManagerInternal;
private final IPackageManager mIPackageManager; private final IPackageManager mIPackageManager;
private final ActivityManager mActivityManager;
private final MyPackageMonitor mMonitor; private final MyPackageMonitor mMonitor;
private final AppOpsManager mAppOpsManager; private final AppOpsManager mAppOpsManager;
@@ -923,6 +925,11 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
*/ */
WallpaperColors primaryColors; WallpaperColors primaryColors;
/**
* If the wallpaper was set from a foreground app (instead of from a background service).
*/
public boolean fromForegroundApp;
WallpaperConnection connection; WallpaperConnection connection;
long lastDiedTime; long lastDiedTime;
boolean wallpaperUpdating; boolean wallpaperUpdating;
@@ -1672,6 +1679,7 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
mAppOpsManager = (AppOpsManager) mContext.getSystemService(Context.APP_OPS_SERVICE); mAppOpsManager = (AppOpsManager) mContext.getSystemService(Context.APP_OPS_SERVICE);
mDisplayManager = mContext.getSystemService(DisplayManager.class); mDisplayManager = mContext.getSystemService(DisplayManager.class);
mDisplayManager.registerDisplayListener(mDisplayListener, null /* handler */); mDisplayManager.registerDisplayListener(mDisplayListener, null /* handler */);
mActivityManager = mContext.getSystemService(ActivityManager.class);
mMonitor = new MyPackageMonitor(); mMonitor = new MyPackageMonitor();
mColorsChangedListeners = new SparseArray<>(); mColorsChangedListeners = new SparseArray<>();
@@ -2613,6 +2621,9 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
} }
} }
final boolean fromForegroundApp = Binder.withCleanCallingIdentity(() ->
mActivityManager.getPackageImportance(callingPackage) == IMPORTANCE_FOREGROUND);
synchronized (mLock) { synchronized (mLock) {
if (DEBUG) Slog.v(TAG, "setWallpaper which=0x" + Integer.toHexString(which)); if (DEBUG) Slog.v(TAG, "setWallpaper which=0x" + Integer.toHexString(which));
WallpaperData wallpaper; WallpaperData wallpaper;
@@ -2635,6 +2646,7 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
wallpaper.imageWallpaperPending = true; wallpaper.imageWallpaperPending = true;
wallpaper.whichPending = which; wallpaper.whichPending = which;
wallpaper.setComplete = completion; wallpaper.setComplete = completion;
wallpaper.fromForegroundApp = fromForegroundApp;
wallpaper.cropHint.set(cropHint); wallpaper.cropHint.set(cropHint);
wallpaper.allowBackup = allowBackup; wallpaper.allowBackup = allowBackup;
} }
@@ -3017,6 +3029,7 @@ public class WallpaperManagerService extends IWallpaperManager.Stub
wallpaper.callbacks.finishBroadcast(); wallpaper.callbacks.finishBroadcast();
final Intent intent = new Intent(Intent.ACTION_WALLPAPER_CHANGED); final Intent intent = new Intent(Intent.ACTION_WALLPAPER_CHANGED);
intent.putExtra(WallpaperManager.EXTRA_FROM_FOREGROUND_APP, wallpaper.fromForegroundApp);
mContext.sendBroadcastAsUser(intent, new UserHandle(mCurrentUserId)); mContext.sendBroadcastAsUser(intent, new UserHandle(mCurrentUserId));
} }