diff --git a/services/core/java/com/android/server/vibrator/VibratorController.java b/services/core/java/com/android/server/vibrator/VibratorController.java index 69cc90bf381ec..efccd57d2fc3e 100644 --- a/services/core/java/com/android/server/vibrator/VibratorController.java +++ b/services/core/java/com/android/server/vibrator/VibratorController.java @@ -304,7 +304,7 @@ final class VibratorController { } } - /** Turns off the vibrator.This will affect the state of {@link #isVibrating()}. */ + /** Turns off the vibrator. This will affect the state of {@link #isVibrating()}. */ public void off() { synchronized (mLock) { mNativeWrapper.off(); @@ -313,6 +313,15 @@ final class VibratorController { } } + /** + * Resets the vibrator hardware to a default state. + * This turns the vibrator off, which will affect the state of {@link #isVibrating()}. + */ + public void reset() { + setExternalControl(false); + off(); + } + @Override public String toString() { synchronized (mLock) { diff --git a/services/core/java/com/android/server/vibrator/VibratorManagerService.java b/services/core/java/com/android/server/vibrator/VibratorManagerService.java index c5c0325e55907..567463fd7725d 100644 --- a/services/core/java/com/android/server/vibrator/VibratorManagerService.java +++ b/services/core/java/com/android/server/vibrator/VibratorManagerService.java @@ -219,7 +219,7 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { // fresh boot. mNativeWrapper.cancelSynced(); for (int i = 0; i < mVibrators.size(); i++) { - mVibrators.valueAt(i).off(); + mVibrators.valueAt(i).reset(); } IntentFilter filter = new IntentFilter(); diff --git a/services/tests/servicestests/src/com/android/server/vibrator/FakeVibratorControllerProvider.java b/services/tests/servicestests/src/com/android/server/vibrator/FakeVibratorControllerProvider.java index 75f8a44c6f865..378304d024e53 100644 --- a/services/tests/servicestests/src/com/android/server/vibrator/FakeVibratorControllerProvider.java +++ b/services/tests/servicestests/src/com/android/server/vibrator/FakeVibratorControllerProvider.java @@ -52,6 +52,7 @@ final class FakeVibratorControllerProvider { private boolean mIsAvailable = true; private long mLatency; + private int mOffCount; private int mCapabilities; private int[] mSupportedEffects; @@ -93,6 +94,7 @@ final class FakeVibratorControllerProvider { @Override public void off() { + mOffCount++; } @Override @@ -308,6 +310,11 @@ final class FakeVibratorControllerProvider { return mExternalControlStates; } + /** Returns the number of times the vibrator was turned off. */ + public int getOffCount() { + return mOffCount; + } + /** * Return the {@link PrebakedSegment} effect enabled with given id, or {@code null} if * missing or disabled. diff --git a/services/tests/servicestests/src/com/android/server/vibrator/VibratorControllerTest.java b/services/tests/servicestests/src/com/android/server/vibrator/VibratorControllerTest.java index a732bd18676ab..9fb8b38a706e5 100644 --- a/services/tests/servicestests/src/com/android/server/vibrator/VibratorControllerTest.java +++ b/services/tests/servicestests/src/com/android/server/vibrator/VibratorControllerTest.java @@ -258,6 +258,21 @@ public class VibratorControllerTest { verify(mNativeWrapperMock, times(2)).off(); } + @Test + public void reset_turnsOffVibratorAndDisablesExternalControl() { + mockVibratorCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); + when(mNativeWrapperMock.on(anyLong(), anyLong())).thenAnswer(args -> args.getArgument(0)); + VibratorController controller = createController(); + + controller.on(100, 1); + assertTrue(controller.isVibrating()); + + controller.reset(); + assertFalse(controller.isVibrating()); + verify(mNativeWrapperMock).setExternalControl(eq(false)); + verify(mNativeWrapperMock).off(); + } + @Test public void registerVibratorStateListener_callbacksAreTriggered() throws Exception { when(mNativeWrapperMock.on(anyLong(), anyLong())).thenAnswer(args -> args.getArgument(0)); diff --git a/services/tests/servicestests/src/com/android/server/vibrator/VibratorManagerServiceTest.java b/services/tests/servicestests/src/com/android/server/vibrator/VibratorManagerServiceTest.java index 2c5159aef1e25..f9e63d1b1d0ac 100644 --- a/services/tests/servicestests/src/com/android/server/vibrator/VibratorManagerServiceTest.java +++ b/services/tests/servicestests/src/com/android/server/vibrator/VibratorManagerServiceTest.java @@ -232,6 +232,19 @@ public class VibratorManagerServiceTest { assertTrue(mVibratorProviders.get(2).isInitialized()); } + @Test + public void createService_resetsVibrators() { + mockVibrators(1, 2); + mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); + mVibratorProviders.get(2).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); + + createService(); + assertEquals(1, mVibratorProviders.get(1).getOffCount()); + assertEquals(1, mVibratorProviders.get(2).getOffCount()); + assertEquals(Arrays.asList(false), mVibratorProviders.get(1).getExternalControlStates()); + assertEquals(Arrays.asList(false), mVibratorProviders.get(2).getExternalControlStates()); + } + @Test public void createService_doNotCrashIfUsedBeforeSystemReady() { mockVibrators(1, 2); @@ -991,7 +1004,7 @@ public class VibratorManagerServiceTest { mExternalVibratorService.onExternalVibrationStop(externalVibration); assertEquals(IExternalVibratorService.SCALE_NONE, scale); - assertEquals(Arrays.asList(true, false), + assertEquals(Arrays.asList(false, true, false), mVibratorProviders.get(1).getExternalControlStates()); } @@ -1017,7 +1030,8 @@ public class VibratorManagerServiceTest { verify(firstController).mute(); verify(secondController, never()).mute(); // Set external control called only once. - assertEquals(Arrays.asList(true), mVibratorProviders.get(1).getExternalControlStates()); + assertEquals(Arrays.asList(false, true), + mVibratorProviders.get(1).getExternalControlStates()); } @Test @@ -1039,7 +1053,8 @@ public class VibratorManagerServiceTest { // Vibration is cancelled. assertTrue(waitUntil(s -> !s.isVibrating(1), service, TEST_TIMEOUT_MILLIS)); - assertEquals(Arrays.asList(true), mVibratorProviders.get(1).getExternalControlStates()); + assertEquals(Arrays.asList(false, true), + mVibratorProviders.get(1).getExternalControlStates()); } private VibrationEffectSegment expectedPrebaked(int effectId) {