Merge "[Settings] Present EID in About phone page"
diff --git a/res/drawable/ic_modifier_keys_reset.xml b/res/drawable/ic_modifier_keys_reset.xml
new file mode 100644
index 0000000..a8cc198
--- /dev/null
+++ b/res/drawable/ic_modifier_keys_reset.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    Copyright (C) 2022 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.
+-->
+
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+        xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
+        android:width="24.0dp"
+        android:height="24.0dp"
+        android:viewportWidth="24.0"
+        android:viewportHeight="24.0"
+        android:tint="?androidprv:attr/colorAccentPrimaryVariant">
+    <path
+        android:fillColor="@android:color/white"
+        android:pathData="M18,4C13.58,0.69 7.31,1.58 4,6V4H2v6h6V8H5.09c1.44,-2.47 4.09,-3.98 6.94,-3.97c4.42,0.02 7.99,3.61 7.97,8.03s-3.61,7.99 -8.03,7.97C7.55,20.01 3.98,16.42 4,12H2c0,3.15 1.48,6.11 4,8c4.42,3.31 10.69,2.42 14,-2C23.31,13.58 22.42,7.31 18,4z"/>
+</vector>
\ No newline at end of file
diff --git a/res/drawable/modifier_key_bordered.xml b/res/drawable/modifier_key_bordered.xml
new file mode 100644
index 0000000..17f0090
--- /dev/null
+++ b/res/drawable/modifier_key_bordered.xml
@@ -0,0 +1,32 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<inset
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:androidprv="http://schemas.android.com/apk/prv/res/android">
+    <ripple
+        android:color="?android:attr/colorControlHighlight">
+        <item>
+            <shape android:shape="rectangle">
+                <corners android:radius="24dp"  />
+                <solid android:color="@android:color/transparent"/>
+                <stroke
+                    android:width="1dp"
+                    android:color="?androidprv:attr/colorAccentPrimaryVariant"/>
+            </shape>
+        </item>
+    </ripple>
+</inset>
\ No newline at end of file
diff --git a/res/drawable/modifier_key_colored.xml b/res/drawable/modifier_key_colored.xml
new file mode 100644
index 0000000..2bb033b
--- /dev/null
+++ b/res/drawable/modifier_key_colored.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<inset
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:androidprv="http://schemas.android.com/apk/prv/res/android">
+    <ripple
+        android:color="?android:attr/colorControlHighlight">
+        <item>
+            <shape android:shape="rectangle">
+                <corners android:radius="24dp"/>
+                <solid android:color="?androidprv:attr/colorAccentPrimary"/>
+            </shape>
+        </item>
+    </ripple>
+</inset>
\ No newline at end of file
diff --git a/res/drawable/modifier_key_lisetview_background.xml b/res/drawable/modifier_key_lisetview_background.xml
new file mode 100644
index 0000000..b65c61e
--- /dev/null
+++ b/res/drawable/modifier_key_lisetview_background.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<inset
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:androidprv="http://schemas.android.com/apk/prv/res/android">
+    <ripple
+        android:color="?android:attr/colorControlHighlight">
+        <item>
+            <shape android:shape="rectangle">
+                <corners android:radius="24dp"/>
+                <solid android:color="?androidprv:attr/colorSurfaceVariant"/>
+            </shape>
+        </item>
+    </ripple>
+</inset>
\ No newline at end of file
diff --git a/res/layout/modifier_key_item.xml b/res/layout/modifier_key_item.xml
new file mode 100644
index 0000000..7bd344c
--- /dev/null
+++ b/res/layout/modifier_key_item.xml
@@ -0,0 +1,49 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<RelativeLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:layout_marginTop="8dip"
+    android:layout_marginBottom="8dip"
+    android:minHeight="?android:attr/listPreferredItemHeight"
+    android:paddingEnd="?android:attr/scrollbarSize"
+    android:layout_weight="1">
+
+    <ImageView
+        android:id="@+id/modifier_key_check_icon"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_centerVertical="true"
+        android:layout_alignParentStart="true"
+        android:layout_marginStart="24dip"
+        android:ellipsize="marquee"
+        android:fadingEdge="horizontal"
+        android:src="@drawable/ic_check_24dp"
+        android:tint="?androidprv:attr/colorAccentPrimaryVariant"/>
+
+    <TextView
+        android:id="@+id/modifier_key_text"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:layout_centerVertical="true"
+        android:textDirection="locale"
+        android:padding="16dp"
+        android:textAppearance="?android:attr/textAppearanceMedium"
+        android:layout_toEndOf="@+id/modifier_key_check_icon"
+        android:ellipsize="marquee"
+        android:fadingEdge="horizontal" />
+
+</RelativeLayout>
diff --git a/res/layout/modifier_key_picker_dialog.xml b/res/layout/modifier_key_picker_dialog.xml
new file mode 100644
index 0000000..8600348
--- /dev/null
+++ b/res/layout/modifier_key_picker_dialog.xml
@@ -0,0 +1,107 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+              xmlns:androidprv="http://schemas.android.com/apk/prv/res/android"
+              android:id="@+id/modifier_key_fragment_container"
+              android:orientation="vertical"
+              android:layout_width="match_parent"
+              android:layout_height="match_parent" >
+
+    <LinearLayout android:orientation="vertical"
+                  android:layout_width="match_parent"
+                  android:layout_height="match_parent"
+                  android:divider="?android:dividerHorizontal"
+                  android:showDividers="end" >
+        <TextView
+            android:id="@+id/modifier_key_picker_title"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="24dip"
+            android:layout_marginBottom="8dip"
+            android:layout_gravity="center_horizontal"
+            android:singleLine="true"
+            android:textAppearance="?android:attr/textAppearanceLarge"
+            android:textColor="?android:attr/textColorPrimary"
+            android:text="@string/modifier_keys_picker_title"/>
+
+        <TextView
+            android:id="@+id/modifier_key_picker_summary"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="8dip"
+            android:layout_marginBottom="16dip"
+            android:layout_gravity="center_horizontal"
+            android:singleLine="true"
+            android:textAppearance="?android:attr/textAppearanceSmall"
+            android:textColor="?android:attr/textColorSecondary"/>
+    </LinearLayout>
+
+    <LinearLayout android:orientation="vertical"
+                  android:layout_width="match_parent"
+                  android:layout_height="match_parent"
+                  android:divider="?android:dividerHorizontal"
+                  android:showDividers="end">
+        <ListView
+            android:id="@+id/modifier_key_picker"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:divider="@null"
+            android:dividerHeight="8dp"
+            android:padding="16dip"
+            android:listSelector="@drawable/modifier_key_lisetview_background"
+        />
+    </LinearLayout>
+
+    <RelativeLayout
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginStart="8dip"
+        android:layout_marginEnd="8dip"
+        android:layout_marginTop="6dip"
+        android:layout_marginBottom="6dip"
+        android:layout_weight="1">
+
+        <Button
+            android:id="@+id/modifier_key_cancel_button"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="6dip"
+            android:layout_marginBottom="6dip"
+            android:layout_marginStart="8dip"
+            android:layout_alignParentStart="true"
+            android:paddingVertical="14dp"
+            android:drawablePadding="9dp"
+            style="@style/ModifierKeyButtonCancel"
+            android:textColor="?android:attr/textColorPrimary"
+            android:text="@string/modifier_keys_cancel"/>
+
+        <Button
+            android:id="@+id/modifier_key_done_button"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="6dip"
+            android:layout_marginBottom="6dip"
+            android:layout_marginEnd="8dip"
+            android:layout_alignParentEnd="true"
+            android:paddingVertical="14dp"
+            android:drawablePadding="9dp"
+            style="@style/ModifierKeyButtonDone"
+            android:textColor="?androidprv:attr/textColorOnAccent"
+            android:text="@string/modifier_keys_done"/>
+
+    </RelativeLayout>
+</LinearLayout>
\ No newline at end of file
diff --git a/res/layout/modifier_key_reset_dialog.xml b/res/layout/modifier_key_reset_dialog.xml
new file mode 100644
index 0000000..fd38b11
--- /dev/null
+++ b/res/layout/modifier_key_reset_dialog.xml
@@ -0,0 +1,86 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2022 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.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+              android:orientation="vertical"
+              android:layout_width="match_parent"
+              android:layout_height="match_parent" >
+
+    <TextView
+        android:id="@+id/modifier_key_reset_dialog_title"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginTop="24dip"
+        android:layout_marginBottom="8dip"
+        android:layout_gravity="center_horizontal"
+        android:singleLine="true"
+        android:textAppearance="?android:attr/textAppearanceLarge"
+        android:textColor="?android:attr/textColorPrimary"
+        android:text="@string/modifier_keys_reset_title" />
+
+    <TextView
+        android:id="@+id/modifier_key_reset_dialog_message"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginTop="8dip"
+        android:layout_marginBottom="16dip"
+        android:layout_marginStart="32dip"
+        android:layout_marginEnd="32dip"
+        android:gravity="center"
+        android:layout_gravity="center_horizontal"
+        android:textAppearance="?android:attr/textAppearanceSmall"
+        android:textColor="?android:attr/textColorSecondary"
+        android:text="@string/modifier_keys_reset_message" />
+
+    <RelativeLayout
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginStart="8dip"
+        android:layout_marginEnd="8dip"
+        android:layout_marginTop="6dip"
+        android:layout_marginBottom="6dip"
+        android:layout_weight="1">
+
+        <Button
+            android:id="@+id/modifier_key_reset_cancel_button"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="6dip"
+            android:layout_marginBottom="6dip"
+            android:layout_marginStart="8dip"
+            android:layout_alignParentStart="true"
+            android:paddingVertical="14dp"
+            android:drawablePadding="9dp"
+            style="@style/ModifierKeyButtonCancel"
+            android:textColor="?android:attr/textColorPrimary"
+            android:text="@string/modifier_keys_cancel"/>
+
+        <Button
+            android:id="@+id/modifier_key_reset_restore_button"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_marginTop="6dip"
+            android:layout_marginBottom="6dip"
+            android:layout_marginEnd="8dip"
+            android:layout_alignParentEnd="true"
+            android:paddingVertical="14dp"
+            android:drawablePadding="9dp"
+            style="@style/ModifierKeyButtonCancel"
+            android:textColor="?android:attr/textColorPrimary"
+            android:text="@string/modifier_keys_restore"/>
+
+    </RelativeLayout>
+</LinearLayout>
\ No newline at end of file
diff --git a/res/values/strings.xml b/res/values/strings.xml
index 2a2cccf..59b3f20 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -3735,6 +3735,37 @@
     <!-- Summary text for 'Switch apps' [CHAR LIMIT=60] -->
     <string name="trackpad_switch_apps_summary">Swipe left or right with four fingers</string>
 
+    <!-- Title for the button to trigger the 'modifier keys settings' page. [CHAR LIMIT=35] -->
+    <string name="modifier_keys_settings">Modifier keys</string>
+    <!-- Summary text for the 'modifier_keys_settings' page. [CHAR LIMIT=100] -->
+    <string name="modifier_keys_settings_summary">Change the behavior of keys</string>
+
+    <!-- Title for the button to trigger the 'modifier keys caps lock'. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_caps_lock" translatable="false">Caps lock</string>
+    <!-- Title for the button to trigger the 'modifier keys ctrl'. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_ctrl" translatable="false">Ctrl</string>
+    <!-- Title for the button to trigger the 'modifier keys meta'. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_meta" translatable="false">Meta</string>
+    <!-- Title for the button to trigger the 'modifier keys alt'. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_alt" translatable="false">Alt</string>
+
+    <!-- Title for the button to trigger the 'modifier keys reset all'. [CHAR LIMIT=35] -->
+    <string name="modifier_keys_reset_title">Reset all</string>
+    <!-- Summary text for the buttons. [CHAR LIMIT=35] -->
+    <string name="modifier_keys_default_summary">Default</string>
+    <!-- Message for the 'Reset all' page. [CHAR LIMIT=100] -->
+    <string name="modifier_keys_reset_message">Are you sure you would like to reset all the modifier keys to their default?</string>
+    <!-- Text of the done button. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_done">Done</string>
+    <!-- Text of the cancel button. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_cancel">Cancel</string>
+    <!-- Text of the restore button. [CHAR LIMIT=15] -->
+    <string name="modifier_keys_restore">Restore</string>
+    <!-- Title for the modifier key picker dialog page [CHAR LIMIT=35] -->
+    <string name="modifier_keys_picker_title">Choose modifier key</string>
+    <!-- Summary for the modifier key picker dialog page [CHAR LIMIT=35] -->
+    <string name="modifier_keys_picker_summary">Choose a new key for <xliff:g id="modifier_key_default_name">%1$s</xliff:g>:</string>
+
     <!-- Summary text for keyboards when no layout has been selected. [CHAR LIMIT=35] -->
     <string name="default_keyboard_layout">Default</string>
 
@@ -8198,7 +8229,7 @@
     <!-- [CHAR LIMIT=60] turn eSim deletion confirmation on/off  -->
     <string name="confirm_sim_deletion_title">Confirm SIM deletion</string>
     <!-- [CHAR LIMIT=NONE] eSim deletion confirmation description  -->
-    <string name="confirm_sim_deletion_description">Verify it\u0027s you before erasing a eSIM</string>
+    <string name="confirm_sim_deletion_description">Verify it\u0027s you before erasing an eSIM</string>
 
     <!-- [CHAR LIMIT=32] Name of Advanced memory protection page in "More Security Settings" and heading of page. -->
     <string name="memtag_title">Advanced memory protection beta</string>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 20ebe255..c262264 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -378,6 +378,20 @@
         <item name="android:colorControlHighlight">@color/ripple_material_inverse</item>
     </style>
 
+    <style name="ModifierKeyButtonCancel" parent="@android:style/Widget.Material.Button">
+        <item name="android:background">@drawable/modifier_key_bordered</item>
+        <item name="android:stateListAnimator">@null</item>
+        <item name="android:textSize">16sp</item>
+        <item name="android:padding">4dp</item>
+    </style>
+
+    <style name="ModifierKeyButtonDone" parent="@android:style/Widget.Material.Button">
+        <item name="android:background">@drawable/modifier_key_colored</item>
+        <item name="android:stateListAnimator">@null</item>
+        <item name="android:textSize">16sp</item>
+        <item name="android:padding">4dp</item>
+    </style>
+
     <style name="LockPatternContainerStyle">
         <item name="android:gravity">center</item>
         <item name="android:maxHeight">@dimen/biometric_auth_pattern_view_max_size</item>
diff --git a/res/xml/modifier_keys_settings.xml b/res/xml/modifier_keys_settings.xml
new file mode 100644
index 0000000..63e7ee1
--- /dev/null
+++ b/res/xml/modifier_keys_settings.xml
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+  Copyright (C) 2022 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.
+-->
+
+<PreferenceScreen
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:settings="http://schemas.android.com/apk/res-auto"
+    android:title="@string/modifier_keys_settings"
+    android:key="modifier_keys_all"
+    settings:controller="com.android.settings.inputmethod.ModifierKeysPreferenceController">
+    <Preference
+        android:key="modifier_keys_caps_lock"
+        android:title="@string/modifier_keys_caps_lock"
+        android:summary="@string/modifier_keys_default_summary"/>
+
+    <Preference
+        android:key="modifier_keys_ctrl"
+        android:title="@string/modifier_keys_ctrl"
+        android:summary="@string/modifier_keys_default_summary"/>
+
+    <Preference
+        android:key="modifier_keys_meta"
+        android:title="@string/modifier_keys_meta"
+        android:summary="@string/modifier_keys_default_summary"/>
+
+    <Preference
+        android:key="modifier_keys_alt"
+        android:title="@string/modifier_keys_alt"
+        android:summary="@string/modifier_keys_default_summary"/>
+
+    <Preference
+        android:key="modifier_keys_restore"
+        android:icon="@drawable/ic_modifier_keys_reset"
+        settings:controller="com.android.settings.inputmethod.ModifierKeysRestorePreferenceController"/>
+</PreferenceScreen>
\ No newline at end of file
diff --git a/res/xml/physical_keyboard_settings.xml b/res/xml/physical_keyboard_settings.xml
index 54a5c65..40851a9 100644
--- a/res/xml/physical_keyboard_settings.xml
+++ b/res/xml/physical_keyboard_settings.xml
@@ -31,5 +31,11 @@
             android:key="keyboard_shortcuts_helper"
             android:title="@string/keyboard_shortcuts_helper"
             android:summary="@string/keyboard_shortcuts_helper_summary" />
+
+        <Preference
+            android:key="modifier_keys_settings"
+            android:title="@string/modifier_keys_settings"
+            android:summary="@string/modifier_keys_settings_summary"
+            android:fragment="com.android.settings.inputmethod.ModifierKeysSettings" />
     </PreferenceCategory>
 </PreferenceScreen>
diff --git a/src/com/android/settings/accessibility/TextReadingPreferenceFragment.java b/src/com/android/settings/accessibility/TextReadingPreferenceFragment.java
index 22bef28..7316e12 100644
--- a/src/com/android/settings/accessibility/TextReadingPreferenceFragment.java
+++ b/src/com/android/settings/accessibility/TextReadingPreferenceFragment.java
@@ -210,6 +210,8 @@
 
     @Override
     public void onSaveInstanceState(Bundle outState) {
+        super.onSaveInstanceState(outState);
+
         if (mNeedResetSettings) {
             outState.putBoolean(NEED_RESET_SETTINGS, true);
         }
diff --git a/src/com/android/settings/core/gateway/SettingsGateway.java b/src/com/android/settings/core/gateway/SettingsGateway.java
index db23c43..1e66871 100644
--- a/src/com/android/settings/core/gateway/SettingsGateway.java
+++ b/src/com/android/settings/core/gateway/SettingsGateway.java
@@ -121,6 +121,7 @@
 import com.android.settings.inputmethod.AvailableVirtualKeyboardFragment;
 import com.android.settings.inputmethod.KeyboardLayoutPickerFragment;
 import com.android.settings.inputmethod.KeyboardSettings;
+import com.android.settings.inputmethod.ModifierKeysSettings;
 import com.android.settings.inputmethod.NewKeyboardLayoutEnabledLocalesFragment;
 import com.android.settings.inputmethod.PhysicalKeyboardFragment;
 import com.android.settings.inputmethod.SpellCheckersSettings;
@@ -217,6 +218,7 @@
             LanguageAndInputSettings.class.getName(),
             LanguageSettings.class.getName(),
             KeyboardSettings.class.getName(),
+            ModifierKeysSettings.class.getName(),
             NewKeyboardLayoutEnabledLocalesFragment.class.getName(),
             TrackpadSettings.class.getName(),
             SpellCheckersSettings.class.getName(),
diff --git a/src/com/android/settings/inputmethod/ModifierKeysPickerDialogFragment.java b/src/com/android/settings/inputmethod/ModifierKeysPickerDialogFragment.java
new file mode 100644
index 0000000..40c15ff
--- /dev/null
+++ b/src/com/android/settings/inputmethod/ModifierKeysPickerDialogFragment.java
@@ -0,0 +1,198 @@
+/*
+ * Copyright (C) 2022 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.inputmethod;
+
+import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_DIALOG;
+
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.content.Context;
+import android.os.Bundle;
+import android.text.Spannable;
+import android.text.SpannableString;
+import android.text.style.ForegroundColorSpan;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.Window;
+import android.widget.AdapterView;
+import android.widget.BaseAdapter;
+import android.widget.Button;
+import android.widget.ImageView;
+import android.widget.ListView;
+import android.widget.TextView;
+
+import androidx.fragment.app.DialogFragment;
+import androidx.preference.Preference;
+
+import com.android.settings.R;
+import com.android.settingslib.Utils;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class ModifierKeysPickerDialogFragment extends DialogFragment {
+
+    private Preference mPreference;
+    private String mKeyDefaultName;
+    private Context mContext;
+
+    public ModifierKeysPickerDialogFragment() {
+    }
+
+    public ModifierKeysPickerDialogFragment(Preference preference) {
+        mPreference = preference;
+        mKeyDefaultName = preference.getTitle().toString();
+    }
+
+    @Override
+    public Dialog onCreateDialog(Bundle savedInstanceState) {
+        super.onCreateDialog(savedInstanceState);
+        mContext = getActivity();
+        String[] modifierKeys = new String[] {
+                mContext.getString(R.string.modifier_keys_caps_lock),
+                mContext.getString(R.string.modifier_keys_ctrl),
+                mContext.getString(R.string.modifier_keys_meta),
+                mContext.getString(R.string.modifier_keys_alt)};
+
+        View dialoglayout  =
+                LayoutInflater.from(mContext).inflate(R.layout.modifier_key_picker_dialog, null);
+        AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(mContext);
+        dialogBuilder.setView(dialoglayout);
+
+        TextView summary = dialoglayout.findViewById(R.id.modifier_key_picker_summary);
+        CharSequence summaryText = mContext.getString(
+                R.string.modifier_keys_picker_summary, mKeyDefaultName);
+        summary.setText(summaryText);
+
+        List<String> list = new ArrayList<>();
+        for (int i = 0; i < modifierKeys.length; i++) {
+            list.add(modifierKeys[i]);
+        }
+        ModifierKeyAdapter adapter = new ModifierKeyAdapter(list);
+        ListView listView = dialoglayout.findViewById(R.id.modifier_key_picker);
+        listView.setAdapter(adapter);
+        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
+            @Override
+            public void onItemClick(AdapterView<?> adapterView, View view, int i, long l) {
+                adapter.setCurrentItem(i);
+                adapter.setClick(true);
+                adapter.notifyDataSetChanged();
+            }
+        });
+
+        AlertDialog modifierKeyDialog = dialogBuilder.create();
+        Button doneButton = dialoglayout.findViewById(R.id.modifier_key_done_button);
+        doneButton.setOnClickListener(v -> {
+            String selectedItem = list.get(adapter.getCurrentItem());
+            Spannable itemSummary;
+            if (selectedItem.equals(mKeyDefaultName)) {
+                itemSummary = new SpannableString(
+                        mContext.getString(R.string.modifier_keys_default_summary));
+                itemSummary.setSpan(
+                        new ForegroundColorSpan(getColorOfTextColorSecondary()),
+                        0, itemSummary.length(), 0);
+                // TODO(b/252812993): remapModifierKey
+            } else {
+                itemSummary = new SpannableString(selectedItem);
+                itemSummary.setSpan(
+                        new ForegroundColorSpan(getColorOfColorAccentPrimaryVariant()),
+                        0, itemSummary.length(), 0);
+            }
+            mPreference.setSummary(itemSummary);
+            modifierKeyDialog.dismiss();
+        });
+
+        Button cancelButton = dialoglayout.findViewById(R.id.modifier_key_cancel_button);
+        cancelButton.setOnClickListener(v -> {
+            modifierKeyDialog.dismiss();
+        });
+
+        final Window window = modifierKeyDialog.getWindow();
+        window.setType(TYPE_SYSTEM_DIALOG);
+
+        return modifierKeyDialog;
+    }
+
+    class ModifierKeyAdapter extends BaseAdapter {
+        private int mCurrentItem = 0;
+        private boolean mIsClick = false;
+        private List<String> mList;
+
+        ModifierKeyAdapter(List<String> list) {
+            this.mList = list;
+        }
+
+        @Override
+        public int getCount() {
+            return mList.size();
+        }
+
+        @Override
+        public Object getItem(int i) {
+            return mList.get(i);
+        }
+
+        @Override
+        public long getItemId(int i) {
+            return i;
+        }
+
+        @Override
+        public View getView(int i, View view, ViewGroup viewGroup) {
+            if (view == null) {
+                view = LayoutInflater.from(mContext).inflate(R.layout.modifier_key_item, null);
+            }
+            TextView textView = view.findViewById(R.id.modifier_key_text);
+            ImageView checkIcon = view.findViewById(R.id.modifier_key_check_icon);
+            textView.setText(mList.get(i));
+            if (mCurrentItem == i && mIsClick) {
+                textView.setTextColor(getColorOfColorAccentPrimaryVariant());
+                checkIcon.setImageAlpha(255);
+            } else {
+                textView.setTextColor(getColorOfTextColorPrimary());
+                checkIcon.setImageAlpha(0);
+            }
+            return view;
+        }
+
+        public void setCurrentItem(int currentItem) {
+            this.mCurrentItem = currentItem;
+        }
+
+        public int getCurrentItem() {
+            return this.mCurrentItem;
+        }
+
+        public void setClick(boolean click) {
+            this.mIsClick = click;
+        }
+    }
+
+    private int getColorOfTextColorPrimary() {
+        return Utils.getColorAttrDefaultColor(mContext, android.R.attr.textColorPrimary);
+    }
+
+    private int getColorOfTextColorSecondary() {
+        return Utils.getColorAttrDefaultColor(mContext, android.R.attr.textColorSecondary);
+    }
+
+    private int getColorOfColorAccentPrimaryVariant() {
+        return Utils.getColorAttrDefaultColor(
+                mContext, com.android.internal.R.attr.colorAccentPrimaryVariant);
+    }
+}
diff --git a/src/com/android/settings/inputmethod/ModifierKeysPreferenceController.java b/src/com/android/settings/inputmethod/ModifierKeysPreferenceController.java
new file mode 100644
index 0000000..a7f8a37
--- /dev/null
+++ b/src/com/android/settings/inputmethod/ModifierKeysPreferenceController.java
@@ -0,0 +1,88 @@
+/*
+ * Copyright (C) 2022 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.inputmethod;
+
+import android.content.Context;
+
+import androidx.fragment.app.DialogFragment;
+import androidx.fragment.app.Fragment;
+import androidx.fragment.app.FragmentManager;
+import androidx.preference.Preference;
+import androidx.preference.PreferenceScreen;
+
+import com.android.settings.core.BasePreferenceController;
+
+public class ModifierKeysPreferenceController extends BasePreferenceController {
+
+    private static String KEY_TAG = "modifier_keys_dialog_tag";
+    private static String KEY_RESTORE_PREFERENCE = "modifier_keys_restore";
+
+    private Fragment mParent;
+    private FragmentManager mFragmentManager;
+
+    public ModifierKeysPreferenceController(Context context, String key) {
+        super(context, key);
+    }
+
+    public void setFragment(Fragment parent) {
+        mParent = parent;
+    }
+
+    @Override
+    public void displayPreference(PreferenceScreen screen) {
+        super.displayPreference(screen);
+        // TODO: getModifierKeyRemapping()
+        // setTitle
+        // setSummary
+        if (mParent == null) {
+            return;
+        }
+        // The dialog screen depends on the previous selected key's fragment.
+        // In the rotation scenario, we should remove the previous dialog screen first.
+        clearPreviousDialog();
+    }
+
+    @Override
+    public boolean handlePreferenceTreeClick(Preference preference) {
+        if (preference.getKey().equals(KEY_RESTORE_PREFERENCE)) {
+            return false;
+        }
+        showModifierKeysDialog(preference);
+        return true;
+    }
+
+    @Override
+    public int getAvailabilityStatus() {
+        return AVAILABLE;
+    }
+
+    private void showModifierKeysDialog(Preference preference) {
+        ModifierKeysPickerDialogFragment fragment =
+                new ModifierKeysPickerDialogFragment(preference);
+        fragment.setTargetFragment(mParent, 0);
+        fragment.show(mFragmentManager, KEY_TAG);
+    }
+
+    private void clearPreviousDialog() {
+        mFragmentManager = mParent.getFragmentManager();
+        DialogFragment preKeysDialogFragment =
+                (DialogFragment) mFragmentManager.findFragmentByTag(KEY_TAG);
+        if (preKeysDialogFragment != null) {
+            preKeysDialogFragment.dismiss();
+        }
+    }
+}
diff --git a/src/com/android/settings/inputmethod/ModifierKeysResetDialogFragment.java b/src/com/android/settings/inputmethod/ModifierKeysResetDialogFragment.java
new file mode 100644
index 0000000..0b605a0
--- /dev/null
+++ b/src/com/android/settings/inputmethod/ModifierKeysResetDialogFragment.java
@@ -0,0 +1,104 @@
+/*
+ * Copyright (C) 2022 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.inputmethod;
+
+import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_DIALOG;
+
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.content.Context;
+import android.os.Bundle;
+import android.text.Spannable;
+import android.text.SpannableString;
+import android.text.style.ForegroundColorSpan;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.Window;
+import android.widget.Button;
+
+import androidx.fragment.app.DialogFragment;
+import androidx.preference.Preference;
+import androidx.preference.PreferenceScreen;
+
+import com.android.settings.R;
+import com.android.settingslib.Utils;
+
+public class ModifierKeysResetDialogFragment extends DialogFragment {
+    private static final String MODIFIER_KEYS_CAPS_LOCK = "modifier_keys_caps_lock";
+    private static final String MODIFIER_KEYS_CTRL = "modifier_keys_ctrl";
+    private static final String MODIFIER_KEYS_META = "modifier_keys_meta";
+    private static final String MODIFIER_KEYS_ALT = "modifier_keys_alt";
+
+    private PreferenceScreen mScreen;
+    private String[] mKeys = {
+            MODIFIER_KEYS_CAPS_LOCK,
+            MODIFIER_KEYS_CTRL,
+            MODIFIER_KEYS_META,
+            MODIFIER_KEYS_ALT};
+
+    public ModifierKeysResetDialogFragment() {
+    }
+
+    public ModifierKeysResetDialogFragment(PreferenceScreen screen) {
+        mScreen = screen;
+    }
+
+    @Override
+    public Dialog onCreateDialog(Bundle savedInstanceState) {
+        super.onCreateDialog(savedInstanceState);
+        Context mContext = getActivity();
+        View dialoglayout =
+                LayoutInflater.from(mContext).inflate(R.layout.modifier_key_reset_dialog, null);
+        AlertDialog.Builder dialogBuilder = new AlertDialog.Builder(mContext);
+        dialogBuilder.setView(dialoglayout);
+        AlertDialog modifierKeyResetDialog = dialogBuilder.create();
+
+        Button restoreButton = dialoglayout.findViewById(R.id.modifier_key_reset_restore_button);
+        restoreButton.setOnClickListener(v -> {
+            resetToDefault();
+            modifierKeyResetDialog.dismiss();
+        });
+
+        Button cancelButton = dialoglayout.findViewById(R.id.modifier_key_reset_cancel_button);
+        cancelButton.setOnClickListener(v -> {
+            modifierKeyResetDialog.dismiss();
+        });
+
+        final Window window = modifierKeyResetDialog.getWindow();
+        window.setType(TYPE_SYSTEM_DIALOG);
+
+        return modifierKeyResetDialog;
+    }
+
+    private void resetToDefault() {
+        Context mContext = getActivity();
+        for (int i = 0; i < mKeys.length; i++) {
+            Preference preference = mScreen.findPreference(mKeys[i]);
+            Spannable title = new SpannableString(
+                    mContext.getString(R.string.modifier_keys_default_summary));
+            title.setSpan(
+                    new ForegroundColorSpan(getColorOfTextColorSecondary()),
+                    0, title.length(), 0);
+            preference.setSummary(title);
+        }
+        // TODO(b/252812993): clearAllModifierKeyRemappings()
+    }
+
+    private int getColorOfTextColorSecondary() {
+        return Utils.getColorAttrDefaultColor(getActivity(), android.R.attr.textColorSecondary);
+    }
+}
diff --git a/src/com/android/settings/inputmethod/ModifierKeysRestorePreferenceController.java b/src/com/android/settings/inputmethod/ModifierKeysRestorePreferenceController.java
new file mode 100644
index 0000000..159cc11
--- /dev/null
+++ b/src/com/android/settings/inputmethod/ModifierKeysRestorePreferenceController.java
@@ -0,0 +1,107 @@
+/*
+ * Copyright (C) 2022 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.inputmethod;
+
+import android.content.Context;
+import android.text.Spannable;
+import android.text.SpannableString;
+import android.text.style.ForegroundColorSpan;
+
+import androidx.fragment.app.DialogFragment;
+import androidx.fragment.app.Fragment;
+import androidx.fragment.app.FragmentManager;
+import androidx.preference.Preference;
+import androidx.preference.PreferenceScreen;
+
+import com.android.settings.R;
+import com.android.settings.core.BasePreferenceController;
+import com.android.settingslib.Utils;
+
+public class ModifierKeysRestorePreferenceController extends BasePreferenceController {
+
+    private static String KEY_TAG = "modifier_keys_dialog_tag";
+
+    private Fragment mParent;
+    private FragmentManager mFragmentManager;
+    private PreferenceScreen mScreen;
+
+    public ModifierKeysRestorePreferenceController(Context context, String key) {
+        super(context, key);
+    }
+
+    public void setFragment(Fragment parent) {
+        mParent = parent;
+    }
+
+    @Override
+    public void displayPreference(PreferenceScreen screen) {
+        super.displayPreference(screen);
+        if (mParent == null) {
+            return;
+        }
+        mScreen = screen;
+        // The dialog screen depends on the previous selected key's fragment.
+        // In the rotation scenario, we should remove the previous dialog first.
+        clearPreviousDialog();
+        setResetKeyColor();
+    }
+
+    @Override
+    public boolean handlePreferenceTreeClick(Preference preference) {
+        if (!preference.getKey().equals(getPreferenceKey())) {
+            return false;
+        }
+        showResetDialog();
+        return true;
+    }
+
+    @Override
+    public int getAvailabilityStatus() {
+        return AVAILABLE;
+    }
+
+    private void showResetDialog() {
+        ModifierKeysResetDialogFragment fragment =
+                new ModifierKeysResetDialogFragment(mScreen);
+        fragment.setTargetFragment(mParent, 0);
+        fragment.show(mFragmentManager, KEY_TAG);
+    }
+
+    private void setResetKeyColor() {
+        Preference preference = mScreen.findPreference(getPreferenceKey());
+        Spannable title = new SpannableString(
+                mParent.getActivity().getString(R.string.modifier_keys_reset_title));
+        title.setSpan(
+                new ForegroundColorSpan(getColorOfColorAccentPrimaryVariant()),
+                0, title.length(), 0);
+        preference.setTitle(title);
+    }
+
+    private int getColorOfColorAccentPrimaryVariant() {
+        return Utils.getColorAttrDefaultColor(
+                mParent.getActivity(), com.android.internal.R.attr.colorAccentPrimaryVariant);
+    }
+
+    private void clearPreviousDialog() {
+        mFragmentManager = mParent.getFragmentManager();
+        DialogFragment preResetDialogFragment =
+                (DialogFragment) mFragmentManager.findFragmentByTag(KEY_TAG);
+        if (preResetDialogFragment != null) {
+            preResetDialogFragment.dismiss();
+        }
+    }
+}
diff --git a/src/com/android/settings/inputmethod/ModifierKeysSettings.java b/src/com/android/settings/inputmethod/ModifierKeysSettings.java
new file mode 100644
index 0000000..2353c2c
--- /dev/null
+++ b/src/com/android/settings/inputmethod/ModifierKeysSettings.java
@@ -0,0 +1,64 @@
+/*
+ * Copyright (C) 2022 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.inputmethod;
+
+import android.app.settings.SettingsEnums;
+import android.content.Context;
+import android.util.FeatureFlagUtils;
+
+import com.android.settings.R;
+import com.android.settings.dashboard.DashboardFragment;
+import com.android.settings.search.BaseSearchIndexProvider;
+import com.android.settingslib.search.SearchIndexable;
+
+@SearchIndexable
+public class ModifierKeysSettings extends DashboardFragment {
+
+    private static final String TAG = "ModifierKeysSettings";
+
+    @Override
+    public void onAttach(Context context) {
+        super.onAttach(context);
+        use(ModifierKeysPreferenceController.class).setFragment(this /*parent*/);
+        use(ModifierKeysRestorePreferenceController.class).setFragment(this /*parent*/);
+    }
+
+    @Override
+    public int getMetricsCategory() {
+        return SettingsEnums.SETTINGS_KEYBOARDS_MODIFIER_KEYS;
+    }
+
+    @Override
+    protected String getLogTag() {
+        return TAG;
+    }
+
+    @Override
+    protected int getPreferenceScreenResId() {
+        return R.xml.modifier_keys_settings;
+    }
+
+    public static final BaseSearchIndexProvider SEARCH_INDEX_DATA_PROVIDER =
+            new BaseSearchIndexProvider(R.xml.modifier_keys_settings) {
+                @Override
+                protected boolean isPageSearchEnabled(Context context) {
+                    return FeatureFlagUtils
+                            .isEnabled(
+                                    context, FeatureFlagUtils.SETTINGS_NEW_KEYBOARD_MODIFIER_KEY);
+                }
+            };
+}
diff --git a/src/com/android/settings/inputmethod/PhysicalKeyboardFragment.java b/src/com/android/settings/inputmethod/PhysicalKeyboardFragment.java
index 38ea840..7d43d7c 100644
--- a/src/com/android/settings/inputmethod/PhysicalKeyboardFragment.java
+++ b/src/com/android/settings/inputmethod/PhysicalKeyboardFragment.java
@@ -67,6 +67,7 @@
     private static final String KEYBOARD_OPTIONS_CATEGORY = "keyboard_options_category";
     private static final String SHOW_VIRTUAL_KEYBOARD_SWITCH = "show_virtual_keyboard_switch";
     private static final String KEYBOARD_SHORTCUTS_HELPER = "keyboard_shortcuts_helper";
+    private static final String MODIFIER_KEYS_SETTINGS = "modifier_keys_settings";
 
     @NonNull
     private final ArrayList<HardKeyboardDeviceInfo> mLastHardKeyboards = new ArrayList<>();
@@ -94,9 +95,14 @@
         mShowVirtualKeyboardSwitch = Preconditions.checkNotNull(
                 (SwitchPreference) mKeyboardAssistanceCategory.findPreference(
                         SHOW_VIRTUAL_KEYBOARD_SWITCH));
+
         mIsNewKeyboardSettings = FeatureFlagUtils.isEnabled(
                 getContext(), FeatureFlagUtils.SETTINGS_NEW_KEYBOARD_UI);
-        // TODO(b/247080921): Support shortcuts list & modifier keys
+        boolean isModifierKeySettingsEnabled = FeatureFlagUtils
+                .isEnabled(getContext(), FeatureFlagUtils.SETTINGS_NEW_KEYBOARD_MODIFIER_KEY);
+        if (!isModifierKeySettingsEnabled) {
+            mKeyboardAssistanceCategory.removePreference(findPreference(MODIFIER_KEYS_SETTINGS));
+        }
     }
 
     @Override