Merge "Do not allow complications when dream overlay is not enabled." into tm-qpr-dev
This commit is contained in:
@@ -16,6 +16,8 @@
|
||||
|
||||
package com.android.systemui.dreams;
|
||||
|
||||
import static com.android.systemui.dreams.dagger.DreamModule.DREAM_OVERLAY_SERVICE_COMPONENT;
|
||||
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.ComponentName;
|
||||
import android.content.Context;
|
||||
@@ -35,6 +37,7 @@ import com.android.systemui.CoreStartable;
|
||||
import com.android.systemui.dagger.qualifiers.Main;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
/**
|
||||
* {@link DreamOverlayRegistrant} is responsible for telling system server that SystemUI should be
|
||||
@@ -98,12 +101,13 @@ public class DreamOverlayRegistrant implements CoreStartable {
|
||||
}
|
||||
|
||||
@Inject
|
||||
public DreamOverlayRegistrant(Context context, @Main Resources resources) {
|
||||
public DreamOverlayRegistrant(Context context, @Main Resources resources,
|
||||
@Named(DREAM_OVERLAY_SERVICE_COMPONENT) ComponentName dreamOverlayServiceComponent) {
|
||||
mContext = context;
|
||||
mResources = resources;
|
||||
mDreamManager = IDreamManager.Stub.asInterface(
|
||||
ServiceManager.getService(DreamService.DREAM_SERVICE));
|
||||
mOverlayServiceComponent = new ComponentName(mContext, DreamOverlayService.class);
|
||||
mOverlayServiceComponent = dreamOverlayServiceComponent;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -16,6 +16,8 @@
|
||||
|
||||
package com.android.systemui.dreams;
|
||||
|
||||
import static com.android.systemui.dreams.dagger.DreamModule.DREAM_OVERLAY_ENABLED;
|
||||
|
||||
import android.service.dreams.DreamService;
|
||||
import android.util.Log;
|
||||
|
||||
@@ -37,6 +39,7 @@ import java.util.function.Consumer;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
/**
|
||||
* {@link DreamOverlayStateController} is the source of truth for Dream overlay configurations and
|
||||
@@ -83,6 +86,7 @@ public class DreamOverlayStateController implements
|
||||
}
|
||||
|
||||
private final Executor mExecutor;
|
||||
private final boolean mOverlayEnabled;
|
||||
private final ArrayList<Callback> mCallbacks = new ArrayList<>();
|
||||
|
||||
@Complication.ComplicationType
|
||||
@@ -94,14 +98,27 @@ public class DreamOverlayStateController implements
|
||||
|
||||
@VisibleForTesting
|
||||
@Inject
|
||||
public DreamOverlayStateController(@Main Executor executor) {
|
||||
public DreamOverlayStateController(@Main Executor executor,
|
||||
@Named(DREAM_OVERLAY_ENABLED) boolean overlayEnabled) {
|
||||
mExecutor = executor;
|
||||
mOverlayEnabled = overlayEnabled;
|
||||
if (DEBUG) {
|
||||
Log.d(TAG, "Dream overlay enabled:" + mOverlayEnabled);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a complication to be included on the dream overlay.
|
||||
*/
|
||||
public void addComplication(Complication complication) {
|
||||
if (!mOverlayEnabled) {
|
||||
if (DEBUG) {
|
||||
Log.d(TAG,
|
||||
"Ignoring adding complication due to overlay disabled:" + complication);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
mExecutor.execute(() -> {
|
||||
if (mComplications.add(complication)) {
|
||||
if (DEBUG) {
|
||||
@@ -116,6 +133,14 @@ public class DreamOverlayStateController implements
|
||||
* Removes a complication from inclusion on the dream overlay.
|
||||
*/
|
||||
public void removeComplication(Complication complication) {
|
||||
if (!mOverlayEnabled) {
|
||||
if (DEBUG) {
|
||||
Log.d(TAG,
|
||||
"Ignoring removing complication due to overlay disabled:" + complication);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
mExecutor.execute(() -> {
|
||||
if (mComplications.remove(complication)) {
|
||||
if (DEBUG) {
|
||||
@@ -193,7 +218,7 @@ public class DreamOverlayStateController implements
|
||||
* @return {@code true} if overlay is active, {@code false} otherwise.
|
||||
*/
|
||||
public boolean isOverlayActive() {
|
||||
return containsState(STATE_DREAM_OVERLAY_ACTIVE);
|
||||
return mOverlayEnabled && containsState(STATE_DREAM_OVERLAY_ACTIVE);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -138,19 +138,27 @@ public class ComplicationHostViewController extends ViewController<ConstraintLay
|
||||
final ComplicationId id = complication.getId();
|
||||
final Complication.ViewHolder viewHolder = complication.getComplication()
|
||||
.createView(complication);
|
||||
|
||||
final View view = viewHolder.getView();
|
||||
|
||||
if (view == null) {
|
||||
Log.e(TAG, "invalid complication view. null view supplied by ViewHolder");
|
||||
return;
|
||||
}
|
||||
|
||||
// Complications to be added before dream entry animations are finished are set
|
||||
// to invisible and are animated in.
|
||||
if (!mEntryAnimationsFinished) {
|
||||
viewHolder.getView().setVisibility(View.INVISIBLE);
|
||||
view.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
mComplications.put(id, viewHolder);
|
||||
if (viewHolder.getView().getParent() != null) {
|
||||
if (view.getParent() != null) {
|
||||
Log.e(TAG, "View for complication "
|
||||
+ complication.getComplication().getClass()
|
||||
+ " already has a parent. Make sure not to reuse complication "
|
||||
+ "views!");
|
||||
}
|
||||
mLayoutEngine.addComplication(id, viewHolder.getView(),
|
||||
mLayoutEngine.addComplication(id, view,
|
||||
viewHolder.getLayoutParams(), viewHolder.getCategory());
|
||||
});
|
||||
}
|
||||
|
||||
@@ -16,7 +16,9 @@
|
||||
|
||||
package com.android.systemui.dreams.dagger;
|
||||
|
||||
import android.content.ComponentName;
|
||||
import android.content.Context;
|
||||
import android.content.pm.PackageManager;
|
||||
import android.content.res.Resources;
|
||||
|
||||
import com.android.dream.lowlight.dagger.LowLightDreamModule;
|
||||
@@ -24,6 +26,7 @@ import com.android.settingslib.dream.DreamBackend;
|
||||
import com.android.systemui.dagger.SysUISingleton;
|
||||
import com.android.systemui.dagger.qualifiers.Main;
|
||||
import com.android.systemui.dreams.DreamOverlayNotificationCountProvider;
|
||||
import com.android.systemui.dreams.DreamOverlayService;
|
||||
import com.android.systemui.dreams.complication.dagger.RegisteredComplicationsModule;
|
||||
|
||||
import java.util.Optional;
|
||||
@@ -45,9 +48,34 @@ import dagger.Provides;
|
||||
})
|
||||
public interface DreamModule {
|
||||
String DREAM_ONLY_ENABLED_FOR_DOCK_USER = "dream_only_enabled_for_dock_user";
|
||||
String DREAM_OVERLAY_SERVICE_COMPONENT = "dream_overlay_service_component";
|
||||
String DREAM_OVERLAY_ENABLED = "dream_overlay_enabled";
|
||||
|
||||
String DREAM_SUPPORTED = "dream_supported";
|
||||
|
||||
/**
|
||||
* Provides the dream component
|
||||
*/
|
||||
@Provides
|
||||
@Named(DREAM_OVERLAY_SERVICE_COMPONENT)
|
||||
static ComponentName providesDreamOverlayService(Context context) {
|
||||
return new ComponentName(context, DreamOverlayService.class);
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides whether dream overlay is enabled.
|
||||
*/
|
||||
@Provides
|
||||
@Named(DREAM_OVERLAY_ENABLED)
|
||||
static Boolean providesDreamOverlayEnabled(PackageManager packageManager,
|
||||
@Named(DREAM_OVERLAY_SERVICE_COMPONENT) ComponentName component) {
|
||||
try {
|
||||
return packageManager.getServiceInfo(component, PackageManager.GET_META_DATA).enabled;
|
||||
} catch (PackageManager.NameNotFoundException e) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides an instance of the dream backend.
|
||||
*/
|
||||
|
||||
@@ -63,7 +63,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testStateChange_overlayActive() {
|
||||
final DreamOverlayStateController stateController = new DreamOverlayStateController(
|
||||
mExecutor);
|
||||
mExecutor, true);
|
||||
stateController.addCallback(mCallback);
|
||||
stateController.setOverlayActive(true);
|
||||
mExecutor.runAllReady();
|
||||
@@ -85,7 +85,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testCallback() {
|
||||
final DreamOverlayStateController stateController = new DreamOverlayStateController(
|
||||
mExecutor);
|
||||
mExecutor, true);
|
||||
stateController.addCallback(mCallback);
|
||||
|
||||
// Add complication and verify callback is notified.
|
||||
@@ -111,7 +111,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testNotifyOnCallbackAdd() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
|
||||
stateController.addComplication(mComplication);
|
||||
mExecutor.runAllReady();
|
||||
@@ -122,10 +122,25 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
verify(mCallback, times(1)).onComplicationsChanged();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNotifyOnCallbackAddOverlayDisabled() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor, false);
|
||||
|
||||
stateController.addComplication(mComplication);
|
||||
mExecutor.runAllReady();
|
||||
|
||||
// Verify callback occurs on add when an overlay is already present.
|
||||
stateController.addCallback(mCallback);
|
||||
mExecutor.runAllReady();
|
||||
verify(mCallback, never()).onComplicationsChanged();
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testComplicationFilteringWhenShouldShowComplications() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
stateController.setShouldShowComplications(true);
|
||||
|
||||
final Complication alwaysAvailableComplication = Mockito.mock(Complication.class);
|
||||
@@ -165,7 +180,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testComplicationFilteringWhenShouldHideComplications() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
stateController.setShouldShowComplications(true);
|
||||
|
||||
final Complication alwaysAvailableComplication = Mockito.mock(Complication.class);
|
||||
@@ -212,7 +227,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
public void testComplicationWithNoTypeNotFiltered() {
|
||||
final Complication complication = Mockito.mock(Complication.class);
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
stateController.addComplication(complication);
|
||||
mExecutor.runAllReady();
|
||||
assertThat(stateController.getComplications(true).contains(complication))
|
||||
@@ -222,7 +237,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testNotifyLowLightChanged() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
|
||||
stateController.addCallback(mCallback);
|
||||
mExecutor.runAllReady();
|
||||
@@ -238,7 +253,7 @@ public class DreamOverlayStateControllerTest extends SysuiTestCase {
|
||||
@Test
|
||||
public void testNotifyEntryAnimationsFinishedChanged() {
|
||||
final DreamOverlayStateController stateController =
|
||||
new DreamOverlayStateController(mExecutor);
|
||||
new DreamOverlayStateController(mExecutor, true);
|
||||
|
||||
stateController.addCallback(mCallback);
|
||||
mExecutor.runAllReady();
|
||||
|
||||
@@ -15,6 +15,8 @@
|
||||
*/
|
||||
package com.android.systemui.dreams.complication;
|
||||
|
||||
import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.ArgumentMatchers.anyInt;
|
||||
import static org.mockito.ArgumentMatchers.eq;
|
||||
import static org.mockito.Mockito.never;
|
||||
import static org.mockito.Mockito.verify;
|
||||
@@ -138,6 +140,21 @@ public class ComplicationHostViewControllerTest extends SysuiTestCase {
|
||||
verify(mLayoutEngine).removeComplication(eq(mComplicationId));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testMalformedComplicationAddition() {
|
||||
final Observer<Collection<ComplicationViewModel>> observer =
|
||||
captureComplicationViewModelsObserver();
|
||||
|
||||
// Add a complication and ensure it is added to the view.
|
||||
final HashSet<ComplicationViewModel> complications = new HashSet<>(
|
||||
Collections.singletonList(mComplicationViewModel));
|
||||
when(mViewHolder.getView()).thenReturn(null);
|
||||
observer.onChanged(complications);
|
||||
|
||||
verify(mLayoutEngine, never()).addComplication(any(), any(), any(), anyInt());
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNewComplicationsBeforeEntryAnimationsFinishSetToInvisible() {
|
||||
final Observer<Collection<ComplicationViewModel>> observer =
|
||||
|
||||
Reference in New Issue
Block a user