Default defaults

How can I read a plist file in my bundle? I’d like to manage this file and read it into my defaults’ registerDefaults so it must be a record obviously, I tried looking for it in the docs but I see core foundation C classes, so I don’t know how to handle it.

Use NSDictionary’s dictionaryWithContentsOfFile: class method.

Thanks :slight_smile:

New user defaults problem.

I googled methods of wiping the prefs plist file and got:

valgloprefs's setPersistentDomain_forName_({},valident)

and

valgloprefs's removePersistentDomainForName_(valident)

considering I have in the finish-launching handler:

		tell current application's class "NSBundle" --get file locations
			tell its mainBundle()
				set valident to its bundleIdentifier()
				set valpreffile to (its pathForResource_ofType_("defaults", "plist")) as string --gets text file containing default prefs
			end tell
		end tell
		set valgloprefs to NSUserDefaults's standardUserDefaults()
		valgloprefs's registerDefaults_(NSDictionary's dictionaryWithContentsOfFile_(valpreffile))

with the ‘defaults.plist’ containing empty and default arrays and dictionaries.

When I use different methods to set some key-values (which I checked work perfectly) and then invoke either of the top two, nothing happens, I have done this without touching the plist myself from a clean build and trashed plist, only opening/quick looking from finder after a cmd-q.

Help please :slight_smile:

What do you expect by calling setPersistentDomain:forName: ?

This method is to access other defaults domains as the own one.
For example to change the primary language you have to read the global preferences with


NSMutableDictionary *globalDomain = [[defaults persistentDomainForName:NSGlobalDomain] mutableCopy];

make the changes and write it back with


[defaults setPersistentDomain:globalDomain forName:NSGlobalDomain];	

to store values into the own defaults file use setObject:forKey: or the derived methods for specified classes or primitive types. Then use the synchronize method to write the preferences to disk.

As written, I want to replace the plist dictionary with {} or delete it all together. I want it to be able to handle keys I didn’t know were there.

I got this from a webpage where a guy states that:

[[NSUserDefaults standardUserDefaults] setPersistentDomain:[NSDictionary dictionary] forName:[[NSBundle mainBundle] bundleIdentifier]];

“In other words, it removeObjectForKey for every single key you ever registered in that app.”

-In his words, this is what I want anyway, all key-values removed.

Your problem may be that AS no such thing as an empty record; {} is an empty list. So you may have to make an empty dictionary and use that:

set emptyDict to current application's NSDictionary's dictionary()
valgloprefs's setPersistentDomain_forName_(emptyDict,valident)

Thanks, I’ll try that, but then why wouldn’t removePersistentDomainForName_(valident) work. When I read the webpage I then looked at docs and found the remove one which really makes more sense, but this doesnt work. Perhaps remove… Doesn’t do what I think.

I just checked the valident is good because valgloprefs’s persistentDomainForName_(valident) returns:

Sadly you get the same log from:

valgloprefs’s setPersistentDomain_forName_((NSDictionary’s dictionary()),valident)
valgloprefs’s synchronize()
log valgloprefs’s persistentDomainForName_(valident)

Edit: I have a workaround, but I still want the proper NSUserDefaults way.

set valprefdict to valgloprefs's persistentDomainForName_(valident)
repeat with valkey in (valprefdict's allKeys()) as list
	valgloprefs's removeObjectForKey_(valkey)
end repeat

Bump :slight_smile:

Hello everybody,

I re-open this post because I have a similar problem. When my app is launched for the first time, there is no defaults set for my Preferences dialog, so the bound values are NIL and the controls appear empty (no radio button enabled, for example).

I’d like to set initial values, which could also be the “factory settings” and create an appropriate button+handler that allows to revert to them. How can I do this? Is it possible to make the NSUserDefaultsController read the values defined into the .xib file and store them as factory settings, or have I to duplicate the .plist file created when the values are set, put this copy into the main bundle and make the NSUserDefaultsController read it? I suppose Cocoa has something to handle this usual problem?

Regards,

You just use registerDefaults: Put that in you applicationWillFinishLaunching method, and pass it an applescript record with pairs of keys and values you want to have when the program first opens. If you later change those values, and they are put in the pList, those values will be used instead – these will be the factory defaults.

Ric

This was my solution with a plist in my bundle named defaults.plist with my default defaults:

tell NSBundle--get plist file location and bundle identifier
	tell its mainBundle()
		set valident to its bundleIdentifier()
		set valpreffile to (its pathForResource_ofType_("defaults", "plist")) as string --gets text file containing default prefs
	end tell
end tell
set valgloprefs to NSUserDefaults's standardUserDefaults()
valgloprefs's registerDefaults_(NSDictionary's dictionaryWithContentsOfFile_(valpreffile))

It seems to work. But to be sure, could you check this code:

the file “atxtdefaults.plist” is a copy of the regular plist file, now part of the project. Is it OK?

Note: I briefly thought to make a single line of code from the two above, just for fun. :wink:

As long as the factory defaults plist is in your bundle, is a file in its own right, it should work. When in doubt release it onto a different machine in /Applications

You should be able to set it up to how you like, I myself created a new plist in my bundle, outlined properties with factory defaults and wrote the normal user defaults code after, but that was a large move towards plists from txts to be fair.

So it’s OK:

.

– in applicationWillFinishLaunching_ :

.

I was using the class not the controller.

What do you mean by “the class”, is it the NSUserDefaults class?

The NSUserDefaultsController is also a class, I use the single instance of it. I also use NSArrayControllers instead of accessing the controlled object directly, it’s just a matter of style. I like controlling the controller. :wink:

And according to the docs, «NSUserDefaultsController is a concrete subclass of NSController that implements a bindings-compatible interface to NSUserDefaults. Properties of an instance of NSUserDefaultsController are bound to user interface items to access and modify values stored using NSUserDefaults.»

It’s much better for my app, as I have a Preferences Window which allows my user to set his preferred values and watch the result at real-time.