Fix lockscreen shortcuts not showing on split shade
The issue was that qsVisible was wrongly being set to `true` when on
split shade, even when it was not visible.
Lockscreen shortcuts only show when QS are not visible.
To check whether QS (or QQS) was visible, we were checking:
1 - qsExpansionFraction > 0
1.1 Split shade: true when full QS showing
1.2 Single shade: true when full QS showing
2 - qsPanelBottomY > 0
2.1 Split Shade: ALWAYS true. Even if QS not showing
2.2 Single shade: true when on QQS or QS
Since on split shade we can always rely on qsExpansionFraction, because
there is no QQS, we changed the condition to ignore qsPanelBottomY
when on split shade.
Fixes: 272448562
Test: Manually on-device:
1 - Enabled teamfood flag
2 - Homescreen -> Wallpaper & Style
3 - Lockscreen -> Pick 2 non-none shortcuts
4 - Lock the screen
5 - Verify shortcuts are visible both in single and split shade
Test: QuickSettingsControllerTest.java
Change-Id: I9adc0c4625aadcc729b484c453c6ef7d17013fc9
This commit is contained in:
@@ -1035,7 +1035,11 @@ public class QuickSettingsController {
|
||||
private void setClippingBounds() {
|
||||
float qsExpansionFraction = computeExpansionFraction();
|
||||
final int qsPanelBottomY = calculateBottomPosition(qsExpansionFraction);
|
||||
final boolean qsVisible = (qsExpansionFraction > 0 || qsPanelBottomY > 0);
|
||||
// Split shade has no QQS
|
||||
final boolean qqsVisible =
|
||||
!mSplitShadeEnabled && qsExpansionFraction == 0 && qsPanelBottomY > 0;
|
||||
final boolean qsVisible = qsExpansionFraction > 0;
|
||||
final boolean qsOrQqsVisible = qqsVisible || qsVisible;
|
||||
checkCorrectScrimVisibility(qsExpansionFraction);
|
||||
|
||||
int top = calculateTopClippingBound(qsPanelBottomY);
|
||||
@@ -1044,7 +1048,7 @@ public class QuickSettingsController {
|
||||
int right = calculateRightClippingBound();
|
||||
// top should never be lower than bottom, otherwise it will be invisible.
|
||||
top = Math.min(top, bottom);
|
||||
applyClippingBounds(left, top, right, bottom, qsVisible);
|
||||
applyClippingBounds(left, top, right, bottom, qsOrQqsVisible);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -32,6 +32,7 @@ import static org.mockito.ArgumentMatchers.any;
|
||||
import static org.mockito.ArgumentMatchers.anyFloat;
|
||||
import static org.mockito.ArgumentMatchers.anyInt;
|
||||
import static org.mockito.ArgumentMatchers.eq;
|
||||
import static org.mockito.Mockito.atLeastOnce;
|
||||
import static org.mockito.Mockito.doAnswer;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.times;
|
||||
@@ -77,7 +78,6 @@ import com.android.systemui.statusbar.StatusBarStateControllerImpl;
|
||||
import com.android.systemui.statusbar.SysuiStatusBarStateController;
|
||||
import com.android.systemui.statusbar.notification.stack.AmbientState;
|
||||
import com.android.systemui.statusbar.notification.stack.NotificationStackScrollLayoutController;
|
||||
import com.android.systemui.statusbar.phone.HeadsUpManagerPhone;
|
||||
import com.android.systemui.statusbar.phone.KeyguardBottomAreaView;
|
||||
import com.android.systemui.statusbar.phone.KeyguardBypassController;
|
||||
import com.android.systemui.statusbar.phone.KeyguardStatusBarView;
|
||||
@@ -91,9 +91,12 @@ import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.mockito.ArgumentCaptor;
|
||||
import org.mockito.Mock;
|
||||
import org.mockito.MockitoAnnotations;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import dagger.Lazy;
|
||||
|
||||
@SmallTest
|
||||
@@ -101,12 +104,14 @@ import dagger.Lazy;
|
||||
@TestableLooper.RunWithLooper(setAsMainLooper = true)
|
||||
public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
|
||||
private static final int SPLIT_SHADE_FULL_TRANSITION_DISTANCE = 400;
|
||||
private static final float QS_FRAME_START_X = 0f;
|
||||
private static final int QS_FRAME_WIDTH = 1000;
|
||||
private static final int QS_FRAME_TOP = 0;
|
||||
private static final int QS_FRAME_BOTTOM = 1000;
|
||||
|
||||
private static final int DEFAULT_HEIGHT = 1000;
|
||||
// In split shade min = max
|
||||
private static final int DEFAULT_MIN_HEIGHT_SPLIT_SHADE = DEFAULT_HEIGHT;
|
||||
private static final int DEFAULT_MIN_HEIGHT = 300;
|
||||
|
||||
private QuickSettingsController mQsController;
|
||||
|
||||
@@ -115,7 +120,6 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
@Mock private KeyguardStatusBarView mKeyguardStatusBar;
|
||||
@Mock private QS mQs;
|
||||
@Mock private QSFragment mQSFragment;
|
||||
|
||||
@Mock private Lazy<NotificationPanelViewController> mPanelViewControllerLazy;
|
||||
@Mock private NotificationPanelViewController mNotificationPanelViewController;
|
||||
@Mock private NotificationPanelView mPanelView;
|
||||
@@ -147,10 +151,7 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
@Mock private FeatureFlags mFeatureFlags;
|
||||
@Mock private InteractionJankMonitor mInteractionJankMonitor;
|
||||
@Mock private ShadeLogger mShadeLogger;
|
||||
|
||||
@Mock private DumpManager mDumpManager;
|
||||
|
||||
@Mock private HeadsUpManagerPhone mHeadsUpManager;
|
||||
@Mock private UiEventLogger mUiEventLogger;
|
||||
|
||||
private SysuiStatusBarStateController mStatusBarStateController;
|
||||
@@ -173,6 +174,8 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
KeyguardStatusView keyguardStatusView = new KeyguardStatusView(mContext);
|
||||
keyguardStatusView.setId(R.id.keyguard_status_view);
|
||||
|
||||
when(mResources.getDimensionPixelSize(
|
||||
R.dimen.lockscreen_shade_qs_transition_distance)).thenReturn(DEFAULT_HEIGHT);
|
||||
when(mPanelView.getResources()).thenReturn(mResources);
|
||||
when(mPanelView.getContext()).thenReturn(getContext());
|
||||
when(mPanelView.findViewById(R.id.keyguard_header)).thenReturn(mKeyguardStatusBar);
|
||||
@@ -529,6 +532,88 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
assertThat(mQsController.isOpenQsEvent(event)).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shadeClosed_onLockscreen_inSplitShade_setsQsNotVisible() {
|
||||
mQsController.setQs(mQs);
|
||||
enableSplitShade(true);
|
||||
lockScreen();
|
||||
|
||||
closeLockedQS();
|
||||
|
||||
assertQsVisible(false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shadeOpened_onLockscreen_inSplitShade_setsQsVisible() {
|
||||
mQsController.setQs(mQs);
|
||||
enableSplitShade(true);
|
||||
lockScreen();
|
||||
|
||||
openLockedQS();
|
||||
|
||||
assertQsVisible(true);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shadeClosed_onLockscreen_inSingleShade_setsQsNotVisible() {
|
||||
mQsController.setQs(mQs);
|
||||
enableSplitShade(false);
|
||||
lockScreen();
|
||||
|
||||
closeLockedQS();
|
||||
|
||||
verify(mQs).setQsVisible(false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void shadeOpened_onLockscreen_inSingleShade_setsQsVisible() {
|
||||
mQsController.setQs(mQs);
|
||||
enableSplitShade(false);
|
||||
lockScreen();
|
||||
|
||||
openLockedQS();
|
||||
|
||||
verify(mQs).setQsVisible(true);
|
||||
}
|
||||
|
||||
private void lockScreen() {
|
||||
mQsController.setBarState(KEYGUARD);
|
||||
}
|
||||
|
||||
private void openLockedQS() {
|
||||
when(mLockscreenShadeTransitionController.getQSDragProgress())
|
||||
.thenReturn((float) DEFAULT_HEIGHT);
|
||||
mLockscreenShadeTransitionCallback.setTransitionToFullShadeAmount(
|
||||
/* pxAmount= */ DEFAULT_HEIGHT,
|
||||
/* animate=*/ false,
|
||||
/* delay= */ 0
|
||||
);
|
||||
}
|
||||
|
||||
private void closeLockedQS() {
|
||||
when(mLockscreenShadeTransitionController.getQSDragProgress()).thenReturn(0f);
|
||||
mLockscreenShadeTransitionCallback.setTransitionToFullShadeAmount(
|
||||
/* pxAmount= */ 0,
|
||||
/* animate=*/ false,
|
||||
/* delay= */ 0
|
||||
);
|
||||
}
|
||||
|
||||
private void setSplitShadeHeightProperties() {
|
||||
// In split shade, min = max
|
||||
when(mQs.getQsMinExpansionHeight()).thenReturn(DEFAULT_MIN_HEIGHT_SPLIT_SHADE);
|
||||
when(mQs.getDesiredHeight()).thenReturn(DEFAULT_HEIGHT);
|
||||
mQsController.updateMinHeight();
|
||||
mQsController.onHeightChanged();
|
||||
}
|
||||
|
||||
private void setDefaultHeightProperties() {
|
||||
when(mQs.getQsMinExpansionHeight()).thenReturn(DEFAULT_MIN_HEIGHT);
|
||||
when(mQs.getDesiredHeight()).thenReturn(DEFAULT_HEIGHT);
|
||||
mQsController.updateMinHeight();
|
||||
mQsController.onHeightChanged();
|
||||
}
|
||||
|
||||
private static MotionEvent createMotionEvent(int x, int y, int action) {
|
||||
return MotionEvent.obtain(0, 0, action, x, y, 0);
|
||||
}
|
||||
@@ -549,6 +634,11 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
private void enableSplitShade(boolean enabled) {
|
||||
when(mResources.getBoolean(R.bool.config_use_split_notification_shade)).thenReturn(enabled);
|
||||
mQsController.updateResources();
|
||||
if (enabled) {
|
||||
setSplitShadeHeightProperties();
|
||||
} else {
|
||||
setDefaultHeightProperties();
|
||||
}
|
||||
}
|
||||
|
||||
private void setIsFullWidth(boolean fullWidth) {
|
||||
@@ -561,5 +651,11 @@ public class QuickSettingsControllerTest extends SysuiTestCase {
|
||||
mQsController.handleShadeLayoutChanged(oldMaxHeight);
|
||||
}
|
||||
|
||||
|
||||
private void assertQsVisible(boolean visible) {
|
||||
ArgumentCaptor<Boolean> visibilityCaptor = ArgumentCaptor.forClass(Boolean.class);
|
||||
verify(mQs, atLeastOnce()).setQsVisible(visibilityCaptor.capture());
|
||||
List<Boolean> allVisibilities = visibilityCaptor.getAllValues();
|
||||
boolean lastVisibility = allVisibilities.get(allVisibilities.size() - 1);
|
||||
assertThat(lastVisibility).isEqualTo(visible);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user