Saving NSMutableDictionary containing UIButtons in the NSUserDefults - ios

I am trying to save a NSMutableDictionary containing UIButtons in the NSUserDefults in this way:
[UserFolderDictionary setObject:FolderButton forKey:[NSString stringWithFormat:#"%ld", (long)numberFinal]];
[[NSUserDefaults standardUserDefaults] setObject:UserFolderDictionary forKey:#"UserFolderDictionarySaved"];
The app crashes with the error 'attempt to insert non-property list object'. To re-catch it I tried this:
NSMutableDictionary* UserFolderDictionary = [[[NSUserDefaults standardUserDefaults] dictionaryForKey:#"UserFolderDictionarySaved"] mutableCopy];
FolderButton is a normal UIButton with a tag and a background image.

You can't save buttons in NSUserDefaults, and furthermore you SHOULDN'T save buttons in NSUserDefaults.
Buttons are view objects, not model objects. You should save state information from your buttons, and then use that information to recreate your button.

You may try this.
`
NSUserDefaults *userDefaults = [NSUserDefaults standardUserDefaults];
[myDictionary setObject:button forKey:#"myBtn"];
//save nsdata
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:myDictionary];
[userDefaults setObject:data forKey: #"SavedBtn"];
[userDefaults synchronize];
//now retrieve it
NSData *data1 = [userDefaults objectForKey:#"SavedBtn"];
NSDictionary *dict = [NSKeyedUnarchiver unarchiveObjectWithData:data1];
`
Hope that Helps!

Related

Objective-C : Can't set NSMutableDictionary from NSUserDefaults

I'm trying to retrieve an NSDictionary that was saved to NSUserDefaults. When I log out what I'm trying to retrieve, it displays correctly:
NSLog(#"%#", [[[NSUserDefaults standardUserDefaults] dictionaryForKey:#"userdetails"] mutableCopy]);
However, when I try to assign to a variable, it returns as nil.
NSMutableDictionary *test123 = [[[NSUserDefaults standardUserDefaults] dictionaryForKey:#"userdetails"] mutableCopy];
Any idea why?
Check with my working code,
Save like this,
NSData *data = [NSKeyedArchiver archivedDataWithRootObject:yourMutableDictionary];
[[NSUserDefaults standardUserDefaults] setObject:data forKey:#"currentUser"];
[[NSUserDefaults standardUserDefaults]synchronize];
Get dictionary ,
NSData *dictionaryData = [[NSUserDefaults standardUserDefaults] objectForKey:#"currentUser"];
NSDictionary *tempDict = [NSKeyedUnarchiver unarchiveObjectWithData:dictionaryData];
Maybe you can try it use the following code:
[[NSUserDefaults standardUserDefaults] setObject:(NSDictionary *)yourDictionary forKey:yourkey];

App crashing during NSUserDefault data removal

When I call this function my app gets crash.
I got this error : [__NSPlaceholderDictionary initWithObjects:forKeys:count:]: attempt to insert nil object from objects[1].
How i can resolve it please help if you know.
NSUserDefaults *defs = [NSUserDefaults standardUserDefaults];
NSDictionary *dict = [defs dictionaryRepresentation];
for (id key in dict)
{
NSObject * object = [dict objectForKey:key];
if(object != nil)
{
[defs removeObjectForKey:key];
[defs synchronize];
}
}
Kindly use following code. It should help you
NSString *applicationDomain = [[NSBundle mainBundle] bundleIdentifier];
[[NSUserDefaults standardUserDefaults] removePersistentDomainForName:applicationDomain];
You can also use
NSDictionary *defaultsDictionary = [[NSUserDefaults standardUserDefaults] dictionaryRepresentation];
for (NSString *key in [defaultsDictionary allKeys]) {
[[NSUserDefaults standardUserDefaults] removeObjectForKey:key];
}
[[NSUserDefaults standardUserDefaults] synchronize]; //outside loop.
NOTE: The crash which you are mentioning is regarding setValue ForKey in a Dictionary. Kindly user breakpoint and see where you are inserting nil value in Dictionary.
try adding the keys of the desired entries into NSArray inside the loop
then do removeObjectsForKeys:array outside the loop
It's preferable to not remove entries while enumerating inside a for loop
My solution for your question is
NSUserDefaults *defs = [NSUserDefaults standardUserDefaults];
NSDictionary *dict = [userDefaults dictionaryRepresentation];
for (id key in dict) {
[dict removeObjectForKey:key];
}
[defs synchronize];

NSUserDefaults: application.plist is reset whenever app starts

I am using NSUserDefaults to store my app settings/configuration.
The code responsible to saving defaults is below:
NSUserDefaults * standardUserDefaults = [NSUserDefaults standardUserDefaults];
// saving settings
[standardUserDefaults setObject:address.text forKey:#"URL"];
[standardUserDefaults setObject:username.text forKey:#"username"];
[standardUserDefaults setObject:password.text forKey:#"password"];
// synchronize the settings
[standardUserDefaults synchronize];
Indeed, the settings seem to have been saved. I open plist file from Libary/Preferences and see that the values are saved. I see those after my method is finished working and [even after] after closing the app.
My problem: whenever I start my app again, the saved values are gone from the plist file[the keys are still present], and I obviously cannot load my preferences.
Please advise.
You can use to save Settings:
NSMutableDictionary *dictSetting = [[NSMutableDictionary alloc] init];
[dictSetting setValue:address.text forKey:#"URL"];
[dictSetting setValue:username.text forKey:#"username"];
[dictSetting setValue:password.text forKey:#"password"];
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
[defaults setObject:dictSetting forKey:#"SETTINGS"];
[defaults synchronize];
to Retrive Setting:
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSDictionary *dictSettingData = [defaults objectForKey:#"SETTINGS"];
NSString *url = [dictSettingData valueForKey:#"URL"];
NSString *username = [dictSettingData valueForKey:#"username"];
NSString *password = [dictSettingData valueForKey:#"password"];

NSUserDefaults overriding previously saved values

I have two completely separate tasks being carried out but somehow they seem to connect.
In ViewController 1, I have:
NSString *foo = #"foo";
NSUserDefaults *default1 = [NSUserDefaults standardUserDefaults]
[default1 setObject:foo forKey:#"foo"];
[default1 synchronize];
and when I do:
NSLog(#"%#", [[NSUserDefaults standardUserDefaults] objectForKey:#"foo"]);
The value printed is what I expect it to be.
In ViewController 2, I have:
NSString *bar = #"bar";
NSUserDefaults *default2 = [NSUserDefaults standardUserDefaults]
[default2 setObject:bar forKey:#"bar"];
[default2 synchronize];
And same again when I NSLog it, the value is what I expect it to be.
But somehow when i try to print object #"foo" again it gives me the value for the second object, in this case #"bar"
Any guidance on why my original value is being overridden by the second value even tough the variable/key names are different in the 2 classes?
You are doing this for both:
[foo setObject:bar forKey:#"bar"];
Shouldn't it be:
[defaults1 setObject:foo forKey:#"foo"];
And
[defaults2 setObject:bar forKey:#"bar"];
There is however, a greater problem:
NSString *foo = #"foo";
NSUserDefaults *default1 = [NSUserDefaults standardUserDefaults];
[default1 setObject:foo forKey:#"foo"];
[default1 synchronize];
NSLog(#"%#", [[NSUserDefaults standardUserDefaults] objectForKey:#"foo"]);
NSString *bar = #"bar";
NSUserDefaults *default2 = [NSUserDefaults standardUserDefaults];
[default2 setObject:bar forKey:#"bar"];
[default2 synchronize];
NSLog(#"%#", [[NSUserDefaults standardUserDefaults] objectForKey:#"bar"]);
Will work properly, however you're creating defaults1 and defaults2 which are both instances of standard defaults, so:
NSUserDefaults * defaults1 = [NSUserDefaults standardUserDefaults];
NSUserDefaults * defaults2 = [NSUserDefaults standardUserDefaults];
[NSUserDefaults standardUserDefaults];
Are all pointers to the standardUserDefaults singleton. So they are identical instances. You could simply do:
NSUserDefaults *standardDefaults = [NSUserDefaults standardUserDefaults];
NSString *foo = #"foo";
[standardDefaults setObject:foo forKey:#"foo"];
NSString *bar = #"bar";
[standardDefaults setObject:bar forKey:#"bar"];
[standardDefaults synchronize];
NSLog(#"%#", [[NSUserDefaults standardUserDefaults] objectForKey:#"foo"]);
NSLog(#"%#", [[NSUserDefaults standardUserDefaults] objectForKey:#"bar"]);
You can print out the entire set of user defaults with code like this
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSDictionary *dictionary = [defaults dictionaryRepresentation];
NSLog( #"%#", dictionary );
Note that Apple puts lots of garbage in the user defaults, so you'll have to scroll to the end to see foo and bar. I'm guessing that you have a typo in code that you haven't shown us, and either foo is being overwritten, or foo simply isn't being displayed properly.
The current code in your question (after 1 edit) is all good and should work correctly.

How would I save a UIButton's properties and load with a button? [duplicate]

This question already has answers here:
Closed 11 years ago.
Possible Duplicate:
How can I save and load the alpha values of a UIButton in an app?
I would like to save the state of the UIButton (e.g. its alpha value and whether it is hidden or not) and this would then load up when the user quits and reloads the app.
I've tried some bits of code with NSUserDefaults but with no luck.
Could somebody help with some sample code so that I can save and load the button's state?
Thanks,
James
Related to Shaharyar's answer (i don't know how to comment):
in this case you need to use NSNumber.
[[NSUserDefaults standardUserDefaults] setValue:[NSNumber numberWithFloat:SOME_FLOAT] forKey:KEY];
because float is not an object, but NSNumber is one.
EDITED:
1) To make sure your defaults are created after the application runs at first time:
in your AppDelegate's initialize-method:
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
NSDictionary *appDefaults = [NSDictionary dictionaryWithObjectsAndKeys:
[NSNumber numberWithFloat:SOME_FLOAT], #"YOUR_KEY",
nil];
[defaults registerDefaults:appDefaults];
2) Updating defaults after:
NSUserDefaults *prefs = [NSUserDefaults standardUserDefaults];
[prefs setFloat:FLOAT_VALUE forKey:#"YOUR_KEY"];
[prefs synchronize];
3) Read defaults:
NSUserDefaults *prefs = [NSUserDefaults standardUserDefaults];
float FLOAT_VALUE = [prefs floatForKey:#"YOUR_KEY"];
Can you post some of the code?
NSUserDefaults is the place to store such information..
Assumption:
Did you make a call to [NSUserDefaults synchronize] after setting the values?
Code:
// Setting a value
[[NSUserDefaults standardUserDefaults] setValue:VALUE forKey:KEY];
[[NSUserDefaults standardUserDefaults] synchronize];
// Getting a value
NSString *var1 = [[NSUserDefaults standardUserDefaults] valueForKey:KEY];
In your case it would be:
// Setting a value
[[NSUserDefaults standardUserDefaults] setFloat:VALUE forKey:KEY];
[[NSUserDefaults standardUserDefaults] synchronize];

Resources