I'm trying to prevent the user from entering an empty string into an EditTextPreference
(in the example, catName
). I use a OnPreferenceChangeListener
to detect when a change is made to the EditTextPreference
, and if there is a change and the string is blank, I use the EditTextPreference.setText()
command to reset to the old value. However, the new value doesn't show up properly if I reopen the EditTextPreference
in the GUI (the string is blank), and if I go back into the main app, I can verify that a blank value is being saved to the preferences.
I've verified that the if statement executes as expected, and that my parameter keeping track of the old name (oldCatName
) is updating as expected. I can even log the catName.getText()
value right before the setOnPreferenceChangeListener
finishes execution and I always see the value I expect (the new value set by the user, and when they enter a blank value, it properly resets to the old value). I'm not sure why setting the value to the EditTextPreference
isn't saving the value to the preferences file or updating the GUI.
public class SettingsActivity extends PreferenceActivity {
private String oldCatName;
private EditTextPreference catName;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
addPreferencesFromResource(R.xml.settings);
catName = (EditTextPreference) findPreference("cat_name");
oldCatName = catName.getText();
catName.setOnPreferenceChangeListener(new OnPreferenceChangeListener() {
@Override
public boolean onPreferenceChange(Preference preference, Object newVal) {
final String value = (String) newVal;
if (value.equals("")) {
catName.setText(oldCatName);
Log.e("new value", catName.getText());
}
else
oldCatName = value;
return true;
}
});
}
}
Thanks for the help! -Michael
Edit: A clarification. The logic in the if statement is executing correctly. The string value of the EditTextPreference
is even updating correctly. However, the value in the GUI if the user taps on the EditTextPreference
again does not correctly update, and the value in the app's shared preferences does not update correctly. It stays blank.
Finally found a solution by doing the following:
I used a
SharedPreferences.OnSharedPreferenceChangeListener
instead of aPreference.OnPreferenceChangeListener
. ThePreference.OnPreferenceChangeListener
looks for when the user changes a preference through the settings menu, and behaves before the change is committed to the preference data. TheSharedPreferences.OnSharedPreferenceChangeListener
listens for changes to the actual preference data, not changes in the GUI, so it happens a little later. I noticed that in my first attempt, I could runsetText()
immediately followed bygetText()
on myEditTextPreference
object, and thegetText()
value wouldn't match what I had just set thesetText()
value to. I'm not sure why this happens, but waiting for the changes to actually commit before trying to runsetText()
led to the correct response. Maybe it was a timing issue?I run
setPreferenceScreen(null)
andaddPreferencesFromResource(R.xml.settings)
after updating the value in theEditTextPreference
. If I didn't do this, sometimes when the user would click on theEditTextPreference
again, the value in the field would appear blank even though the value in the settings file wasn't. This forces the settings page to, more or less, refresh itself.The working code is below: