I am currently working with SharedPreferences in Android, and I encountered a weird behavior I cannot explain. This is my code:
SharedPreferences appPreferences = this.getSharedPreferences("settings", Context.MODE_PRIVATE);
appPreferences.edit().putBoolean("launched_before", true);
appPreferences.edit().apply();
appPreferences = null;
appPreferences = this.getSharedPreferences("settings", Context.MODE_PRIVATE);
boolean test = appPreferences.getBoolean("launched_before", false); //this is false
The value that I write to my SharedPreferences is not being saved. I know I could use getDefaultSharedPreferences(), but I do not want to do this here, as the default file stores other values.
When I use commit() instead of apply(), the return value of commit() is true, but I still cannot load the file correctly.
This happens because your code doesn't do what you think. When you call edit(), it does not start an "edit transaction". Instead it returns a new instance of Editor object each time you call it. So let's look at this code:
SharedPreferences appPreferences = getSharedPreferences("settings", Context.MODE_PRIVATE);
// Here you create a FIRST Editor object, which stores the modification
// You never call apply() on this object, and thus your changes are dropped.
appPreferences.edit().putBoolean("launched_before", true);
// Here you create a SECOND Editor object (which has no modifications)
// and you call apply() on it, thus changing nothing.
appPreferences.edit().apply();
You created the first editor object which you put settings in, but you called apply on the second editor object which had no changes. Since you never called apply() on the editor object which had modification, your change was never saved.
The fix is obvious - use a single instance of Editor for your modification, and call apply/commit on this instance:
SharedPreferences appPreferences = this.getSharedPreferences("settings", Context.MODE_PRIVATE);
SharedPreferences.Editor ed = appPreferences.edit();
ed.putBoolean("launched_before", true);
ed.apply();
Here you can use as key "com.yourdomain.yourapp.your_key_name" and for each value use another key...try this
private SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(appContext);
public void putBoolean(String key, boolean value) {
checkForNullKey(key);
preferences.edit().putBoolean(key, value).apply();
}
public boolean getBoolean(String key) {
return preferences.getBoolean(key, false);
}
public void checkForNullKey(String key){
if (key == null){
throw new NullPointerException();
}
}
Related
I am saving some data to SharedPreference from a fragment and want use these data in other fragments. But I want to perform fragment transaction only if SharedPreferences are saved successfully, otherwise, other fragments would not be able to retrieve data (since using those SharedPreference values to retrieve data).
My code:
public class MainActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener{
... ... ... ... ... ... ... ... ...
public void setSharedPref(String key, String val) {
SharedPreferences sharedPref = this.getPreferences(Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sharedPref.edit();
editor.putString(key, val);
editor.commit();
}
public String fetchSharedPref(String key) {
SharedPreferences sharedPref = this.getPreferences(Context.MODE_PRIVATE);
String val = sharedPref.getString(key, Constant.SHARED_PREF_DEFAULT_MSN);
return val;
}
}
How can I be sure that SharedPreferences are saved successfully?
Is there any way to implement a callback that will be invoked only if SharedPreferences saved successfully?
From the docs.
SharedPreferences sharedPref = getActivity().getPreferences(Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sharedPref.edit();
editor.putInt(getString(R.string.saved_high_score), newHighScore);
editor.commit();
Then go and check commit() method here.
Return type: boolean
Description: Returns true if the new values were successfully written to persistent storage.
Find the solution :
SharedPreferences sharedPref = getActivity().getPreferences(Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sharedPref.edit();
editor.putInt("Your Key", "Your value");
boolean savedOrNot = editor.commit();
if(savedOrNot){
// Successfully saved
}else{
// Not saved
}
Form Documentation
apply()
This saves your data into memory immediately and saves the data to
disk on a separate thread. So there is no chance of blocking the main
thread (your app won’t hang).
It is the preferred technique but has only been available since
Gingerbread (API 9, Android 2.3).
commit()
Calling this will save the data to the file however, the process is
carried out in the thread that called it, stopping everything else
until the save is complete. It returns true on successful completion,
false on failure.
Use commit() if you need confirmation of the success of saving your
data or if you are developing for pre-Gingerbread devices. commit()
has been available since API 1
so your can check status at editor.commit();
commit() returns true if the save works, false otherwise.
commit() returns true if the save works, false otherwise.
You can alter your method as follows.
public boolean setSharedPref(String key, String val) {
SharedPreferences sharedPref = this.getPreferences(Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sharedPref.edit();
editor.putString(key, val);
return editor.commit()
}
Difference between apply and commit https://developer.android.com/reference/android/content/SharedPreferences.Editor.html
The editor.commit() will return boolean value , which will let you know if data has been saved.
If you would like to analyze all the data saved in shared preferences and sqlite ,then i would recommend using facebook stetho
Its a debug bridge for android , you can check all of your shared preferences data and sql databases for debugging.
I know this has been asked before, but i can't seem to figure it out
i am trying to get my preferences by this:
SharedPreferences preferences = this.getActivity().getSharedPreferences("storedName", Context.MODE_PRIVATE);
String loginemail = preferences.getString("storedName", "");
but this doesn't seem to work, i have multiple sharedPreferences which i need to get in my fragment what is the correct way to do it?
As getDefaulSharedPreferences(this) doesn't work.
i store my prefs like so:
savePreferences("shareUniqePass", uniqePassIds.getText().toString());
savePreferences("storedName", inputEmail.getText().toString());
savePreferences("Storedpass", inputPassword.getText().toString());
private void savePreferences(String key, boolean value){
SharedPreferences sharedPreferences = PreferenceManager
.getDefaultSharedPreferences(this);
Editor checkbox = sharedPreferences.edit();
checkbox.putBoolean(key, value);
checkbox.commit();
}
private void savePreferences(String key, String value){
SharedPreferences sharedPreferences = PreferenceManager
.getDefaultSharedPreferences(this);
Editor names = sharedPreferences.edit();
names.putString(key, value);
names.commit();
}
Instead of getting it from getSharedPreferences use the getDefaultSharedPreferences.
As getDefaulSharedPreferences(this) doesn't work.
You used getDefaultSharedPreferences for saving the data and therefore you must use getDefaultSharedPreferences to get the data that was saved.
this mean the instance of your fragment instead use the getActivity() to get the instance of context from your activity.
sample:
String loginemail = PreferenceManager.getDefaultSharedPreferences(getActivity()).getString(PREF_USER_NAME, "");;
You need to make sure that your saving and loading the data from the same shared preferences. If you're only accessing it from the one activity / fragment, you should use getDefaulSharedPreferences(this).
If, however, you're going to use it from several different activities / fragments, you should use:
private void savePreferences(String key, boolean value){
SharedPreferences prefs = getActivity().getSharedPreferences("storedName", Context.MODE_PRIVATE);
Editor checkbox = sharedPreferences.edit();
checkbox.putBoolean(key, value);
checkbox.commit();
}
I found all answers here and tried all solutions, still my shared prefs are not persistent.
Here's my code:
public static void setActivated(boolean activated) {
SharedPreferences sp = Utils.getContext().getSharedPreferences(
USER_PREFS, Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sp.edit();
editor.putBoolean(ASD, activated);
editor.commit();
}
public static boolean isActivated() {
SharedPreferences sp = Utils.getContext().getSharedPreferences(USER_PREFS, Context.MODE_PRIVATE);
return sp.getBoolean(ASD, true);
}
I've tried also:
editor.clear();
editor.put ..
editor.commit();
I've also tried with
editor.apply();
I even tried with both .apply() and .commit() and no luck.
Another idea was to try using a different mode for the files:
...getSharedPreferences(USER_PREFS, Context.MODE_MULTI_PROCESS);
The problem is that the values saved are not persistent. If I close the app and then re-open it the values are all wrong.
Does anyone have any ideas? I would also mention that the problem is only on some devices, for example HTC One S, Samsung Galaxy S3 (I tested on a different S3 and it worked perfectly).
EDIT: I call the save on a button click listener and I call isActivated when I load the fragment (after onViewCreated()).
Thanks!
Hi I think it should work. If clearing does not work, you could try the second option as detailed in my solution:
You have 2 options:
Get shared preference value during the life-cycle of the activity.
Call .clear before .commit
See my answer:
Android Persistent Checkable Menu in Custom Widget After Reboot Android
public abstract SharedPreferences.Editor clear()
Added in API level 1 Mark in the editor to remove all values from the
preferences. Once commit is called, the only remaining preferences
will be any that you have defined in this editor. Note that when
committing back to the preferences, the clear is done first,
regardless of whether you called clear before or after put methods on
this editor.
Returns Returns a reference to the same Editor object, so you can
chain put calls together.
In my user preferences class I was getting a null value on some other strings and my code was something like this:
SharedPreferences sp = Utils.getContext()
.getSharedPreferences(USER_PREFS, Context.MODE_PRIVATE);
SharedPreferences.Editor editor = sp.edit();
if (session != null && !"".equals(session)) {
sessionId = session;
editor.putString(SESSION, sessionId).commit();
} else {
sessionId = null;
editor.clear().commit();
}
The editor.clear() was resetting all my other commits!
I don't know why, but it is working by just putting your prefs code inside the async task:
prefss = getSharedPreferences(ACCOUNT_PREFS_NAME, MODE_MULTI_PROCESS);
new AsyncSave(favNamesList).execute();
private static class AsyncSave extends AsyncTask<Void, Void, Boolean> {
String favNamesList;
AsyncSave(String favNamesList) {
this.favNamesList = favNamesList;
}
#Override
protected Boolean doInBackground(Void... params) {
prefss.edit().putString("favNamesList", strings).apply();
return null;
}
}
activity.getPreferences(mode) and sharedPreferences.edit()
Can I do this?
(at some Activity class):
//...
private SharedPreferences pref;
private Editor editor;
onCreate() {
pref = getPreferences(Activity.MODE_PRIVATE);
editor = pref.edit();
}
onDestroy() {
int someSavedInt = pref.getInt("SomeInt", 0);
editor.putInt("SomeInt", someSavedInt * 2);
}
//...
Or always before use should I get value of pref and editor?
you can create static variable of shared preference too. or can get it each time, both are fine.
Just keep in mind you have to do editor.commit(); to save/commit these values always.
I'm trying to write an activity that would be able to both write and read sharedpreferences data.
I initiate SharedPreferences at the beginning
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
Then this function writes an int to SP and call another function.
public void SetHue(int i)
{
SharedPreferences.Editor editor = preferences.edit();
editor.putInt("storedInt", i); // value to store
editor.commit();
ApplyHue();
}
this other function should read that int from SP...
public void ApplyHue()
{
int hueInt = preferences.getInt("storedInt", 0);
/// adjust background image hue according to hueInt.
}
I can't simply pass this int from one function to another, because I need other activities to be able to run ApplyHue() function, which should use hueInt from memory.
What do you think might be causing it to crash?
Thanks!
I think you wrote this line in the class before your onCreate method.
SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(this);
Decalare SharedPreferences preferences; in the class and then in onCreate
preferences = PreferenceManager.getDefaultSharedPreferences(this);
Hopefully your problem will be solved