1 /* 2 * Copyright (C) 2015 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 android.support.v14.preference; 18 19 import android.app.AlertDialog; 20 import android.content.DialogInterface; 21 import android.os.Bundle; 22 import android.support.annotation.NonNull; 23 import android.support.v7.preference.ListPreference; 24 25 public class ListPreferenceDialogFragment extends PreferenceDialogFragment { 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 newInstance(String key)36 public static ListPreferenceDialogFragment newInstance(String key) { 37 final ListPreferenceDialogFragment fragment = new ListPreferenceDialogFragment(); 38 final Bundle b = new Bundle(1); 39 b.putString(ARG_KEY, key); 40 fragment.setArguments(b); 41 return fragment; 42 } 43 44 @Override onCreate(Bundle savedInstanceState)45 public void onCreate(Bundle savedInstanceState) { 46 super.onCreate(savedInstanceState); 47 if (savedInstanceState == null) { 48 final ListPreference preference = getListPreference(); 49 50 if (preference.getEntries() == null || preference.getEntryValues() == null) { 51 throw new IllegalStateException( 52 "ListPreference requires an entries array and an entryValues array."); 53 } 54 55 mClickedDialogEntryIndex = preference.findIndexOfValue(preference.getValue()); 56 mEntries = preference.getEntries(); 57 mEntryValues = preference.getEntryValues(); 58 } else { 59 mClickedDialogEntryIndex = savedInstanceState.getInt(SAVE_STATE_INDEX, 0); 60 mEntries = savedInstanceState.getCharSequenceArray(SAVE_STATE_ENTRIES); 61 mEntryValues = savedInstanceState.getCharSequenceArray(SAVE_STATE_ENTRY_VALUES); 62 } 63 } 64 65 @Override onSaveInstanceState(@onNull Bundle outState)66 public void onSaveInstanceState(@NonNull Bundle outState) { 67 super.onSaveInstanceState(outState); 68 outState.putInt(SAVE_STATE_INDEX, mClickedDialogEntryIndex); 69 outState.putCharSequenceArray(SAVE_STATE_ENTRIES, mEntries); 70 outState.putCharSequenceArray(SAVE_STATE_ENTRY_VALUES, mEntryValues); 71 } 72 getListPreference()73 private ListPreference getListPreference() { 74 return (ListPreference) getPreference(); 75 } 76 77 @Override onPrepareDialogBuilder(AlertDialog.Builder builder)78 protected void onPrepareDialogBuilder(AlertDialog.Builder builder) { 79 super.onPrepareDialogBuilder(builder); 80 81 builder.setSingleChoiceItems(mEntries, mClickedDialogEntryIndex, 82 new DialogInterface.OnClickListener() { 83 @Override 84 public void onClick(DialogInterface dialog, int which) { 85 mClickedDialogEntryIndex = which; 86 87 /* 88 * Clicking on an item simulates the positive button 89 * click, and dismisses the dialog. 90 */ 91 ListPreferenceDialogFragment.this.onClick(dialog, 92 DialogInterface.BUTTON_POSITIVE); 93 dialog.dismiss(); 94 } 95 }); 96 97 /* 98 * The typical interaction for list-based dialogs is to have 99 * click-on-an-item dismiss the dialog instead of the user having to 100 * press 'Ok'. 101 */ 102 builder.setPositiveButton(null, null); 103 } 104 105 @Override onDialogClosed(boolean positiveResult)106 public void onDialogClosed(boolean positiveResult) { 107 final ListPreference preference = getListPreference(); 108 if (positiveResult && mClickedDialogEntryIndex >= 0) { 109 String value = mEntryValues[mClickedDialogEntryIndex].toString(); 110 if (preference.callChangeListener(value)) { 111 preference.setValue(value); 112 } 113 } 114 } 115 116 } 117