Home | History | Annotate | Download | only in preference
      1 /*
      2  * Copyright 2018 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package androidx.preference;
     18 
     19 import android.content.DialogInterface;
     20 import android.os.Bundle;
     21 
     22 import androidx.annotation.NonNull;
     23 import androidx.appcompat.app.AlertDialog;
     24 
     25 public class ListPreferenceDialogFragmentCompat extends PreferenceDialogFragmentCompat {
     26 
     27     private static final String SAVE_STATE_INDEX = "ListPreferenceDialogFragment.index";
     28     private static final String SAVE_STATE_ENTRIES = "ListPreferenceDialogFragment.entries";
     29     private static final String SAVE_STATE_ENTRY_VALUES =
     30             "ListPreferenceDialogFragment.entryValues";
     31 
     32     private int mClickedDialogEntryIndex;
     33     private CharSequence[] mEntries;
     34     private CharSequence[] mEntryValues;
     35 
     36     public static ListPreferenceDialogFragmentCompat newInstance(String key) {
     37         final ListPreferenceDialogFragmentCompat fragment =
     38                 new ListPreferenceDialogFragmentCompat();
     39         final Bundle b = new Bundle(1);
     40         b.putString(ARG_KEY, key);
     41         fragment.setArguments(b);
     42         return fragment;
     43     }
     44 
     45     @Override
     46     public void onCreate(Bundle savedInstanceState) {
     47         super.onCreate(savedInstanceState);
     48         if (savedInstanceState == null) {
     49             final ListPreference preference = getListPreference();
     50 
     51             if (preference.getEntries() == null || preference.getEntryValues() == null) {
     52                 throw new IllegalStateException(
     53                         "ListPreference requires an entries array and an entryValues array.");
     54             }
     55 
     56             mClickedDialogEntryIndex = preference.findIndexOfValue(preference.getValue());
     57             mEntries = preference.getEntries();
     58             mEntryValues = preference.getEntryValues();
     59         } else {
     60             mClickedDialogEntryIndex = savedInstanceState.getInt(SAVE_STATE_INDEX, 0);
     61             mEntries = savedInstanceState.getCharSequenceArray(SAVE_STATE_ENTRIES);
     62             mEntryValues = savedInstanceState.getCharSequenceArray(SAVE_STATE_ENTRY_VALUES);
     63         }
     64     }
     65 
     66     @Override
     67     public void onSaveInstanceState(@NonNull Bundle outState) {
     68         super.onSaveInstanceState(outState);
     69         outState.putInt(SAVE_STATE_INDEX, mClickedDialogEntryIndex);
     70         outState.putCharSequenceArray(SAVE_STATE_ENTRIES, mEntries);
     71         outState.putCharSequenceArray(SAVE_STATE_ENTRY_VALUES, mEntryValues);
     72     }
     73 
     74     private ListPreference getListPreference() {
     75         return (ListPreference) getPreference();
     76     }
     77 
     78     @Override
     79     protected void onPrepareDialogBuilder(AlertDialog.Builder builder) {
     80         super.onPrepareDialogBuilder(builder);
     81 
     82         builder.setSingleChoiceItems(mEntries, mClickedDialogEntryIndex,
     83                 new DialogInterface.OnClickListener() {
     84                     @Override
     85                     public void onClick(DialogInterface dialog, int which) {
     86                         mClickedDialogEntryIndex = which;
     87 
     88                         /*
     89                          * Clicking on an item simulates the positive button
     90                          * click, and dismisses the dialog.
     91                          */
     92                         ListPreferenceDialogFragmentCompat.this.onClick(dialog,
     93                                 DialogInterface.BUTTON_POSITIVE);
     94                         dialog.dismiss();
     95                     }
     96                 });
     97 
     98         /*
     99          * The typical interaction for list-based dialogs is to have
    100          * click-on-an-item dismiss the dialog instead of the user having to
    101          * press 'Ok'.
    102          */
    103         builder.setPositiveButton(null, null);
    104     }
    105 
    106     @Override
    107     public void onDialogClosed(boolean positiveResult) {
    108         final ListPreference preference = getListPreference();
    109         if (positiveResult && mClickedDialogEntryIndex >= 0) {
    110             String value = mEntryValues[mClickedDialogEntryIndex].toString();
    111             if (preference.callChangeListener(value)) {
    112                 preference.setValue(value);
    113             }
    114         }
    115     }
    116 
    117 }
    118