Loading core/java/android/service/dreams/DreamManagerInternal.java +35 −0 Original line number Diff line number Diff line Loading @@ -58,4 +58,39 @@ public abstract class DreamManagerInternal { * @param isScreenOn True if the screen is currently on. */ public abstract boolean canStartDreaming(boolean isScreenOn); /** * Return whether dreams can continue when undocking by default. Even if the default is true, * it can be overridden temporarily, in which case {@link DreamManagerStateListener} will be * informed of any changes. */ public abstract boolean keepDreamingWhenUndockedDefault(); /** * Register a {@link DreamManagerStateListener}, which will be called when there are changes to * dream state. * * @param listener The listener to register. */ public abstract void registerDreamManagerStateListener(DreamManagerStateListener listener); /** * Unregister a {@link DreamManagerStateListener}, which will be called when there are changes * to dream state. * * @param listener The listener to unregister. */ public abstract void unregisterDreamManagerStateListener(DreamManagerStateListener listener); /** * Called when there are changes to dream state. */ public interface DreamManagerStateListener { /** * Called when keep dreaming when undocked has changed. * * @param keepDreaming True if the current dream should continue when undocking. */ void onKeepDreamingWhenUndockedChanged(boolean keepDreaming); } } services/core/java/com/android/server/dreams/DreamManagerService.java +36 −1 Original line number Diff line number Diff line Loading @@ -81,6 +81,7 @@ import java.lang.annotation.RetentionPolicy; import java.util.ArrayList; import java.util.List; import java.util.Objects; import java.util.concurrent.CopyOnWriteArrayList; /** * Service api for managing dreams. Loading Loading @@ -120,6 +121,10 @@ public final class DreamManagerService extends SystemService { private final boolean mDreamsEnabledByDefaultConfig; private final boolean mDreamsActivatedOnChargeByDefault; private final boolean mDreamsActivatedOnDockByDefault; private final boolean mKeepDreamingWhenUndockedDefault; private final CopyOnWriteArrayList<DreamManagerInternal.DreamManagerStateListener> mDreamManagerStateListeners = new CopyOnWriteArrayList<>(); @GuardedBy("mLock") private DreamRecord mCurrentDream; Loading Loading @@ -226,6 +231,8 @@ public final class DreamManagerService extends SystemService { mDreamsActivatedOnDockByDefault = mContext.getResources().getBoolean( com.android.internal.R.bool.config_dreamsActivatedOnDockByDefault); mSettingsObserver = new SettingsObserver(mHandler); mKeepDreamingWhenUndockedDefault = mContext.getResources().getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking); } @Override Loading Loading @@ -300,6 +307,7 @@ public final class DreamManagerService extends SystemService { pw.println("mIsDocked=" + mIsDocked); pw.println("mIsCharging=" + mIsCharging); pw.println("mWhenToDream=" + mWhenToDream); pw.println("mKeepDreamingWhenUndockedDefault=" + mKeepDreamingWhenUndockedDefault); pw.println("getDozeComponent()=" + getDozeComponent()); pw.println(); Loading Loading @@ -328,6 +336,15 @@ public final class DreamManagerService extends SystemService { } } private void reportKeepDreamingWhenUndockedChanged(boolean keepDreaming) { mHandler.post(() -> { for (DreamManagerInternal.DreamManagerStateListener listener : mDreamManagerStateListeners) { listener.onKeepDreamingWhenUndockedChanged(keepDreaming); } }); } /** Whether a real dream is occurring. */ private boolean isDreamingInternal() { synchronized (mLock) { Loading Loading @@ -571,6 +588,8 @@ public final class DreamManagerService extends SystemService { } mSystemDreamComponent = componentName; reportKeepDreamingWhenUndockedChanged( mKeepDreamingWhenUndockedDefault && mSystemDreamComponent == null); // Switch dream if currently dreaming and not dozing. if (isDreamingInternal() && !isDozingInternal()) { Loading Loading @@ -1012,6 +1031,22 @@ public final class DreamManagerService extends SystemService { public void requestDream() { requestDreamInternal(); } @Override public boolean keepDreamingWhenUndockedDefault() { // This value does not change, so a lock should not be needed. return mKeepDreamingWhenUndockedDefault; } @Override public void registerDreamManagerStateListener(DreamManagerStateListener listener) { mDreamManagerStateListeners.add(listener); } @Override public void unregisterDreamManagerStateListener(DreamManagerStateListener listener) { mDreamManagerStateListeners.remove(listener); } } private static final class DreamRecord { Loading services/core/java/com/android/server/power/PowerManagerService.java +21 −8 Original line number Diff line number Diff line Loading @@ -468,9 +468,6 @@ public final class PowerManagerService extends SystemService // True if the device should wake up when plugged or unplugged. private boolean mWakeUpWhenPluggedOrUnpluggedConfig; // True if the device should keep dreaming when undocked. private boolean mKeepDreamingWhenUndockingConfig; // True if the device should wake up when plugged or unplugged in theater mode. private boolean mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig; Loading Loading @@ -677,6 +674,19 @@ public final class PowerManagerService extends SystemService // but the DreamService has not yet been told to start (it's an async process). private boolean mDozeStartInProgress; // Whether to keep dreaming when the device is undocked. private boolean mKeepDreamingWhenUndocked; private final class DreamManagerStateListener implements DreamManagerInternal.DreamManagerStateListener { @Override public void onKeepDreamingWhenUndockedChanged(boolean keepDreaming) { synchronized (mLock) { mKeepDreamingWhenUndocked = keepDreaming; } } } private final class PowerGroupWakefulnessChangeListener implements PowerGroup.PowerGroupListener { @GuardedBy("mLock") Loading Loading @@ -1265,6 +1275,12 @@ public final class PowerManagerService extends SystemService new DisplayGroupPowerChangeListener(); mDisplayManagerInternal.registerDisplayGroupListener(displayGroupPowerChangeListener); // These DreamManager methods do not acquire locks, so they should be safe to call. mKeepDreamingWhenUndocked = mDreamManager.keepDreamingWhenUndockedDefault(); if (mKeepDreamingWhenUndocked) { mDreamManager.registerDreamManagerStateListener(new DreamManagerStateListener()); } mWirelessChargerDetector = mInjector.createWirelessChargerDetector(sensorManager, mInjector.createSuspendBlocker( this, "PowerManagerService.WirelessChargerDetector"), Loading Loading @@ -1382,8 +1398,6 @@ public final class PowerManagerService extends SystemService com.android.internal.R.bool.config_powerDecoupleInteractiveModeFromDisplay); mWakeUpWhenPluggedOrUnpluggedConfig = resources.getBoolean( com.android.internal.R.bool.config_unplugTurnsOnScreen); mKeepDreamingWhenUndockingConfig = resources.getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking); mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig = resources.getBoolean( com.android.internal.R.bool.config_allowTheaterModeWakeFromUnplug); mSuspendWhenScreenOffDueToProximityConfig = resources.getBoolean( Loading Loading @@ -2508,7 +2522,7 @@ public final class PowerManagerService extends SystemService } // Don't wake when undocking while dreaming if configured not to. if (mKeepDreamingWhenUndockingConfig if (mKeepDreamingWhenUndocked && getGlobalWakefulnessLocked() == WAKEFULNESS_DREAMING && wasPowered && !mIsPowered && oldPlugType == BatteryManager.BATTERY_PLUGGED_DOCK) { Loading Loading @@ -4457,8 +4471,7 @@ public final class PowerManagerService extends SystemService + mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig); pw.println(" mTheaterModeEnabled=" + mTheaterModeEnabled); pw.println(" mKeepDreamingWhenUndockingConfig=" + mKeepDreamingWhenUndockingConfig); pw.println(" mKeepDreamingWhenUndocked=" + mKeepDreamingWhenUndocked); pw.println(" mSuspendWhenScreenOffDueToProximityConfig=" + mSuspendWhenScreenOffDueToProximityConfig); pw.println(" mDreamsSupportedConfig=" + mDreamsSupportedConfig); Loading services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java +61 −5 Original line number Diff line number Diff line Loading @@ -619,17 +619,42 @@ public class PowerManagerServiceTest { } /** * Tests that dreaming continues when undocking and configured to do so. * Tests that dreaming stops when undocking and not configured to keep dreaming. */ @Test public void testWakefulnessDream_shouldKeepDreamingWhenUndocked() { public void testWakefulnessDream_shouldStopDreamingWhenUndocked_whenNotConfigured() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(false); createService(); startSystem(); when(mResourcesSpy.getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking)) when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); setPluggedIn(true); forceAwake(); // Needs to be awake first before it can dream. forceDream(); when(mBatteryManagerInternalMock.getPlugType()).thenReturn(0); setPluggedIn(false); assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_AWAKE); } /** * Tests that dreaming continues when undocking and configured to do so. */ @Test public void testWakefulnessDream_shouldKeepDreamingWhenUndocked_whenConfigured() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); mService.readConfigurationLocked(); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(true); createService(); startSystem(); when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); Loading @@ -643,6 +668,37 @@ public class PowerManagerServiceTest { assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_DREAMING); } /** * Tests that dreaming stops when undocking while showing a dream that prevents it. */ @Test public void testWakefulnessDream_shouldStopDreamingWhenUndocked_whenDreamPrevents() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(true); createService(); startSystem(); ArgumentCaptor<DreamManagerInternal.DreamManagerStateListener> dreamManagerStateListener = ArgumentCaptor.forClass(DreamManagerInternal.DreamManagerStateListener.class); verify(mDreamManagerInternalMock).registerDreamManagerStateListener( dreamManagerStateListener.capture()); when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); setPluggedIn(true); forceAwake(); // Needs to be awake first before it can dream. forceDream(); dreamManagerStateListener.getValue().onKeepDreamingWhenUndockedChanged(false); when(mBatteryManagerInternalMock.getPlugType()).thenReturn(0); setPluggedIn(false); assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_AWAKE); } @Test public void testWakefulnessDoze_goToSleep() { createService(); Loading Loading
core/java/android/service/dreams/DreamManagerInternal.java +35 −0 Original line number Diff line number Diff line Loading @@ -58,4 +58,39 @@ public abstract class DreamManagerInternal { * @param isScreenOn True if the screen is currently on. */ public abstract boolean canStartDreaming(boolean isScreenOn); /** * Return whether dreams can continue when undocking by default. Even if the default is true, * it can be overridden temporarily, in which case {@link DreamManagerStateListener} will be * informed of any changes. */ public abstract boolean keepDreamingWhenUndockedDefault(); /** * Register a {@link DreamManagerStateListener}, which will be called when there are changes to * dream state. * * @param listener The listener to register. */ public abstract void registerDreamManagerStateListener(DreamManagerStateListener listener); /** * Unregister a {@link DreamManagerStateListener}, which will be called when there are changes * to dream state. * * @param listener The listener to unregister. */ public abstract void unregisterDreamManagerStateListener(DreamManagerStateListener listener); /** * Called when there are changes to dream state. */ public interface DreamManagerStateListener { /** * Called when keep dreaming when undocked has changed. * * @param keepDreaming True if the current dream should continue when undocking. */ void onKeepDreamingWhenUndockedChanged(boolean keepDreaming); } }
services/core/java/com/android/server/dreams/DreamManagerService.java +36 −1 Original line number Diff line number Diff line Loading @@ -81,6 +81,7 @@ import java.lang.annotation.RetentionPolicy; import java.util.ArrayList; import java.util.List; import java.util.Objects; import java.util.concurrent.CopyOnWriteArrayList; /** * Service api for managing dreams. Loading Loading @@ -120,6 +121,10 @@ public final class DreamManagerService extends SystemService { private final boolean mDreamsEnabledByDefaultConfig; private final boolean mDreamsActivatedOnChargeByDefault; private final boolean mDreamsActivatedOnDockByDefault; private final boolean mKeepDreamingWhenUndockedDefault; private final CopyOnWriteArrayList<DreamManagerInternal.DreamManagerStateListener> mDreamManagerStateListeners = new CopyOnWriteArrayList<>(); @GuardedBy("mLock") private DreamRecord mCurrentDream; Loading Loading @@ -226,6 +231,8 @@ public final class DreamManagerService extends SystemService { mDreamsActivatedOnDockByDefault = mContext.getResources().getBoolean( com.android.internal.R.bool.config_dreamsActivatedOnDockByDefault); mSettingsObserver = new SettingsObserver(mHandler); mKeepDreamingWhenUndockedDefault = mContext.getResources().getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking); } @Override Loading Loading @@ -300,6 +307,7 @@ public final class DreamManagerService extends SystemService { pw.println("mIsDocked=" + mIsDocked); pw.println("mIsCharging=" + mIsCharging); pw.println("mWhenToDream=" + mWhenToDream); pw.println("mKeepDreamingWhenUndockedDefault=" + mKeepDreamingWhenUndockedDefault); pw.println("getDozeComponent()=" + getDozeComponent()); pw.println(); Loading Loading @@ -328,6 +336,15 @@ public final class DreamManagerService extends SystemService { } } private void reportKeepDreamingWhenUndockedChanged(boolean keepDreaming) { mHandler.post(() -> { for (DreamManagerInternal.DreamManagerStateListener listener : mDreamManagerStateListeners) { listener.onKeepDreamingWhenUndockedChanged(keepDreaming); } }); } /** Whether a real dream is occurring. */ private boolean isDreamingInternal() { synchronized (mLock) { Loading Loading @@ -571,6 +588,8 @@ public final class DreamManagerService extends SystemService { } mSystemDreamComponent = componentName; reportKeepDreamingWhenUndockedChanged( mKeepDreamingWhenUndockedDefault && mSystemDreamComponent == null); // Switch dream if currently dreaming and not dozing. if (isDreamingInternal() && !isDozingInternal()) { Loading Loading @@ -1012,6 +1031,22 @@ public final class DreamManagerService extends SystemService { public void requestDream() { requestDreamInternal(); } @Override public boolean keepDreamingWhenUndockedDefault() { // This value does not change, so a lock should not be needed. return mKeepDreamingWhenUndockedDefault; } @Override public void registerDreamManagerStateListener(DreamManagerStateListener listener) { mDreamManagerStateListeners.add(listener); } @Override public void unregisterDreamManagerStateListener(DreamManagerStateListener listener) { mDreamManagerStateListeners.remove(listener); } } private static final class DreamRecord { Loading
services/core/java/com/android/server/power/PowerManagerService.java +21 −8 Original line number Diff line number Diff line Loading @@ -468,9 +468,6 @@ public final class PowerManagerService extends SystemService // True if the device should wake up when plugged or unplugged. private boolean mWakeUpWhenPluggedOrUnpluggedConfig; // True if the device should keep dreaming when undocked. private boolean mKeepDreamingWhenUndockingConfig; // True if the device should wake up when plugged or unplugged in theater mode. private boolean mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig; Loading Loading @@ -677,6 +674,19 @@ public final class PowerManagerService extends SystemService // but the DreamService has not yet been told to start (it's an async process). private boolean mDozeStartInProgress; // Whether to keep dreaming when the device is undocked. private boolean mKeepDreamingWhenUndocked; private final class DreamManagerStateListener implements DreamManagerInternal.DreamManagerStateListener { @Override public void onKeepDreamingWhenUndockedChanged(boolean keepDreaming) { synchronized (mLock) { mKeepDreamingWhenUndocked = keepDreaming; } } } private final class PowerGroupWakefulnessChangeListener implements PowerGroup.PowerGroupListener { @GuardedBy("mLock") Loading Loading @@ -1265,6 +1275,12 @@ public final class PowerManagerService extends SystemService new DisplayGroupPowerChangeListener(); mDisplayManagerInternal.registerDisplayGroupListener(displayGroupPowerChangeListener); // These DreamManager methods do not acquire locks, so they should be safe to call. mKeepDreamingWhenUndocked = mDreamManager.keepDreamingWhenUndockedDefault(); if (mKeepDreamingWhenUndocked) { mDreamManager.registerDreamManagerStateListener(new DreamManagerStateListener()); } mWirelessChargerDetector = mInjector.createWirelessChargerDetector(sensorManager, mInjector.createSuspendBlocker( this, "PowerManagerService.WirelessChargerDetector"), Loading Loading @@ -1382,8 +1398,6 @@ public final class PowerManagerService extends SystemService com.android.internal.R.bool.config_powerDecoupleInteractiveModeFromDisplay); mWakeUpWhenPluggedOrUnpluggedConfig = resources.getBoolean( com.android.internal.R.bool.config_unplugTurnsOnScreen); mKeepDreamingWhenUndockingConfig = resources.getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking); mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig = resources.getBoolean( com.android.internal.R.bool.config_allowTheaterModeWakeFromUnplug); mSuspendWhenScreenOffDueToProximityConfig = resources.getBoolean( Loading Loading @@ -2508,7 +2522,7 @@ public final class PowerManagerService extends SystemService } // Don't wake when undocking while dreaming if configured not to. if (mKeepDreamingWhenUndockingConfig if (mKeepDreamingWhenUndocked && getGlobalWakefulnessLocked() == WAKEFULNESS_DREAMING && wasPowered && !mIsPowered && oldPlugType == BatteryManager.BATTERY_PLUGGED_DOCK) { Loading Loading @@ -4457,8 +4471,7 @@ public final class PowerManagerService extends SystemService + mWakeUpWhenPluggedOrUnpluggedInTheaterModeConfig); pw.println(" mTheaterModeEnabled=" + mTheaterModeEnabled); pw.println(" mKeepDreamingWhenUndockingConfig=" + mKeepDreamingWhenUndockingConfig); pw.println(" mKeepDreamingWhenUndocked=" + mKeepDreamingWhenUndocked); pw.println(" mSuspendWhenScreenOffDueToProximityConfig=" + mSuspendWhenScreenOffDueToProximityConfig); pw.println(" mDreamsSupportedConfig=" + mDreamsSupportedConfig); Loading
services/tests/servicestests/src/com/android/server/power/PowerManagerServiceTest.java +61 −5 Original line number Diff line number Diff line Loading @@ -619,17 +619,42 @@ public class PowerManagerServiceTest { } /** * Tests that dreaming continues when undocking and configured to do so. * Tests that dreaming stops when undocking and not configured to keep dreaming. */ @Test public void testWakefulnessDream_shouldKeepDreamingWhenUndocked() { public void testWakefulnessDream_shouldStopDreamingWhenUndocked_whenNotConfigured() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(false); createService(); startSystem(); when(mResourcesSpy.getBoolean( com.android.internal.R.bool.config_keepDreamingWhenUndocking)) when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); setPluggedIn(true); forceAwake(); // Needs to be awake first before it can dream. forceDream(); when(mBatteryManagerInternalMock.getPlugType()).thenReturn(0); setPluggedIn(false); assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_AWAKE); } /** * Tests that dreaming continues when undocking and configured to do so. */ @Test public void testWakefulnessDream_shouldKeepDreamingWhenUndocked_whenConfigured() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); mService.readConfigurationLocked(); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(true); createService(); startSystem(); when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); Loading @@ -643,6 +668,37 @@ public class PowerManagerServiceTest { assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_DREAMING); } /** * Tests that dreaming stops when undocking while showing a dream that prevents it. */ @Test public void testWakefulnessDream_shouldStopDreamingWhenUndocked_whenDreamPrevents() { // Make sure "unplug turns on screen" is configured to true. when(mResourcesSpy.getBoolean(com.android.internal.R.bool.config_unplugTurnsOnScreen)) .thenReturn(true); when(mDreamManagerInternalMock.keepDreamingWhenUndockedDefault()).thenReturn(true); createService(); startSystem(); ArgumentCaptor<DreamManagerInternal.DreamManagerStateListener> dreamManagerStateListener = ArgumentCaptor.forClass(DreamManagerInternal.DreamManagerStateListener.class); verify(mDreamManagerInternalMock).registerDreamManagerStateListener( dreamManagerStateListener.capture()); when(mBatteryManagerInternalMock.getPlugType()) .thenReturn(BatteryManager.BATTERY_PLUGGED_DOCK); setPluggedIn(true); forceAwake(); // Needs to be awake first before it can dream. forceDream(); dreamManagerStateListener.getValue().onKeepDreamingWhenUndockedChanged(false); when(mBatteryManagerInternalMock.getPlugType()).thenReturn(0); setPluggedIn(false); assertThat(mService.getGlobalWakefulnessLocked()).isEqualTo(WAKEFULNESS_AWAKE); } @Test public void testWakefulnessDoze_goToSleep() { createService(); Loading