Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5d772136 authored by joeshih's avatar joeshih
Browse files

Support Vibrate for calls in Settings Slices

Use TogglePreferenceController instead of AbstractPreferenceController
for VibrateWhenRingPreferenceControllr

Bug:74915140
Test: make RunSettingsRoboTests
Change-Id: I501a1470da7dc1ff582c2a90b5235b25036caefc
parent 1ae09fe2
Loading
Loading
Loading
Loading
+7 −5
Original line number Diff line number Diff line
@@ -64,11 +64,6 @@
        settings:controller="com.android.settings.notification.RingVolumePreferenceController"
        settings:allowDividerAbove="true"/>

    <!-- Also vibrate for calls -->
    <SwitchPreference
        android:key="vibrate_when_ringing"
        android:title="@string/vibrate_when_ringing_title"
        android:order="-155"/>

    <!-- Alarm volume -->
    <com.android.settings.notification.VolumeSeekBarPreference
@@ -87,6 +82,13 @@
        android:order="-140"
        settings:controller="com.android.settings.notification.NotificationVolumePreferenceController"/>

    <!-- Also vibrate for calls -->
    <SwitchPreference
        android:key="vibrate_when_ringing"
        android:title="@string/vibrate_when_ringing_title"
        settings:controller="com.android.settings.notification.VibrateWhenRingPreferenceController"
        android:order="-130"/>

    <!-- Interruptions -->
    <com.android.settingslib.RestrictedPreference
        android:key="zen_mode"
+0 −2
Original line number Diff line number Diff line
@@ -50,7 +50,6 @@ public class SoundSettings extends DashboardFragment {
    private static final String SELECTED_PREFERENCE_KEY = "selected_preference";
    private static final int REQUEST_CODE = 200;
    private static final String KEY_ZEN_MODE = "zen_mode";

    private static final int SAMPLE_CUTOFF = 2000;  // manually cap sample playback at 2 seconds

    @VisibleForTesting
@@ -197,7 +196,6 @@ public class SoundSettings extends DashboardFragment {
            SoundSettings fragment, Lifecycle lifecycle) {
        final List<AbstractPreferenceController> controllers = new ArrayList<>();
        controllers.add(new ZenModePreferenceController(context, lifecycle, KEY_ZEN_MODE));
        controllers.add(new VibrateWhenRingPreferenceController(context));

        // Volumes are added via xml

+28 −40
Original line number Diff line number Diff line
@@ -16,6 +16,8 @@

package com.android.settings.notification;

import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;

import android.content.ContentResolver;
import android.content.Context;
import android.database.ContentObserver;
@@ -24,26 +26,41 @@ import android.os.Handler;
import android.provider.Settings;
import androidx.preference.Preference;
import androidx.preference.PreferenceScreen;
import androidx.preference.TwoStatePreference;

import com.android.settings.Utils;
import com.android.settings.core.PreferenceControllerMixin;
import com.android.settingslib.core.AbstractPreferenceController;
import com.android.settings.core.TogglePreferenceController;
import com.android.settingslib.core.lifecycle.LifecycleObserver;
import com.android.settingslib.core.lifecycle.events.OnPause;
import com.android.settingslib.core.lifecycle.events.OnResume;

import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;

public class VibrateWhenRingPreferenceController extends AbstractPreferenceController
        implements PreferenceControllerMixin, Preference.OnPreferenceChangeListener,
        LifecycleObserver, OnResume, OnPause {
public class VibrateWhenRingPreferenceController extends TogglePreferenceController
        implements LifecycleObserver, OnResume, OnPause {

    private static final String KEY_VIBRATE_WHEN_RINGING = "vibrate_when_ringing";
    private final int DEFAULT_VALUE = 0;
    private final int NOTIFICATION_VIBRATE_WHEN_RINGING = 1;
    private SettingObserver mSettingObserver;

    public VibrateWhenRingPreferenceController(Context context) {
        super(context);
    public VibrateWhenRingPreferenceController(Context context, String key) {
        super(context, key);
    }

    @Override
    public boolean isChecked() {
        return Settings.System.getInt(mContext.getContentResolver(),
                VIBRATE_WHEN_RINGING, DEFAULT_VALUE) != DEFAULT_VALUE;
    }

    @Override
    public boolean setChecked(boolean isChecked) {
        return Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
                isChecked ? NOTIFICATION_VIBRATE_WHEN_RINGING : DEFAULT_VALUE);
    }

    @Override
    @AvailabilityStatus
    public int getAvailabilityStatus() {
        return Utils.isVoiceCapable(mContext) ? AVAILABLE : UNSUPPORTED_ON_DEVICE;
    }

    @Override
@@ -70,34 +87,6 @@ public class VibrateWhenRingPreferenceController extends AbstractPreferenceContr
        }
    }

    @Override
    public boolean handlePreferenceTreeClick(Preference preference) {
        return false;
    }

    @Override
    public String getPreferenceKey() {
        return KEY_VIBRATE_WHEN_RINGING;
    }

    @Override
    public boolean isAvailable() {
        return Utils.isVoiceCapable(mContext);
    }

    @Override
    public void updateState(Preference preference) {
        ((TwoStatePreference) preference).setChecked(
            Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 0) != 0);
    }

    @Override
    public boolean onPreferenceChange(Preference preference, Object newValue) {
        final boolean val = (Boolean) newValue;
        return Settings.System.putInt(mContext.getContentResolver(),
            VIBRATE_WHEN_RINGING, val ? 1 : 0);
    }

    private final class SettingObserver extends ContentObserver {

        private final Uri VIBRATE_WHEN_RINGING_URI =
@@ -127,5 +116,4 @@ public class VibrateWhenRingPreferenceController extends AbstractPreferenceContr
            }
        }
    }

}
+94 −13
Original line number Diff line number Diff line
@@ -17,11 +17,17 @@
package com.android.settings.notification;

import static android.provider.Settings.System.VIBRATE_WHEN_RINGING;

import static com.android.settings.core.BasePreferenceController.AVAILABLE;
import static com.android.settings.core.BasePreferenceController.UNSUPPORTED_ON_DEVICE;

import static com.google.common.truth.Truth.assertThat;

import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.when;

import android.content.ContentResolver;
import android.content.Context;
import android.provider.Settings;
import androidx.preference.Preference;
@@ -37,26 +43,32 @@ import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
import org.robolectric.RuntimeEnvironment;
import org.robolectric.shadow.api.Shadow;
import org.robolectric.shadows.ShadowContentResolver;

@RunWith(SettingsRobolectricTestRunner.class)
public class VibrateWhenRingPreferenceControllerTest {

    @Mock
    private static final String KEY_VIBRATE_WHEN_RINGING = "vibrate_when_ringing";
    private final int DEFAULT_VALUE = 0;
    private final int NOTIFICATION_VIBRATE_WHEN_RINGING = 1;
    private Context mContext;
    private ContentResolver mContentResolver;
    @Mock
    private PreferenceScreen mScreen;
    @Mock
    private TelephonyManager mTelephonyManager;

    private VibrateWhenRingPreferenceController mController;
    private Preference mPreference;

    @Before
    public void setUp() {
        MockitoAnnotations.initMocks(this);
        mContext = spy(RuntimeEnvironment.application);
        mContentResolver = mContext.getContentResolver();
        when(mContext.getSystemService(Context.TELEPHONY_SERVICE)).thenReturn(mTelephonyManager);
        mController = new VibrateWhenRingPreferenceController(mContext);
        mPreference = new Preference(RuntimeEnvironment.application);
        mController = new VibrateWhenRingPreferenceController(mContext, KEY_VIBRATE_WHEN_RINGING);
        mPreference = new Preference(mContext);
        mPreference.setKey(mController.getPreferenceKey());
        when(mScreen.findPreference(mPreference.getKey())).thenReturn(mPreference);
    }
@@ -79,27 +91,96 @@ public class VibrateWhenRingPreferenceControllerTest {
        assertThat(mPreference.isVisible()).isFalse();
    }

    @Test
    public void testOnPreferenceChange_turnOn_returnOn() {
        mController.onPreferenceChange(null, true);
        final int mode = Settings.System.getInt(mContext.getContentResolver(),
                VIBRATE_WHEN_RINGING, DEFAULT_VALUE);

        assertThat(mode).isEqualTo(NOTIFICATION_VIBRATE_WHEN_RINGING);
    }

    @Test
    public void testOnPreferenceChange_turnOff_returnOff() {
        mController.onPreferenceChange(null, false);
        final int mode = Settings.System.getInt(mContext.getContentResolver(),
                VIBRATE_WHEN_RINGING, DEFAULT_VALUE);

        assertThat(mode).isEqualTo(DEFAULT_VALUE);
    }

    @Test
    public void voiceCapable_availabled() {
        when(mTelephonyManager.isVoiceCapable()).thenReturn(true);

        assertThat(mController.getAvailabilityStatus()).isEqualTo(AVAILABLE);
    }

    @Test
    public void voiceCapable_notAvailabled() {
        when(mTelephonyManager.isVoiceCapable()).thenReturn(false);

        assertThat(mController.getAvailabilityStatus()).isEqualTo(UNSUPPORTED_ON_DEVICE);
    }

    @Test
    public void updateState_settingIsOn_preferenceShouldBeChecked() {
        final TwoStatePreference preference = mock(TwoStatePreference.class);
        final Context context = RuntimeEnvironment.application;
        Settings.System.putInt(context.getContentResolver(), VIBRATE_WHEN_RINGING, 1);
        Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 1);

        mController = new VibrateWhenRingPreferenceController(context);
        mController.updateState(preference);

        verify(preference).setChecked(true);
        assertThat(mController.isChecked()).isTrue();
    }

    @Test
    public void updateState_settingIsOff_preferenceShouldNotBeChecked() {
        final TwoStatePreference preference = mock(TwoStatePreference.class);
        final Context context = RuntimeEnvironment.application;
        Settings.System.putInt(context.getContentResolver(), VIBRATE_WHEN_RINGING, 0);
        Settings.System.putInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING, 0);

        mController = new VibrateWhenRingPreferenceController(context);
        mController.updateState(preference);

        verify(preference).setChecked(false);
        assertThat(mController.isChecked()).isFalse();
    }

    @Test
    public void setChecked_settingsIsOn() {
        mController.setChecked(true);
        final int mode = Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
                -1);

        assertThat(mode).isEqualTo(NOTIFICATION_VIBRATE_WHEN_RINGING);
    }

    @Test
    public void setChecked_settingsIsOff() {
        mController.setChecked(false);
        final int mode = Settings.System.getInt(mContext.getContentResolver(), VIBRATE_WHEN_RINGING,
                -1);

        assertThat(mode).isEqualTo(DEFAULT_VALUE);
    }

    @Test
    public void testObserver_onResume_shouldRegisterObserver() {
        final ShadowContentResolver shadowContentResolver = Shadow.extract(mContentResolver);
        mController.displayPreference(mScreen);

        mController.onResume();

        assertThat(shadowContentResolver.getContentObservers(
                Settings.System.getUriFor(VIBRATE_WHEN_RINGING))).isNotEmpty();
    }

    @Test
    public void testObserver_onPause_shouldUnregisterObserver() {
        final ShadowContentResolver shadowContentResolver = Shadow.extract(mContentResolver);
        mController.displayPreference(mScreen);

        mController.onResume();
        mController.onPause();

        assertThat(shadowContentResolver.getContentObservers(
                Settings.System.getUriFor(VIBRATE_WHEN_RINGING))).isEmpty();
    }
}