From 4c5add5c98fe7c3e33cd3bfe0160f1c38041010f Mon Sep 17 00:00:00 2001 From: Darrell Shi Date: Fri, 11 Nov 2022 15:11:51 +0000 Subject: [PATCH] Check home controls availability on overlay active. The callback that home controls observes is only triggered when the controls services update, which is one of the conditions for whether home controls is available. When the user adds the first or removes the last device control, the hasFavorites condition changes but does not trigger an update. So to address that, home controls should check availability when the dream overlay becomes active, parallel to which on the lock screen. Test: DreamHomeControlsComplicationTest Test: reboot device with no favorited device controls > add favorite device controls > start dreaming > see home controls chip Test: similar to above but start with favorites and remove last Bug: 257348199 Fix: 257348199 Change-Id: I537a240963e0523c8fc40008dee961c7a434094a --- .../DreamHomeControlsComplication.java | 49 ++++++++++++++----- .../DreamHomeControlsComplicationTest.java | 35 ++++++++++++- 2 files changed, 70 insertions(+), 14 deletions(-) diff --git a/packages/SystemUI/src/com/android/systemui/dreams/complication/DreamHomeControlsComplication.java b/packages/SystemUI/src/com/android/systemui/dreams/complication/DreamHomeControlsComplication.java index cedd850ac2eff..c01cf43eae74a 100644 --- a/packages/SystemUI/src/com/android/systemui/dreams/complication/DreamHomeControlsComplication.java +++ b/packages/SystemUI/src/com/android/systemui/dreams/complication/DreamHomeControlsComplication.java @@ -33,6 +33,7 @@ import com.android.internal.logging.UiEvent; import com.android.internal.logging.UiEventLogger; import com.android.systemui.CoreStartable; import com.android.systemui.animation.ActivityLaunchAnimator; +import com.android.systemui.controls.ControlsServiceInfo; import com.android.systemui.controls.dagger.ControlsComponent; import com.android.systemui.controls.management.ControlsListingController; import com.android.systemui.controls.ui.ControlsActivity; @@ -42,6 +43,8 @@ import com.android.systemui.dreams.complication.dagger.DreamHomeControlsComplica import com.android.systemui.plugins.ActivityStarter; import com.android.systemui.util.ViewController; +import java.util.List; + import javax.inject.Inject; import javax.inject.Named; @@ -76,16 +79,25 @@ public class DreamHomeControlsComplication implements Complication { private final DreamOverlayStateController mDreamOverlayStateController; private final ControlsComponent mControlsComponent; - private boolean mControlServicesAvailable = false; + private boolean mOverlayActive = false; // Callback for when the home controls service availability changes. private final ControlsListingController.ControlsListingCallback mControlsCallback = - serviceInfos -> { - boolean available = !serviceInfos.isEmpty(); + services -> updateHomeControlsComplication(); - if (available != mControlServicesAvailable) { - mControlServicesAvailable = available; - updateComplicationAvailability(); + private final DreamOverlayStateController.Callback mOverlayStateCallback = + new DreamOverlayStateController.Callback() { + @Override + public void onStateChanged() { + if (mOverlayActive == mDreamOverlayStateController.isOverlayActive()) { + return; + } + + mOverlayActive = !mOverlayActive; + + if (mOverlayActive) { + updateHomeControlsComplication(); + } } }; @@ -102,18 +114,29 @@ public class DreamHomeControlsComplication implements Complication { public void start() { mControlsComponent.getControlsListingController().ifPresent( c -> c.addCallback(mControlsCallback)); + mDreamOverlayStateController.addCallback(mOverlayStateCallback); } - private void updateComplicationAvailability() { + private void updateHomeControlsComplication() { + mControlsComponent.getControlsListingController().ifPresent(c -> { + if (isHomeControlsAvailable(c.getCurrentServices())) { + mDreamOverlayStateController.addComplication(mComplication); + } else { + mDreamOverlayStateController.removeComplication(mComplication); + } + }); + } + + private boolean isHomeControlsAvailable(List controlsServices) { + if (controlsServices.isEmpty()) { + return false; + } + final boolean hasFavorites = mControlsComponent.getControlsController() .map(c -> !c.getFavorites().isEmpty()) .orElse(false); - if (!hasFavorites || !mControlServicesAvailable - || mControlsComponent.getVisibility() == UNAVAILABLE) { - mDreamOverlayStateController.removeComplication(mComplication); - } else { - mDreamOverlayStateController.addComplication(mComplication); - } + final ControlsComponent.Visibility visibility = mControlsComponent.getVisibility(); + return hasFavorites && visibility != UNAVAILABLE; } } diff --git a/packages/SystemUI/tests/src/com/android/systemui/dreams/complication/DreamHomeControlsComplicationTest.java b/packages/SystemUI/tests/src/com/android/systemui/dreams/complication/DreamHomeControlsComplicationTest.java index aa8c93edce68a..30ad485d7ac3b 100644 --- a/packages/SystemUI/tests/src/com/android/systemui/dreams/complication/DreamHomeControlsComplicationTest.java +++ b/packages/SystemUI/tests/src/com/android/systemui/dreams/complication/DreamHomeControlsComplicationTest.java @@ -90,7 +90,10 @@ public class DreamHomeControlsComplicationTest extends SysuiTestCase { private ActivityStarter mActivityStarter; @Mock - UiEventLogger mUiEventLogger; + private UiEventLogger mUiEventLogger; + + @Captor + private ArgumentCaptor mStateCallbackCaptor; @Before public void setup() { @@ -164,6 +167,29 @@ public class DreamHomeControlsComplicationTest extends SysuiTestCase { verify(mDreamOverlayStateController).addComplication(mComplication); } + @Test + public void complicationAvailability_checkAvailabilityWhenDreamOverlayBecomesActive() { + final DreamHomeControlsComplication.Registrant registrant = + new DreamHomeControlsComplication.Registrant(mComplication, + mDreamOverlayStateController, mControlsComponent); + registrant.start(); + + setServiceAvailable(true); + setHaveFavorites(false); + + // Complication not available on start. + verify(mDreamOverlayStateController, never()).addComplication(mComplication); + + // Favorite controls added, complication should be available now. + setHaveFavorites(true); + + // Dream overlay becomes active. + setDreamOverlayActive(true); + + // Verify complication is added. + verify(mDreamOverlayStateController).addComplication(mComplication); + } + /** * Ensures clicking home controls chip logs UiEvent. */ @@ -196,10 +222,17 @@ public class DreamHomeControlsComplicationTest extends SysuiTestCase { private void setServiceAvailable(boolean value) { final List serviceInfos = mock(List.class); + when(mControlsListingController.getCurrentServices()).thenReturn(serviceInfos); when(serviceInfos.isEmpty()).thenReturn(!value); triggerControlsListingCallback(serviceInfos); } + private void setDreamOverlayActive(boolean value) { + when(mDreamOverlayStateController.isOverlayActive()).thenReturn(value); + verify(mDreamOverlayStateController).addCallback(mStateCallbackCaptor.capture()); + mStateCallbackCaptor.getValue().onStateChanged(); + } + private void triggerControlsListingCallback(List serviceInfos) { verify(mControlsListingController).addCallback(mCallbackCaptor.capture()); mCallbackCaptor.getValue().onServicesUpdated(serviceInfos);