Loading core/java/android/os/vibrator/flags.aconfig +10 −0 Original line number Diff line number Diff line Loading @@ -155,3 +155,13 @@ flag { purpose: PURPOSE_BUGFIX } } flag { namespace: "haptics" name: "fix_external_vibration_system_update_aware" description: "Fix the audio-coupled haptics handling of system updates." bug: "372241975" metadata { purpose: PURPOSE_BUGFIX } } services/core/java/com/android/server/vibrator/VibratorManagerService.java +26 −12 Original line number Diff line number Diff line Loading @@ -1015,9 +1015,12 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { updateAlwaysOnLocked(mAlwaysOnEffects.valueAt(i)); } // TODO(b/372241975): investigate why external vibrations were not handled here before if (mCurrentSession == null || (mCurrentSession instanceof ExternalVibrationSession)) { if (mCurrentSession == null) { return; } if (!Flags.fixExternalVibrationSystemUpdateAware() && (mCurrentSession instanceof ExternalVibrationSession)) { return; } Loading @@ -1025,7 +1028,7 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { if (inputDevicesChanged || (ignoreStatus != null)) { if (DEBUG) { Slog.d(TAG, "Canceling vibration because settings changed: " + (inputDevicesChanged ? "input devices changed" : ignoreStatus)); + (ignoreStatus == null ? "input devices changed" : ignoreStatus)); } mCurrentSession.requestEnd(Status.CANCELLED_BY_SETTINGS_UPDATE); } Loading Loading @@ -2334,7 +2337,14 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { @GuardedBy("mLock") private void maybeClearCurrentAndNextSessionsLocked( Predicate<VibrationSession> shouldEndSessionPredicate, Status endStatus) { // TODO(b/372241975): investigate why external vibrations were not handled here before if (Flags.fixExternalVibrationSystemUpdateAware()) { if (shouldEndSessionPredicate.test(mNextSession)) { clearNextSessionLocked(endStatus); } if (shouldEndSessionPredicate.test(mCurrentSession)) { mCurrentSession.requestEnd(endStatus); } } else { if (!(mNextSession instanceof ExternalVibrationSession) && shouldEndSessionPredicate.test(mNextSession)) { clearNextSessionLocked(endStatus); Loading @@ -2344,6 +2354,7 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { mCurrentSession.requestEnd(endStatus); } } } /** * Waits until the current vibration finished processing, timing out after the given Loading Loading @@ -2535,6 +2546,9 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { Slog.d(TAG, "Stopping external vibration: " + vib); } mCurrentSession.requestEnd(Status.FINISHED); } else if (Build.IS_DEBUGGABLE) { Slog.wtf(TAG, "VibrationSession invalid on external vibration stop." + " currentSession=" + mCurrentSession + ", received=" + vib); } } } finally { Loading services/tests/vibrator/src/com/android/server/vibrator/VibratorManagerServiceTest.java +127 −6 Original line number Diff line number Diff line Loading @@ -147,6 +147,9 @@ public class VibratorManagerServiceTest { new AudioAttributes.Builder().setUsage(AudioAttributes.USAGE_ALARM).build(); private static final AudioAttributes AUDIO_NOTIFICATION_ATTRS = new AudioAttributes.Builder().setUsage(AudioAttributes.USAGE_NOTIFICATION).build(); private static final AudioAttributes AUDIO_HAPTIC_FEEDBACK_ATTRS = new AudioAttributes.Builder().setUsage( AudioAttributes.USAGE_ASSISTANCE_SONIFICATION).build(); private static final VibrationAttributes ALARM_ATTRS = new VibrationAttributes.Builder().setUsage(VibrationAttributes.USAGE_ALARM).build(); private static final VibrationAttributes HAPTIC_FEEDBACK_ATTRS = Loading Loading @@ -2674,7 +2677,8 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenDeniedAppOps_doNotCancelVibration() throws Throwable { @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyDeniedAppOps_doNotCancelVibration() throws Throwable { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2697,10 +2701,11 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenPowerModeChanges_doNotCancelVibration() throws Exception { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenDeniedAppOps_cancelVibration() throws Throwable { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); Loading @@ -2711,13 +2716,59 @@ public class VibratorManagerServiceTest { assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); when(mAppOpsManagerMock.checkAudioOpNoThrow(eq(AppOpsManager.OP_VIBRATE), eq(AudioAttributes.USAGE_ALARM), anyInt(), anyString())) .thenReturn(AppOpsManager.MODE_IGNORED); service.mAppOpsChangeListener.onOpChanged(AppOpsManager.OP_VIBRATE, null); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyPowerModeChanges_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_HAPTIC_FEEDBACK_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); mRegisteredPowerModeListener.onLowPowerModeChanged(LOW_POWER_STATE); verify(externalVibrationControllerMock, never()).mute(); } @Test public void onExternalVibration_thenSettingsChange_doNotCancelVibration() throws Exception { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenPowerModeChanges_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_HAPTIC_FEEDBACK_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); mRegisteredPowerModeListener.onLowPowerModeChanged(LOW_POWER_STATE); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacySettingsChange_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2739,7 +2790,31 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenScreenTurnsOff_doNotCancelVibration() throws Throwable { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenSettingsChange_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); setUserSetting(Settings.System.ALARM_VIBRATION_INTENSITY, Vibrator.VIBRATION_INTENSITY_OFF); service.mVibrationSettings.mSettingObserver.onChange(false); service.updateServiceState(); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyScreenTurnsOff_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2759,7 +2834,30 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenFgUserRequestsMute_doNotCancelVibration() throws Throwable { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenScreenTurnsOff_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); service.mIntentReceiver.onReceive(mContextSpy, new Intent(Intent.ACTION_SCREEN_OFF)); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyFgUserRequestsMute_doNotCancelVibration() throws Exception { assumeTrue(UserManagerInternal.shouldShowNotificationForBackgroundUserSounds()); mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); Loading @@ -2780,6 +2878,29 @@ public class VibratorManagerServiceTest { verify(externalVibrationControllerMock, never()).mute(); } @Test @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenFgUserRequestsMute_cancelVibration() throws Exception { assumeTrue(UserManagerInternal.shouldShowNotificationForBackgroundUserSounds()); mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); service.mIntentReceiver.onReceive(mContextSpy, new Intent( BackgroundUserSoundNotifier.ACTION_MUTE_SOUND)); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_VENDOR_VIBRATION_EFFECTS) public void startVibrationSession_withoutFeatureFlag_throwsException() throws Exception { Loading Loading
core/java/android/os/vibrator/flags.aconfig +10 −0 Original line number Diff line number Diff line Loading @@ -155,3 +155,13 @@ flag { purpose: PURPOSE_BUGFIX } } flag { namespace: "haptics" name: "fix_external_vibration_system_update_aware" description: "Fix the audio-coupled haptics handling of system updates." bug: "372241975" metadata { purpose: PURPOSE_BUGFIX } }
services/core/java/com/android/server/vibrator/VibratorManagerService.java +26 −12 Original line number Diff line number Diff line Loading @@ -1015,9 +1015,12 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { updateAlwaysOnLocked(mAlwaysOnEffects.valueAt(i)); } // TODO(b/372241975): investigate why external vibrations were not handled here before if (mCurrentSession == null || (mCurrentSession instanceof ExternalVibrationSession)) { if (mCurrentSession == null) { return; } if (!Flags.fixExternalVibrationSystemUpdateAware() && (mCurrentSession instanceof ExternalVibrationSession)) { return; } Loading @@ -1025,7 +1028,7 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { if (inputDevicesChanged || (ignoreStatus != null)) { if (DEBUG) { Slog.d(TAG, "Canceling vibration because settings changed: " + (inputDevicesChanged ? "input devices changed" : ignoreStatus)); + (ignoreStatus == null ? "input devices changed" : ignoreStatus)); } mCurrentSession.requestEnd(Status.CANCELLED_BY_SETTINGS_UPDATE); } Loading Loading @@ -2334,7 +2337,14 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { @GuardedBy("mLock") private void maybeClearCurrentAndNextSessionsLocked( Predicate<VibrationSession> shouldEndSessionPredicate, Status endStatus) { // TODO(b/372241975): investigate why external vibrations were not handled here before if (Flags.fixExternalVibrationSystemUpdateAware()) { if (shouldEndSessionPredicate.test(mNextSession)) { clearNextSessionLocked(endStatus); } if (shouldEndSessionPredicate.test(mCurrentSession)) { mCurrentSession.requestEnd(endStatus); } } else { if (!(mNextSession instanceof ExternalVibrationSession) && shouldEndSessionPredicate.test(mNextSession)) { clearNextSessionLocked(endStatus); Loading @@ -2344,6 +2354,7 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { mCurrentSession.requestEnd(endStatus); } } } /** * Waits until the current vibration finished processing, timing out after the given Loading Loading @@ -2535,6 +2546,9 @@ public class VibratorManagerService extends IVibratorManagerService.Stub { Slog.d(TAG, "Stopping external vibration: " + vib); } mCurrentSession.requestEnd(Status.FINISHED); } else if (Build.IS_DEBUGGABLE) { Slog.wtf(TAG, "VibrationSession invalid on external vibration stop." + " currentSession=" + mCurrentSession + ", received=" + vib); } } } finally { Loading
services/tests/vibrator/src/com/android/server/vibrator/VibratorManagerServiceTest.java +127 −6 Original line number Diff line number Diff line Loading @@ -147,6 +147,9 @@ public class VibratorManagerServiceTest { new AudioAttributes.Builder().setUsage(AudioAttributes.USAGE_ALARM).build(); private static final AudioAttributes AUDIO_NOTIFICATION_ATTRS = new AudioAttributes.Builder().setUsage(AudioAttributes.USAGE_NOTIFICATION).build(); private static final AudioAttributes AUDIO_HAPTIC_FEEDBACK_ATTRS = new AudioAttributes.Builder().setUsage( AudioAttributes.USAGE_ASSISTANCE_SONIFICATION).build(); private static final VibrationAttributes ALARM_ATTRS = new VibrationAttributes.Builder().setUsage(VibrationAttributes.USAGE_ALARM).build(); private static final VibrationAttributes HAPTIC_FEEDBACK_ATTRS = Loading Loading @@ -2674,7 +2677,8 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenDeniedAppOps_doNotCancelVibration() throws Throwable { @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyDeniedAppOps_doNotCancelVibration() throws Throwable { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2697,10 +2701,11 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenPowerModeChanges_doNotCancelVibration() throws Exception { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenDeniedAppOps_cancelVibration() throws Throwable { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); Loading @@ -2711,13 +2716,59 @@ public class VibratorManagerServiceTest { assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); when(mAppOpsManagerMock.checkAudioOpNoThrow(eq(AppOpsManager.OP_VIBRATE), eq(AudioAttributes.USAGE_ALARM), anyInt(), anyString())) .thenReturn(AppOpsManager.MODE_IGNORED); service.mAppOpsChangeListener.onOpChanged(AppOpsManager.OP_VIBRATE, null); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyPowerModeChanges_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_HAPTIC_FEEDBACK_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); mRegisteredPowerModeListener.onLowPowerModeChanged(LOW_POWER_STATE); verify(externalVibrationControllerMock, never()).mute(); } @Test public void onExternalVibration_thenSettingsChange_doNotCancelVibration() throws Exception { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenPowerModeChanges_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_HAPTIC_FEEDBACK_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); mRegisteredPowerModeListener.onLowPowerModeChanged(LOW_POWER_STATE); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacySettingsChange_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2739,7 +2790,31 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenScreenTurnsOff_doNotCancelVibration() throws Throwable { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenSettingsChange_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); setUserSetting(Settings.System.ALARM_VIBRATION_INTENSITY, Vibrator.VIBRATION_INTENSITY_OFF); service.mVibrationSettings.mSettingObserver.onChange(false); service.updateServiceState(); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyScreenTurnsOff_doNotCancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); Loading @@ -2759,7 +2834,30 @@ public class VibratorManagerServiceTest { } @Test public void onExternalVibration_thenFgUserRequestsMute_doNotCancelVibration() throws Throwable { @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenScreenTurnsOff_cancelVibration() throws Exception { mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); service.mIntentReceiver.onReceive(mContextSpy, new Intent(Intent.ACTION_SCREEN_OFF)); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_legacyFgUserRequestsMute_doNotCancelVibration() throws Exception { assumeTrue(UserManagerInternal.shouldShowNotificationForBackgroundUserSounds()); mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); Loading @@ -2780,6 +2878,29 @@ public class VibratorManagerServiceTest { verify(externalVibrationControllerMock, never()).mute(); } @Test @EnableFlags(android.os.vibrator.Flags.FLAG_FIX_EXTERNAL_VIBRATION_SYSTEM_UPDATE_AWARE) public void onExternalVibration_thenFgUserRequestsMute_cancelVibration() throws Exception { assumeTrue(UserManagerInternal.shouldShowNotificationForBackgroundUserSounds()); mockVibrators(1); mVibratorProviders.get(1).setCapabilities(IVibrator.CAP_EXTERNAL_CONTROL); VibratorManagerService service = createSystemReadyService(); IExternalVibrationController externalVibrationControllerMock = mock(IExternalVibrationController.class); ExternalVibration externalVibration = new ExternalVibration(UID, PACKAGE_NAME, AUDIO_ALARM_ATTRS, externalVibrationControllerMock, mock(IBinder.class)); ExternalVibrationScale scale = mExternalVibratorService.onExternalVibrationStart( externalVibration); assertThat(scale.scaleLevel).isNotEqualTo(ExternalVibrationScale.ScaleLevel.SCALE_MUTE); service.mIntentReceiver.onReceive(mContextSpy, new Intent( BackgroundUserSoundNotifier.ACTION_MUTE_SOUND)); verify(externalVibrationControllerMock).mute(); } @Test @DisableFlags(android.os.vibrator.Flags.FLAG_VENDOR_VIBRATION_EFFECTS) public void startVibrationSession_withoutFeatureFlag_throwsException() throws Exception { Loading