Loading packages/SystemUI/src/com/android/systemui/doze/DozeSensors.java +59 −8 Original line number Diff line number Diff line Loading @@ -16,6 +16,8 @@ package com.android.systemui.doze; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_QUICK_PICKUP; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_DISPLAY; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_LOCK_SCREEN; Loading Loading @@ -98,6 +100,7 @@ public class DozeSensors { private final DozeLog mDozeLog; private final SecureSettings mSecureSettings; private final DevicePostureController mDevicePostureController; private final AuthController mAuthController; private final boolean mScreenOffUdfpsEnabled; // Sensors Loading @@ -115,6 +118,7 @@ public class DozeSensors { private boolean mListening; private boolean mListeningTouchScreenSensors; private boolean mListeningProxSensors; private boolean mUdfpsEnrolled; @DevicePostureController.DevicePostureInt private int mDevicePosture; Loading Loading @@ -169,10 +173,11 @@ public class DozeSensors { config.screenOffUdfpsEnabled(KeyguardUpdateMonitor.getCurrentUser()); mDevicePostureController = devicePostureController; mDevicePosture = mDevicePostureController.getDevicePosture(); mAuthController = authController; boolean udfpsEnrolled = authController.isUdfpsEnrolled(KeyguardUpdateMonitor.getCurrentUser()); boolean alwaysOn = mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT); mUdfpsEnrolled = mAuthController.isUdfpsEnrolled(KeyguardUpdateMonitor.getCurrentUser()); mAuthController.addCallback(mAuthControllerCallback); mTriggerSensors = new TriggerSensor[] { new TriggerSensor( mSensorManager.getDefaultSensor(Sensor.TYPE_SIGNIFICANT_MOTION), Loading Loading @@ -221,7 +226,7 @@ public class DozeSensors { findSensor(config.udfpsLongPressSensorType()), "doze_pulse_on_auth", true /* settingDef */, udfpsEnrolled && (alwaysOn || mScreenOffUdfpsEnabled), udfpsLongPressConfigured(), DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS, true /* reports touch coordinates */, true /* touchscreen */, Loading @@ -230,7 +235,8 @@ public class DozeSensors { new PluginSensor( new SensorManagerPlugin.Sensor(TYPE_WAKE_DISPLAY), Settings.Secure.DOZE_WAKE_DISPLAY_GESTURE, mConfig.wakeScreenGestureAvailable() && alwaysOn, mConfig.wakeScreenGestureAvailable() && mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT), DozeLog.REASON_SENSOR_WAKE_UP_PRESENCE, false /* reports touch coordinates */, false /* touchscreen */), Loading @@ -246,8 +252,7 @@ public class DozeSensors { findSensor(config.quickPickupSensorType()), Settings.Secure.DOZE_QUICK_PICKUP_GESTURE, true /* setting default */, config.quickPickupSensorEnabled(KeyguardUpdateMonitor.getCurrentUser()) && udfpsEnrolled, quickPickUpConfigured(), DozeLog.REASON_SENSOR_QUICK_PICKUP, false /* requiresTouchCoordinates */, false /* requiresTouchscreen */, Loading @@ -265,6 +270,16 @@ public class DozeSensors { mDevicePostureController.addCallback(mDevicePostureCallback); } private boolean udfpsLongPressConfigured() { return mUdfpsEnrolled && (mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT) || mScreenOffUdfpsEnabled); } private boolean quickPickUpConfigured() { return mUdfpsEnrolled && mConfig.quickPickupSensorEnabled(KeyguardUpdateMonitor.getCurrentUser()); } /** * Unregister all sensors and callbacks. */ Loading @@ -276,6 +291,7 @@ public class DozeSensors { mProximitySensor.pause(); mDevicePostureController.removeCallback(mDevicePostureCallback); mAuthController.removeCallback(mAuthControllerCallback); } /** Loading Loading @@ -450,6 +466,7 @@ public class DozeSensors { pw.println("mSelectivelyRegisterProxSensors=" + mSelectivelyRegisterProxSensors); pw.println("mListeningProxSensors=" + mListeningProxSensors); pw.println("mScreenOffUdfpsEnabled=" + mScreenOffUdfpsEnabled); pw.println("mUdfpsEnrolled=" + mUdfpsEnrolled); IndentingPrintWriter idpw = new IndentingPrintWriter(pw); idpw.increaseIndent(); for (TriggerSensor s : mTriggerSensors) { Loading @@ -468,7 +485,7 @@ public class DozeSensors { @VisibleForTesting class TriggerSensor extends TriggerEventListener { @NonNull final Sensor[] mSensors; // index = posture, value = sensor final boolean mConfigured; boolean mConfigured; final int mPulseReason; private final String mSetting; private final boolean mReportsTouchCoordinates; Loading Loading @@ -606,8 +623,18 @@ public class DozeSensors { updateListening(); } /** * Update configured state. */ public void setConfigured(boolean configured) { if (mConfigured == configured) return; mConfigured = configured; updateListening(); } public void updateListening() { final Sensor sensor = mSensors[mPosture]; if (!mConfigured || sensor == null) return; if (mRequested && !mDisabled && (enabledBySetting() || mIgnoresSetting)) { if (!mRegistered) { Loading Loading @@ -791,6 +818,30 @@ public class DozeSensors { } }; private final AuthController.Callback mAuthControllerCallback = new AuthController.Callback() { @Override public void onAllAuthenticatorsRegistered() { updateUdfpsEnrolled(); } @Override public void onEnrollmentsChanged() { updateUdfpsEnrolled(); } private void updateUdfpsEnrolled() { mUdfpsEnrolled = mAuthController.isUdfpsEnrolled( KeyguardUpdateMonitor.getCurrentUser()); for (TriggerSensor sensor : mTriggerSensors) { if (REASON_SENSOR_QUICK_PICKUP == sensor.mPulseReason) { sensor.setConfigured(quickPickUpConfigured()); } else if (REASON_SENSOR_UDFPS_LONG_PRESS == sensor.mPulseReason) { sensor.setConfigured(udfpsLongPressConfigured()); } } } }; public interface Callback { /** Loading packages/SystemUI/tests/src/com/android/systemui/doze/DozeSensorsTest.java +70 −1 Original line number Diff line number Diff line Loading @@ -17,6 +17,7 @@ package com.android.systemui.doze; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_TAP; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_LOCK_SCREEN; import static org.junit.Assert.assertEquals; Loading @@ -37,6 +38,7 @@ import static org.mockito.Mockito.when; import android.database.ContentObserver; import android.hardware.Sensor; import android.hardware.display.AmbientDisplayConfiguration; import android.os.UserHandle; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import android.testing.TestableLooper.RunWithLooper; Loading @@ -57,6 +59,8 @@ import com.android.systemui.util.wakelock.WakeLock; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.ArgumentCaptor; import org.mockito.Captor; import org.mockito.Mock; import org.mockito.MockitoAnnotations; Loading Loading @@ -94,6 +98,13 @@ public class DozeSensorsTest extends SysuiTestCase { private DevicePostureController mDevicePostureController; @Mock private ProximitySensor mProximitySensor; // Capture listeners so that they can be used to send events @Captor private ArgumentCaptor<AuthController.Callback> mAuthControllerCallbackCaptor = ArgumentCaptor.forClass(AuthController.Callback.class); private AuthController.Callback mAuthControllerCallback; private FakeSettings mFakeSettings = new FakeSettings(); private SensorManagerPlugin.SensorEventListener mWakeLockScreenListener; private TestableLooper mTestableLooper; Loading @@ -105,14 +116,18 @@ public class DozeSensorsTest extends SysuiTestCase { MockitoAnnotations.initMocks(this); mTestableLooper = TestableLooper.get(this); when(mAmbientDisplayConfiguration.tapSensorTypeMapping()) .thenReturn(new String[]{"tapSEnsor"}); .thenReturn(new String[]{"tapSensor"}); when(mAmbientDisplayConfiguration.getWakeLockScreenDebounce()).thenReturn(5000L); when(mAmbientDisplayConfiguration.alwaysOnEnabled(anyInt())).thenReturn(true); when(mAmbientDisplayConfiguration.enabled(UserHandle.USER_CURRENT)).thenReturn(true); doAnswer(invocation -> { ((Runnable) invocation.getArgument(0)).run(); return null; }).when(mWakeLock).wrap(any(Runnable.class)); mDozeSensors = new TestableDozeSensors(); verify(mAuthController).addCallback(mAuthControllerCallbackCaptor.capture()); mAuthControllerCallback = mAuthControllerCallbackCaptor.getValue(); } @Test Loading Loading @@ -375,6 +390,35 @@ public class DozeSensorsTest extends SysuiTestCase { "some other name")); } @Test public void testUdfpsEnrollmentChanged() throws Exception { // GIVEN a UDFPS_LONG_PRESS trigger sensor that's not configured Sensor mockSensor = mock(Sensor.class); TriggerSensor triggerSensor = mDozeSensors.createDozeSensor( mockSensor, REASON_SENSOR_UDFPS_LONG_PRESS, /* configured */ false); mDozeSensors.addSensor(triggerSensor); when(mSensorManager.requestTriggerSensor(eq(triggerSensor), eq(mockSensor))) .thenReturn(true); // WHEN listening state is set to TRUE mDozeSensors.setListening(true, true); // THEN mRegistered is still false b/c !mConfigured assertFalse(triggerSensor.mConfigured); assertFalse(triggerSensor.mRegistered); // WHEN enrollment changes to TRUE when(mAuthController.isUdfpsEnrolled(anyInt())).thenReturn(true); mAuthControllerCallback.onEnrollmentsChanged(); // THEN mConfigured = TRUE assertTrue(triggerSensor.mConfigured); // THEN mRegistered = TRUE assertTrue(triggerSensor.mRegistered); } private class TestableDozeSensors extends DozeSensors { TestableDozeSensors() { Loading Loading @@ -407,6 +451,22 @@ public class DozeSensorsTest extends SysuiTestCase { requiresTouchScreen); } public TriggerSensor createDozeSensor( Sensor sensor, int pulseReason, boolean configured ) { return new TriggerSensor(/* sensor */ sensor, /* setting name */ "test_setting", /* settingDefault */ true, /* configured */ configured, /* pulseReason*/ pulseReason, /* reportsTouchCoordinate*/ false, /* requiresTouchscreen */ false, /* ignoresSetting */ false, /* requiresTouchScreen */false); } /** * create a doze sensor that supports postures and is enabled */ Loading @@ -422,6 +482,15 @@ public class DozeSensorsTest extends SysuiTestCase { /* requiresProx */false, posture); } public void addSensor(TriggerSensor sensor) { TriggerSensor[] newArray = new TriggerSensor[mTriggerSensors.length + 1]; for (int i = 0; i < mTriggerSensors.length; i++) { newArray[i] = mTriggerSensors[i]; } newArray[mTriggerSensors.length] = sensor; mTriggerSensors = newArray; } } public static void setSensorType(Sensor sensor, int type, String strType) throws Exception { Loading Loading
packages/SystemUI/src/com/android/systemui/doze/DozeSensors.java +59 −8 Original line number Diff line number Diff line Loading @@ -16,6 +16,8 @@ package com.android.systemui.doze; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_QUICK_PICKUP; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_DISPLAY; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_LOCK_SCREEN; Loading Loading @@ -98,6 +100,7 @@ public class DozeSensors { private final DozeLog mDozeLog; private final SecureSettings mSecureSettings; private final DevicePostureController mDevicePostureController; private final AuthController mAuthController; private final boolean mScreenOffUdfpsEnabled; // Sensors Loading @@ -115,6 +118,7 @@ public class DozeSensors { private boolean mListening; private boolean mListeningTouchScreenSensors; private boolean mListeningProxSensors; private boolean mUdfpsEnrolled; @DevicePostureController.DevicePostureInt private int mDevicePosture; Loading Loading @@ -169,10 +173,11 @@ public class DozeSensors { config.screenOffUdfpsEnabled(KeyguardUpdateMonitor.getCurrentUser()); mDevicePostureController = devicePostureController; mDevicePosture = mDevicePostureController.getDevicePosture(); mAuthController = authController; boolean udfpsEnrolled = authController.isUdfpsEnrolled(KeyguardUpdateMonitor.getCurrentUser()); boolean alwaysOn = mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT); mUdfpsEnrolled = mAuthController.isUdfpsEnrolled(KeyguardUpdateMonitor.getCurrentUser()); mAuthController.addCallback(mAuthControllerCallback); mTriggerSensors = new TriggerSensor[] { new TriggerSensor( mSensorManager.getDefaultSensor(Sensor.TYPE_SIGNIFICANT_MOTION), Loading Loading @@ -221,7 +226,7 @@ public class DozeSensors { findSensor(config.udfpsLongPressSensorType()), "doze_pulse_on_auth", true /* settingDef */, udfpsEnrolled && (alwaysOn || mScreenOffUdfpsEnabled), udfpsLongPressConfigured(), DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS, true /* reports touch coordinates */, true /* touchscreen */, Loading @@ -230,7 +235,8 @@ public class DozeSensors { new PluginSensor( new SensorManagerPlugin.Sensor(TYPE_WAKE_DISPLAY), Settings.Secure.DOZE_WAKE_DISPLAY_GESTURE, mConfig.wakeScreenGestureAvailable() && alwaysOn, mConfig.wakeScreenGestureAvailable() && mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT), DozeLog.REASON_SENSOR_WAKE_UP_PRESENCE, false /* reports touch coordinates */, false /* touchscreen */), Loading @@ -246,8 +252,7 @@ public class DozeSensors { findSensor(config.quickPickupSensorType()), Settings.Secure.DOZE_QUICK_PICKUP_GESTURE, true /* setting default */, config.quickPickupSensorEnabled(KeyguardUpdateMonitor.getCurrentUser()) && udfpsEnrolled, quickPickUpConfigured(), DozeLog.REASON_SENSOR_QUICK_PICKUP, false /* requiresTouchCoordinates */, false /* requiresTouchscreen */, Loading @@ -265,6 +270,16 @@ public class DozeSensors { mDevicePostureController.addCallback(mDevicePostureCallback); } private boolean udfpsLongPressConfigured() { return mUdfpsEnrolled && (mConfig.alwaysOnEnabled(UserHandle.USER_CURRENT) || mScreenOffUdfpsEnabled); } private boolean quickPickUpConfigured() { return mUdfpsEnrolled && mConfig.quickPickupSensorEnabled(KeyguardUpdateMonitor.getCurrentUser()); } /** * Unregister all sensors and callbacks. */ Loading @@ -276,6 +291,7 @@ public class DozeSensors { mProximitySensor.pause(); mDevicePostureController.removeCallback(mDevicePostureCallback); mAuthController.removeCallback(mAuthControllerCallback); } /** Loading Loading @@ -450,6 +466,7 @@ public class DozeSensors { pw.println("mSelectivelyRegisterProxSensors=" + mSelectivelyRegisterProxSensors); pw.println("mListeningProxSensors=" + mListeningProxSensors); pw.println("mScreenOffUdfpsEnabled=" + mScreenOffUdfpsEnabled); pw.println("mUdfpsEnrolled=" + mUdfpsEnrolled); IndentingPrintWriter idpw = new IndentingPrintWriter(pw); idpw.increaseIndent(); for (TriggerSensor s : mTriggerSensors) { Loading @@ -468,7 +485,7 @@ public class DozeSensors { @VisibleForTesting class TriggerSensor extends TriggerEventListener { @NonNull final Sensor[] mSensors; // index = posture, value = sensor final boolean mConfigured; boolean mConfigured; final int mPulseReason; private final String mSetting; private final boolean mReportsTouchCoordinates; Loading Loading @@ -606,8 +623,18 @@ public class DozeSensors { updateListening(); } /** * Update configured state. */ public void setConfigured(boolean configured) { if (mConfigured == configured) return; mConfigured = configured; updateListening(); } public void updateListening() { final Sensor sensor = mSensors[mPosture]; if (!mConfigured || sensor == null) return; if (mRequested && !mDisabled && (enabledBySetting() || mIgnoresSetting)) { if (!mRegistered) { Loading Loading @@ -791,6 +818,30 @@ public class DozeSensors { } }; private final AuthController.Callback mAuthControllerCallback = new AuthController.Callback() { @Override public void onAllAuthenticatorsRegistered() { updateUdfpsEnrolled(); } @Override public void onEnrollmentsChanged() { updateUdfpsEnrolled(); } private void updateUdfpsEnrolled() { mUdfpsEnrolled = mAuthController.isUdfpsEnrolled( KeyguardUpdateMonitor.getCurrentUser()); for (TriggerSensor sensor : mTriggerSensors) { if (REASON_SENSOR_QUICK_PICKUP == sensor.mPulseReason) { sensor.setConfigured(quickPickUpConfigured()); } else if (REASON_SENSOR_UDFPS_LONG_PRESS == sensor.mPulseReason) { sensor.setConfigured(udfpsLongPressConfigured()); } } } }; public interface Callback { /** Loading
packages/SystemUI/tests/src/com/android/systemui/doze/DozeSensorsTest.java +70 −1 Original line number Diff line number Diff line Loading @@ -17,6 +17,7 @@ package com.android.systemui.doze; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_TAP; import static com.android.systemui.doze.DozeLog.REASON_SENSOR_UDFPS_LONG_PRESS; import static com.android.systemui.plugins.SensorManagerPlugin.Sensor.TYPE_WAKE_LOCK_SCREEN; import static org.junit.Assert.assertEquals; Loading @@ -37,6 +38,7 @@ import static org.mockito.Mockito.when; import android.database.ContentObserver; import android.hardware.Sensor; import android.hardware.display.AmbientDisplayConfiguration; import android.os.UserHandle; import android.testing.AndroidTestingRunner; import android.testing.TestableLooper; import android.testing.TestableLooper.RunWithLooper; Loading @@ -57,6 +59,8 @@ import com.android.systemui.util.wakelock.WakeLock; import org.junit.Before; import org.junit.Test; import org.junit.runner.RunWith; import org.mockito.ArgumentCaptor; import org.mockito.Captor; import org.mockito.Mock; import org.mockito.MockitoAnnotations; Loading Loading @@ -94,6 +98,13 @@ public class DozeSensorsTest extends SysuiTestCase { private DevicePostureController mDevicePostureController; @Mock private ProximitySensor mProximitySensor; // Capture listeners so that they can be used to send events @Captor private ArgumentCaptor<AuthController.Callback> mAuthControllerCallbackCaptor = ArgumentCaptor.forClass(AuthController.Callback.class); private AuthController.Callback mAuthControllerCallback; private FakeSettings mFakeSettings = new FakeSettings(); private SensorManagerPlugin.SensorEventListener mWakeLockScreenListener; private TestableLooper mTestableLooper; Loading @@ -105,14 +116,18 @@ public class DozeSensorsTest extends SysuiTestCase { MockitoAnnotations.initMocks(this); mTestableLooper = TestableLooper.get(this); when(mAmbientDisplayConfiguration.tapSensorTypeMapping()) .thenReturn(new String[]{"tapSEnsor"}); .thenReturn(new String[]{"tapSensor"}); when(mAmbientDisplayConfiguration.getWakeLockScreenDebounce()).thenReturn(5000L); when(mAmbientDisplayConfiguration.alwaysOnEnabled(anyInt())).thenReturn(true); when(mAmbientDisplayConfiguration.enabled(UserHandle.USER_CURRENT)).thenReturn(true); doAnswer(invocation -> { ((Runnable) invocation.getArgument(0)).run(); return null; }).when(mWakeLock).wrap(any(Runnable.class)); mDozeSensors = new TestableDozeSensors(); verify(mAuthController).addCallback(mAuthControllerCallbackCaptor.capture()); mAuthControllerCallback = mAuthControllerCallbackCaptor.getValue(); } @Test Loading Loading @@ -375,6 +390,35 @@ public class DozeSensorsTest extends SysuiTestCase { "some other name")); } @Test public void testUdfpsEnrollmentChanged() throws Exception { // GIVEN a UDFPS_LONG_PRESS trigger sensor that's not configured Sensor mockSensor = mock(Sensor.class); TriggerSensor triggerSensor = mDozeSensors.createDozeSensor( mockSensor, REASON_SENSOR_UDFPS_LONG_PRESS, /* configured */ false); mDozeSensors.addSensor(triggerSensor); when(mSensorManager.requestTriggerSensor(eq(triggerSensor), eq(mockSensor))) .thenReturn(true); // WHEN listening state is set to TRUE mDozeSensors.setListening(true, true); // THEN mRegistered is still false b/c !mConfigured assertFalse(triggerSensor.mConfigured); assertFalse(triggerSensor.mRegistered); // WHEN enrollment changes to TRUE when(mAuthController.isUdfpsEnrolled(anyInt())).thenReturn(true); mAuthControllerCallback.onEnrollmentsChanged(); // THEN mConfigured = TRUE assertTrue(triggerSensor.mConfigured); // THEN mRegistered = TRUE assertTrue(triggerSensor.mRegistered); } private class TestableDozeSensors extends DozeSensors { TestableDozeSensors() { Loading Loading @@ -407,6 +451,22 @@ public class DozeSensorsTest extends SysuiTestCase { requiresTouchScreen); } public TriggerSensor createDozeSensor( Sensor sensor, int pulseReason, boolean configured ) { return new TriggerSensor(/* sensor */ sensor, /* setting name */ "test_setting", /* settingDefault */ true, /* configured */ configured, /* pulseReason*/ pulseReason, /* reportsTouchCoordinate*/ false, /* requiresTouchscreen */ false, /* ignoresSetting */ false, /* requiresTouchScreen */false); } /** * create a doze sensor that supports postures and is enabled */ Loading @@ -422,6 +482,15 @@ public class DozeSensorsTest extends SysuiTestCase { /* requiresProx */false, posture); } public void addSensor(TriggerSensor sensor) { TriggerSensor[] newArray = new TriggerSensor[mTriggerSensors.length + 1]; for (int i = 0; i < mTriggerSensors.length; i++) { newArray[i] = mTriggerSensors[i]; } newArray[mTriggerSensors.length] = sensor; mTriggerSensors = newArray; } } public static void setSensorType(Sensor sensor, int type, String strType) throws Exception { Loading