From 29d526719ade4fc0f8ac69fac0e961f7fea35b25 Mon Sep 17 00:00:00 2001 From: Michael Wright Date: Wed, 24 Jan 2018 15:40:46 +0000 Subject: [PATCH] Add new touch and notification vibration intensity settings. Bug: 64185329 Test: ROBOTEST_FILTER=VibrationSettingsTest m -j RunSettingsRoboTests Change-Id: I449c7e0041aabfe48935a57cde93e8af77dcd783 --- res/values/strings.xml | 30 +++ ...bility_notification_vibration_settings.xml | 20 ++ res/xml/accessibility_settings.xml | 6 + ...accessibility_touch_vibration_settings.xml | 20 ++ res/xml/accessibility_vibration_settings.xml | 31 +++ .../accessibility/AccessibilitySettings.java | 35 +++- ...tificationVibrationPreferenceFragment.java | 51 +++++ .../TouchVibrationPreferenceFragment.java | 61 ++++++ .../VibrationPreferenceFragment.java | 193 ++++++++++++++++++ .../accessibility/VibrationSettings.java | 153 ++++++++++++++ .../search/SearchIndexableResourcesImpl.java | 2 + .../VibrationPreferenceFragmentTest.java | 138 +++++++++++++ 12 files changed, 739 insertions(+), 1 deletion(-) create mode 100644 res/xml/accessibility_notification_vibration_settings.xml create mode 100644 res/xml/accessibility_touch_vibration_settings.xml create mode 100644 res/xml/accessibility_vibration_settings.xml create mode 100644 src/com/android/settings/accessibility/NotificationVibrationPreferenceFragment.java create mode 100644 src/com/android/settings/accessibility/TouchVibrationPreferenceFragment.java create mode 100644 src/com/android/settings/accessibility/VibrationPreferenceFragment.java create mode 100644 src/com/android/settings/accessibility/VibrationSettings.java create mode 100644 tests/robotests/src/com/android/settings/accessibility/VibrationPreferenceFragmentTest.java diff --git a/res/values/strings.xml b/res/values/strings.xml index d7f54769a47..29224121aef 100644 --- a/res/values/strings.xml +++ b/res/values/strings.xml @@ -4431,6 +4431,12 @@ Click after pointer stops moving Delay before click + + Vibration + + Ring & notification vibration + + Touch vibration Use service @@ -4474,6 +4480,30 @@ Very long delay (%1$d ms) + + Ring & notification set to off + + + Ring & notification set to low + + + Ring & notification set to medium + + + Ring & notification set to high + + + Off + + + Low + + + Medium + + + High + Settings diff --git a/res/xml/accessibility_notification_vibration_settings.xml b/res/xml/accessibility_notification_vibration_settings.xml new file mode 100644 index 00000000000..b37d3636db1 --- /dev/null +++ b/res/xml/accessibility_notification_vibration_settings.xml @@ -0,0 +1,20 @@ + + + + diff --git a/res/xml/accessibility_settings.xml b/res/xml/accessibility_settings.xml index b5da848eb30..060868e37fc 100644 --- a/res/xml/accessibility_settings.xml +++ b/res/xml/accessibility_settings.xml @@ -93,6 +93,12 @@ android:entries="@array/long_press_timeout_selector_titles" android:entryValues="@array/long_press_timeout_selector_values" android:persistent="false"/> + + + + + + diff --git a/res/xml/accessibility_vibration_settings.xml b/res/xml/accessibility_vibration_settings.xml new file mode 100644 index 00000000000..d61454d0b46 --- /dev/null +++ b/res/xml/accessibility_vibration_settings.xml @@ -0,0 +1,31 @@ + + + + + + + + + diff --git a/src/com/android/settings/accessibility/AccessibilitySettings.java b/src/com/android/settings/accessibility/AccessibilitySettings.java index df8d4c8b4b3..7335baec401 100644 --- a/src/com/android/settings/accessibility/AccessibilitySettings.java +++ b/src/com/android/settings/accessibility/AccessibilitySettings.java @@ -16,6 +16,8 @@ package com.android.settings.accessibility; +import static android.os.Vibrator.VibrationIntensity; + import android.accessibilityservice.AccessibilityServiceInfo; import android.app.admin.DevicePolicyManager; import android.content.ComponentName; @@ -28,6 +30,7 @@ import android.net.Uri; import android.os.Bundle; import android.os.Handler; import android.os.UserHandle; +import android.os.Vibrator; import android.provider.SearchIndexableResource; import android.provider.Settings; import android.support.annotation.VisibleForTesting; @@ -111,6 +114,8 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements "tts_settings_preference"; private static final String AUTOCLICK_PREFERENCE_SCREEN = "autoclick_preference_screen"; + private static final String VIBRATION_PREFERENCE_SCREEN = + "vibration_preference_screen"; @VisibleForTesting static final String TOGGLE_INVERSION_PREFERENCE = "toggle_inversion_preference"; @@ -215,6 +220,7 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements private Preference mAutoclickPreferenceScreen; private Preference mAccessibilityShortcutPreferenceScreen; private Preference mDisplayDaltonizerPreferenceScreen; + private Preference mVibrationPreferenceScreen; private SwitchPreference mToggleInversionPreference; private int mLongPressTimeoutDefault; @@ -452,9 +458,11 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements // Display color adjustments. mDisplayDaltonizerPreferenceScreen = findPreference(DISPLAY_DALTONIZER_PREFERENCE_SCREEN); - // Accessibility shortcut + // Accessibility shortcut. mAccessibilityShortcutPreferenceScreen = findPreference(ACCESSIBILITY_SHORTCUT_PREFERENCE); + // Vibrations. + mVibrationPreferenceScreen = findPreference(VIBRATION_PREFERENCE_SCREEN); } private void updateAllPreferences() { @@ -661,6 +669,8 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements mSelectLongPressTimeoutPreference.setValue(value); mSelectLongPressTimeoutPreference.setSummary(mLongPressTimeoutValueToTitleMap.get(value)); + updateVibrationSummary(mVibrationPreferenceScreen); + updateFeatureSummary(Settings.Secure.ACCESSIBILITY_CAPTIONING_ENABLED, mCaptioningPreferenceScreen); updateFeatureSummary(Settings.Secure.ACCESSIBILITY_DISPLAY_DALTONIZER_ENABLED, @@ -726,6 +736,29 @@ public class AccessibilitySettings extends SettingsPreferenceFragment implements pref.setSummary(entries[index]); } + private void updateVibrationSummary(Preference pref) { + Vibrator vibrator = getContext().getSystemService(Vibrator.class); + final int intensity = Settings.System.getInt(getContext().getContentResolver(), + Settings.System.NOTIFICATION_VIBRATION_INTENSITY, + vibrator.getDefaultNotificationVibrationIntensity()); + mVibrationPreferenceScreen.setSummary(getVibrationSummary(getContext(), intensity)); + } + + private String getVibrationSummary(Context context, @VibrationIntensity int intensity) { + switch (intensity) { + case Vibrator.VIBRATION_INTENSITY_OFF: + return context.getString(R.string.accessibility_vibration_summary_off); + case Vibrator.VIBRATION_INTENSITY_LOW: + return context.getString(R.string.accessibility_vibration_summary_low); + case Vibrator.VIBRATION_INTENSITY_MEDIUM: + return context.getString(R.string.accessibility_vibration_summary_medium); + case Vibrator.VIBRATION_INTENSITY_HIGH: + return context.getString(R.string.accessibility_vibration_summary_high); + default: + return ""; + } + } + private void updateLockScreenRotationCheckbox() { Context context = getActivity(); if (context != null) { diff --git a/src/com/android/settings/accessibility/NotificationVibrationPreferenceFragment.java b/src/com/android/settings/accessibility/NotificationVibrationPreferenceFragment.java new file mode 100644 index 00000000000..6340bb1417e --- /dev/null +++ b/src/com/android/settings/accessibility/NotificationVibrationPreferenceFragment.java @@ -0,0 +1,51 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.settings.accessibility; + +import android.os.Vibrator; +import android.provider.Settings; + +import com.android.internal.logging.nano.MetricsProto.MetricsEvent; +import com.android.settings.R; + +/** + * Fragment for picking accessibility shortcut service + */ +public class NotificationVibrationPreferenceFragment extends VibrationPreferenceFragment { + @Override + public int getMetricsCategory() { + return MetricsEvent.ACCESSIBILITY_VIBRATION_NOTIFICATION; + } + + @Override + protected int getPreferenceScreenResId() { + return R.xml.accessibility_notification_vibration_settings; + } + + /** + * Get the setting string of the vibration intensity setting this preference is dealing with. + */ + @Override + protected String getVibrationIntensitySetting() { + return Settings.System.NOTIFICATION_VIBRATION_INTENSITY; + } + + @Override + protected int getDefaultVibrationIntensity() { + Vibrator vibrator = getContext().getSystemService(Vibrator.class); + return vibrator.getDefaultNotificationVibrationIntensity(); + } +} diff --git a/src/com/android/settings/accessibility/TouchVibrationPreferenceFragment.java b/src/com/android/settings/accessibility/TouchVibrationPreferenceFragment.java new file mode 100644 index 00000000000..ea36833db54 --- /dev/null +++ b/src/com/android/settings/accessibility/TouchVibrationPreferenceFragment.java @@ -0,0 +1,61 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.settings.accessibility; + +import android.graphics.drawable.Drawable; +import android.os.Vibrator; +import android.provider.Settings; + +import com.android.internal.logging.nano.MetricsProto.MetricsEvent; +import com.android.settings.R; + +/** + * Fragment for picking accessibility shortcut service + */ +public class TouchVibrationPreferenceFragment extends VibrationPreferenceFragment { + @Override + public int getMetricsCategory() { + return MetricsEvent.ACCESSIBILITY_VIBRATION_TOUCH; + } + + @Override + protected int getPreferenceScreenResId() { + return R.xml.accessibility_touch_vibration_settings; + } + + /** + * Get the setting string of the vibration intensity setting this preference is dealing with. + */ + @Override + protected String getVibrationIntensitySetting() { + return Settings.System.HAPTIC_FEEDBACK_INTENSITY; + } + + @Override + protected int getDefaultVibrationIntensity() { + Vibrator vibrator = getContext().getSystemService(Vibrator.class); + return vibrator.getDefaultHapticFeedbackIntensity(); + } + + @Override + public void onVibrationIntensitySelected(int intensity) { + // We want to keep HAPTIC_FEEDBACK_ENABLED consistent with this setting since some + // applications check it directly before triggering their own haptic feedback. + final boolean hapticFeedbackEnabled = !(intensity == Vibrator.VIBRATION_INTENSITY_OFF); + Settings.System.putInt(getContext().getContentResolver(), + Settings.System.HAPTIC_FEEDBACK_ENABLED, hapticFeedbackEnabled ? 1 : 0); + } +} diff --git a/src/com/android/settings/accessibility/VibrationPreferenceFragment.java b/src/com/android/settings/accessibility/VibrationPreferenceFragment.java new file mode 100644 index 00000000000..f81208f3a5e --- /dev/null +++ b/src/com/android/settings/accessibility/VibrationPreferenceFragment.java @@ -0,0 +1,193 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package com.android.settings.accessibility; + +import static android.os.Vibrator.VibrationIntensity; + +import android.support.annotation.VisibleForTesting; +import android.content.Context; +import android.database.ContentObserver; +import android.graphics.drawable.Drawable; +import android.net.Uri; +import android.os.Handler; +import android.os.Vibrator; +import android.provider.Settings; +import android.util.ArrayMap; +import android.util.Log; + +import com.android.internal.accessibility.AccessibilityShortcutController; +import com.android.internal.logging.nano.MetricsProto.MetricsEvent; +import com.android.settings.R; +import com.android.settings.widget.RadioButtonPickerFragment; + +import java.util.ArrayList; +import java.util.Comparator; +import java.util.List; +import java.util.Map; + +/** + * Fragment for changing vibration settings. + */ +public abstract class VibrationPreferenceFragment extends RadioButtonPickerFragment { + private static final String TAG = "VibrationPreferenceFragment"; + + @VisibleForTesting + final static String KEY_INTENSITY_OFF = "intensity_off"; + @VisibleForTesting + final static String KEY_INTENSITY_LOW = "intensity_low"; + @VisibleForTesting + final static String KEY_INTENSITY_MEDIUM = "intensity_medium"; + @VisibleForTesting + final static String KEY_INTENSITY_HIGH = "intensity_high"; + + private final Map mCandidates; + private final SettingsObserver mSettingsObserver; + + public VibrationPreferenceFragment() { + mCandidates = new ArrayMap<>(); + mCandidates.put(KEY_INTENSITY_OFF, + new VibrationIntensityCandidateInfo(KEY_INTENSITY_OFF, + R.string.accessibility_vibration_intensity_off, + Vibrator.VIBRATION_INTENSITY_OFF)); + mCandidates.put(KEY_INTENSITY_LOW, + new VibrationIntensityCandidateInfo(KEY_INTENSITY_LOW, + R.string.accessibility_vibration_intensity_low, + Vibrator.VIBRATION_INTENSITY_LOW)); + mCandidates.put(KEY_INTENSITY_MEDIUM, + new VibrationIntensityCandidateInfo(KEY_INTENSITY_MEDIUM, + R.string.accessibility_vibration_intensity_medium, + Vibrator.VIBRATION_INTENSITY_MEDIUM)); + mCandidates.put(KEY_INTENSITY_HIGH, + new VibrationIntensityCandidateInfo(KEY_INTENSITY_HIGH, + R.string.accessibility_vibration_intensity_high, + Vibrator.VIBRATION_INTENSITY_HIGH)); + mSettingsObserver = new SettingsObserver(); + } + + @Override + public void onAttach(Context context) { + super.onAttach(context); + mSettingsObserver.register(); + } + + @Override + public void onDetach() { + super.onDetach(); + mSettingsObserver.unregister(); + } + + /** + * Get the setting string of the vibration intensity setting this preference is dealing with. + */ + protected abstract String getVibrationIntensitySetting(); + + /** + * Get the default intensity for the desired setting. + */ + protected abstract int getDefaultVibrationIntensity(); + + /** + * When a new vibration intensity is selected by the user. + */ + protected void onVibrationIntensitySelected(int intensity) { } + + @Override + protected List getCandidates() { + List candidates = new ArrayList<>(mCandidates.values()); + candidates.sort( + Comparator.comparing(VibrationIntensityCandidateInfo::getIntensity).reversed()); + return candidates; + } + + @Override + protected String getDefaultKey() { + final int vibrationIntensity = Settings.System.getInt(getContext().getContentResolver(), + getVibrationIntensitySetting(), getDefaultVibrationIntensity()); + for (VibrationIntensityCandidateInfo candidate : mCandidates.values()) { + if (candidate.getIntensity() == vibrationIntensity) { + return candidate.getKey(); + } + } + return null; + } + + @Override + protected boolean setDefaultKey(String key) { + VibrationIntensityCandidateInfo candidate = mCandidates.get(key); + if (candidate == null) { + Log.e(TAG, "Tried to set unknown intensity (key=" + key + ")!"); + return false; + } + Settings.System.putInt(getContext().getContentResolver(), + getVibrationIntensitySetting(), candidate.getIntensity()); + onVibrationIntensitySelected(candidate.getIntensity()); + return true; + } + + @VisibleForTesting + class VibrationIntensityCandidateInfo extends CandidateInfo { + private String mKey; + private int mLabelId; + @VibrationIntensity + private int mIntensity; + + public VibrationIntensityCandidateInfo(String key, int labelId, int intensity) { + super(true /* enabled */); + mKey = key; + mLabelId = labelId; + mIntensity = intensity; + } + + @Override + public CharSequence loadLabel() { + return getContext().getString(mLabelId); + } + + @Override + public Drawable loadIcon() { + return null; + } + + @Override + public String getKey() { + return mKey; + } + + public int getIntensity() { + return mIntensity; + } + } + + private class SettingsObserver extends ContentObserver { + public SettingsObserver() { + super(new Handler()); + } + + public void register() { + getContext().getContentResolver().registerContentObserver( + Settings.System.getUriFor(getVibrationIntensitySetting()), false, this); + } + + public void unregister() { + getContext().getContentResolver().unregisterContentObserver(this); + } + + @Override + public void onChange(boolean selfChange, Uri uri) { + updateCandidates(); + } + } +} diff --git a/src/com/android/settings/accessibility/VibrationSettings.java b/src/com/android/settings/accessibility/VibrationSettings.java new file mode 100644 index 00000000000..8aa45136831 --- /dev/null +++ b/src/com/android/settings/accessibility/VibrationSettings.java @@ -0,0 +1,153 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.accessibility; + +import android.content.Context; +import android.net.Uri; +import android.os.Bundle; +import android.os.Handler; +import android.os.Vibrator; +import android.provider.SearchIndexableResource; +import android.provider.Settings; +import android.support.annotation.VisibleForTesting; +import android.support.v7.preference.Preference; + +import com.android.internal.logging.nano.MetricsProto.MetricsEvent; +import com.android.settings.R; +import com.android.settings.SettingsPreferenceFragment; +import com.android.settings.search.BaseSearchIndexProvider; +import com.android.settings.search.Indexable; + +import java.util.ArrayList; +import java.util.List; + +/** + * Activity with the accessibility settings. + */ +public class VibrationSettings extends SettingsPreferenceFragment implements Indexable { + + // Preferences + @VisibleForTesting + static final String NOTIFICATION_VIBRATION_PREFERENCE_SCREEN = + "notification_vibration_preference_screen"; + @VisibleForTesting + static final String TOUCH_VIBRATION_PREFERENCE_SCREEN = + "touch_vibration_preference_screen"; + + private final Handler mHandler = new Handler(); + private final SettingsContentObserver mSettingsContentObserver; + + private Preference mNotificationVibrationPreferenceScreen; + private Preference mTouchVibrationPreferenceScreen; + + public VibrationSettings() { + List vibrationSettings = new ArrayList<>(); + vibrationSettings.add(Settings.System.HAPTIC_FEEDBACK_INTENSITY); + vibrationSettings.add(Settings.System.NOTIFICATION_VIBRATION_INTENSITY); + mSettingsContentObserver = new SettingsContentObserver(mHandler, vibrationSettings) { + @Override + public void onChange(boolean selfChange, Uri uri) { + updatePreferences(); + } + }; + } + + @Override + public int getMetricsCategory() { + return MetricsEvent.ACCESSIBILITY_VIBRATION; + } + + @Override + public void onCreate(Bundle icicle) { + super.onCreate(icicle); + addPreferencesFromResource(R.xml.accessibility_vibration_settings); + initializePreferences(); + } + + @Override + public void onResume() { + super.onResume(); + updatePreferences(); + mSettingsContentObserver.register(getContentResolver()); + } + + @Override + public void onPause() { + mSettingsContentObserver.unregister(getContentResolver()); + super.onPause(); + } + + private void initializePreferences() { + // Notification and notification vibration strength adjustments. + mNotificationVibrationPreferenceScreen = + findPreference(NOTIFICATION_VIBRATION_PREFERENCE_SCREEN); + + // Touch feedback strength adjustments. + mTouchVibrationPreferenceScreen = findPreference(TOUCH_VIBRATION_PREFERENCE_SCREEN); + } + + private void updatePreferences() { + updateNotificationVibrationSummary(mNotificationVibrationPreferenceScreen); + updateTouchVibrationSummary(mTouchVibrationPreferenceScreen); + } + + private void updateNotificationVibrationSummary(Preference pref) { + Vibrator vibrator = getContext().getSystemService(Vibrator.class); + final int intensity = Settings.System.getInt(getContext().getContentResolver(), + Settings.System.NOTIFICATION_VIBRATION_INTENSITY, + vibrator.getDefaultNotificationVibrationIntensity()); + CharSequence summary = getVibrationIntensitySummary(getContext(), intensity); + mNotificationVibrationPreferenceScreen.setSummary(summary); + } + + private void updateTouchVibrationSummary(Preference pref) { + Vibrator vibrator = getContext().getSystemService(Vibrator.class); + final int intensity = Settings.System.getInt(getContext().getContentResolver(), + Settings.System.HAPTIC_FEEDBACK_INTENSITY, + vibrator.getDefaultHapticFeedbackIntensity()); + CharSequence summary = getVibrationIntensitySummary(getContext(), intensity); + mTouchVibrationPreferenceScreen.setSummary(summary); + } + + public static String getVibrationIntensitySummary(Context context, int intensity) { + switch (intensity) { + case Vibrator.VIBRATION_INTENSITY_OFF: + return context.getString(R.string.accessibility_vibration_intensity_off); + case Vibrator.VIBRATION_INTENSITY_LOW: + return context.getString(R.string.accessibility_vibration_intensity_low); + case Vibrator.VIBRATION_INTENSITY_MEDIUM: + return context.getString(R.string.accessibility_vibration_intensity_medium); + case Vibrator.VIBRATION_INTENSITY_HIGH: + return context.getString(R.string.accessibility_vibration_intensity_high); + default: + return ""; + } + } + + public static final SearchIndexProvider SEARCH_INDEX_DATA_PROVIDER = + new BaseSearchIndexProvider() { + @Override + public List getXmlResourcesToIndex(Context context, + boolean enabled) { + List indexables = new ArrayList<>(); + SearchIndexableResource indexable = new SearchIndexableResource(context); + indexable.xmlResId = R.xml.accessibility_vibration_settings; + indexables.add(indexable); + return indexables; + } + }; +} diff --git a/src/com/android/settings/search/SearchIndexableResourcesImpl.java b/src/com/android/settings/search/SearchIndexableResourcesImpl.java index 1edc2deab9b..bcf412c5554 100644 --- a/src/com/android/settings/search/SearchIndexableResourcesImpl.java +++ b/src/com/android/settings/search/SearchIndexableResourcesImpl.java @@ -26,6 +26,7 @@ import com.android.settings.deviceinfo.aboutphone.MyDeviceInfoFragment; import com.android.settings.accessibility.AccessibilitySettings; import com.android.settings.accessibility.AccessibilityShortcutPreferenceFragment; import com.android.settings.accessibility.MagnificationPreferenceFragment; +import com.android.settings.accessibility.VibrationSettings; import com.android.settings.accounts.AccountDashboardFragment; import com.android.settings.applications.AppAndNotificationDashboardFragment; import com.android.settings.applications.DefaultAppSettings; @@ -176,6 +177,7 @@ public class SearchIndexableResourcesImpl implements SearchIndexableResources { addIndex(NightDisplaySettings.class); addIndex(SmartBatterySettings.class); addIndex(MyDeviceInfoFragment.class); + addIndex(VibrationSettings.class); } @Override diff --git a/tests/robotests/src/com/android/settings/accessibility/VibrationPreferenceFragmentTest.java b/tests/robotests/src/com/android/settings/accessibility/VibrationPreferenceFragmentTest.java new file mode 100644 index 00000000000..f6a5a8231b7 --- /dev/null +++ b/tests/robotests/src/com/android/settings/accessibility/VibrationPreferenceFragmentTest.java @@ -0,0 +1,138 @@ +/* + * Copyright (C) 2018 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.accessibility; + +import static com.android.settings.accessibility.VibrationPreferenceFragment.KEY_INTENSITY_OFF; +import static com.android.settings.accessibility.VibrationPreferenceFragment.KEY_INTENSITY_LOW; +import static com.android.settings.accessibility.VibrationPreferenceFragment.KEY_INTENSITY_MEDIUM; +import static com.android.settings.accessibility.VibrationPreferenceFragment.KEY_INTENSITY_HIGH; +import static com.google.common.truth.Truth.assertThat; +import static org.mockito.Mockito.doReturn; +import static org.mockito.Mockito.spy; +import static org.mockito.Mockito.when; + +import android.app.Activity; +import android.content.Context; +import android.os.UserManager; +import android.os.Vibrator; +import android.provider.Settings; + +import com.android.settings.TestConfig; +import com.android.settings.accessibility.VibrationPreferenceFragment.VibrationIntensityCandidateInfo; +import com.android.settings.testutils.FakeFeatureFactory; +import com.android.settings.testutils.SettingsRobolectricTestRunner; +import com.android.settings.widget.RadioButtonPickerFragment.CandidateInfo; + +import org.junit.Before; +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.Answers; +import org.mockito.Mock; +import org.mockito.MockitoAnnotations; +import org.robolectric.RuntimeEnvironment; +import org.robolectric.annotation.Config; + +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +@RunWith(SettingsRobolectricTestRunner.class) +@Config(manifest = TestConfig.MANIFEST_PATH, sdk = TestConfig.SDK_VERSION) +public class VibrationPreferenceFragmentTest { + public static final Map INTENSITY_TO_KEY = new HashMap<>(); + + @Mock(answer = Answers.RETURNS_DEEP_STUBS) + private Activity mActivity; + @Mock + private UserManager mUserManager; + + private Context mContext; + private TestVibrationPreferenceFragment mFragment; + + static { + INTENSITY_TO_KEY.put(Vibrator.VIBRATION_INTENSITY_OFF, KEY_INTENSITY_OFF); + INTENSITY_TO_KEY.put(Vibrator.VIBRATION_INTENSITY_LOW, KEY_INTENSITY_LOW); + INTENSITY_TO_KEY.put(Vibrator.VIBRATION_INTENSITY_MEDIUM, KEY_INTENSITY_MEDIUM); + INTENSITY_TO_KEY.put(Vibrator.VIBRATION_INTENSITY_HIGH, KEY_INTENSITY_HIGH); + } + + @Before + public void setUp() { + MockitoAnnotations.initMocks(this); + FakeFeatureFactory.setupForTest(); + + mContext = RuntimeEnvironment.application; + + mFragment = spy(new TestVibrationPreferenceFragment()); + doReturn(mUserManager).when(mActivity).getSystemService(Context.USER_SERVICE); + doReturn(mContext).when(mFragment).getContext(); + mFragment.onAttach(mActivity); + } + + @Test + public void changeIntensitySetting_shouldResultInCorrespondingKey() { + for (Map.Entry entry : INTENSITY_TO_KEY.entrySet()) { + Settings.System.putInt(mContext.getContentResolver(), + Settings.System.HAPTIC_FEEDBACK_INTENSITY, entry.getKey()); + assertThat(mFragment.getDefaultKey()).isEqualTo(entry.getValue()); + } + } + + @Test + public void initialDefaultKey_shouldBeMedium() { + assertThat(mFragment.getDefaultKey()).isEqualTo(KEY_INTENSITY_MEDIUM); + } + + @Test + public void candidates_shouldBeSortedByIntensity() { + final List candidates = mFragment.getCandidates(); + assertThat(candidates.size()).isEqualTo(INTENSITY_TO_KEY.size()); + VibrationIntensityCandidateInfo prevCandidate = + (VibrationIntensityCandidateInfo) candidates.get(0); + for (int i = 1; i < candidates.size(); i++) { + VibrationIntensityCandidateInfo candidate = + (VibrationIntensityCandidateInfo) candidates.get(i); + assertThat(candidate.getIntensity()).isLessThan(prevCandidate.getIntensity()); + } + } + + private class TestVibrationPreferenceFragment extends VibrationPreferenceFragment { + @Override + protected int getPreferenceScreenResId() { + return 0; + } + + @Override + public int getMetricsCategory() { + return 0; + } + + /** + * Get the setting string of the vibration intensity setting this preference is dealing with. + */ + @Override + protected String getVibrationIntensitySetting() { + return Settings.System.HAPTIC_FEEDBACK_INTENSITY; + } + + @Override + protected int getDefaultVibrationIntensity() { + return Vibrator.VIBRATION_INTENSITY_MEDIUM; + } + } +} +