Reputation: 1128
I'm very comfortable with writing iOS apps, but OS X unexpectedly seems somewhat alien.
Here's the question upfront (read on for context):
When my application launches using the .xib set in the Main Interface field under the deployment info of my apps target, why does the AppDelegate get instantiated after the ViewControllers?
Context (no pun intended):
The reason I ask is because I'm using Core Data (spare me any heckling for this decision), and typically you keep a pointer to the MOC (Managed Object Context) in AppDelegate. One of my controllers is trying to get this MOC instance variable but the AppDelegate instance isn't around yet and therefore my app doesn't present data just after launch.
The AppDelegate and the two ViewControllers are in the .xib. The VCs are hooked to views inside a split view. They're trying to use the MOC in viewDidLoad to make queries. They are accessing the AppDelegate like this:
let delegate = NSApplication.sharedApplication().delegate as AppDelegate
let moc = delegate.managedObjectContext
This will crash as the .delegate
property of the sharedApplication()
returns nil.
I tried making an NSWindowController from the .xib in applicationDidFinishLaunching
and removing the .xib from the Main Interface field, but then applicationDidFinishLaunching
doesn't get called at all.
I've ensured that all the connections in IB for from the Application and the Files Owner (NSApplcation) delegate IBOutlets to the AppDelegate have been made.
UPDATE - 31/03/15
Stephen Darlington's answer below offers a good solution for my/this case. And as I understand it's actually better to setup the MOC in the way he's suggested.
If a correct answer arrives that explains why the AppDelegate is being instantiated at some later time in the launch process, I'll mark it correct instead of Stephen's. Thanks Stephen!
Upvotes: 1
Views: 159
Reputation: 1128
Here's another option without having to subclass NSApplication:
applicationDidFinishLaunching
method init your view controllers from their .xib files.Upvotes: 1
Reputation: 1128
I also faced this issue with setting up Parse. To get around it, I simply subclassed NSApplication and set it as the Principle class
in the Info.plist
. In your NSApplication subclass, override the init methods and initialise Parse or anything else you need to, there.
Upvotes: 0
Reputation: 52565
The "easy" solution would be to have managedObjectContext
create a MOC if one doesn't exist (i.e., change it from a property to a method). That way which ever code gets there first the stack will be available.
(I'll spare the lectures about both creating the Core Data stack in the app delegate and accessing the app delegate like that!)
Upvotes: 1