What is the job of an Object I am binding to? - objective-c

When I use Interface Builder > Inspector > Bindings to set up an binding for one of my view Items (i.e. an textfield), then I have to specify an object to which this view item will be bound to.
So I am wondering now, what exactly is the job of this object I specify in "Bind to:"?
I assume that Interface Builder automatically creates some methods which do all that synchronization stuff. Is that right?
And what does it mean when I "Bind to: File's Owner"? Is that my file with the main-Method inside?

… what exactly is the job of this object I specify in "Bind to:"?
You bind your view to your controller. The controller owns the model; the controller key you bind to is the name of a property that serves up some part of that model. The model objects have their own properties, and you may (in some cases must) provide a model key path along with the controller key.
I assume that Interface Builder automatically creates some methods which do all that synchronization stuff. Is that right?
Nope. IB never ever creates methods. The Bindings system does all that synchronization stuff, and it already exists. IB just calls it (specifically, it calls the bind:::: method I mentioned in my answer to your other question).
And what does it mean when I "Bind to: File's Owner"?
The File's Owner is the object that owns all the top-level objects in the nib file. The owner of the MainMenu nib is the application object (NSApp). In a document-based application, the document object will load a nib containing the document window; as such, it is the owner of the window, along with any other top-level objects in that nib.
Is that my file with the main-Method inside?
There's no such file, because there's no such method. There is a main function, but it's a function, not a method of an object. There's no object there, so you can't bind to it.
And you can't bind to a file, only an object. The source files disappear* when you link the program into a single executable. The executable contains only classes and functions, and the nibs contain objects (instances of the classes).
If you're asking which file is being owned, it's the nib file (or, more precisely, its contents—but “File's Contents' Owner” is a bit long).
*Well, except for debug symbols, which identify the filename and line number of each instruction.

The object you bind to has to be key value coding and key value observing compatible. Bindings is just a wrapper that use both those technics in a way that results in much less code.
If you really want to know how it works, there's an entry in Mike Ash's blog how KVO works..
I don't know if you want that much details. I suggest that you read the intro to bindings of cocoadevcentral.com. It makes a fairly good job at explaining them.
To your specific question about the File's Owner, Apple writes:
Each Cocoa application has a main nib
file that contains the
application-specific menus and
possibly one or more windows. NSApp
is File's Owner of the main nib
file. When an application launches,
NSApp loads the main nib file,
unarchiving it, and displays the menus
and initial windows.

Related

What are the correct connections for App Delegate and Application

Unannounced, the 2 notices in the image below were discovered while searching for why -applicationShouldTerminate: is not being called in AppDelegate.m on quit (Cmd+Q). It worked some time ago.
Hovering over the two yellow triangles reveals:
NSObject does not have an outlet named delegate.
The action 'terminate:' is not defined on 'NSObject'.
Xcode is not showing errors or warnings and the app builds.
-applicationShouldTerminateAfterLastWindowClosed: IS called within AppDelegate.m when the red dot of the window is clicked.
My experience with Cocoa is thin (learning). I've compared the connections for File's Owner, Application and App Delegate in 2 other projects, and think a missing window outlet might be the cause. The notices above point to something else.
I would like to make sure the connections are correct as a first step. How do I repair this?
Edit: Add image of Main Window Controller connections
Edit 2: Add image of File's Owner connections
In the main NIB of an application, the two placeholders, File's Owner and Application, both end up referring to the same object. That object is the application object, the sole instance of NSApplication or a custom subclass of it. The Application placeholder is always holding the place of the application object because that's its purpose. The File's Owner placeholder is holding the place of whatever object is specified as the NIB's owner when it is loaded at run time. When Cocoa loads the main NIB at application startup, it specifies the application object as the owner. For other NIBs, File's Owner will likely be some other object.
However, Interface Builder doesn't know that a given NIB is the main one. So, it treats those two placeholders independently.
I don't know why Interface Builder has taken to setting the class of the Application placeholder to NSObject. It should really be NSApplication. That's why Interface Builder doesn't realize that the application object has a delegate outlet and an action method -terminate:.
As it happens, the class of File's Owner is properly set to NSApplication.
So, there are two ways to fix this:
Set the class of the Application placeholder to NSApplication or, in the rare case that you're using a subclass, that subclass.
Disconnect those connection from the Application placeholder and connect them to File's Owner instead. This is the way that the standard project templates do it.
For any given main NIB, you should probably standardize on using one or the other but not both. That is, one or the other should have no connections. That way you avoid conflicting or redundant connections.

Cocoa - explanation of view handling

I'm learning Cocoa at the moment, and have followed 'generic' tutorials on getting a basic form with a button and label.
With the .xib, I've added an 'Object' (instance of NSObject subclass), and have also created a ViewController class, which I connect to my view by setting Custom Class to ViewController. I then code up my ViewController.h and .m files adding a pressedButton method, and a label (myLabel). This all works OK (ie. the label updates when the button is pressed).
My question is: what am I actually doing with this process in C++ terms (a language I'm more familiar with)? As I understood it, my 'Object' (set to class ViewController) represents an instance of the .xib file (may be wrong here), and with this set to the ViewController class, I'm able to make outlets and actions in ViewController.h/.m, but I'm still not sure what's really going on behind the scenes.
Lastly, the XCode template provides an AppDelegate class 'free'. Given I'm managing my controls via my ViewController class, what would this file/object be used for - is it for application specific things that do not relate to the view itself, or is it also used to manage the controls on the form too (like you see in some tutorials I think)?
I hope, I understood the first part of your question well. The .xib (xml verison of nib file) does not represent a class or object. It is rather used to create a view object with all its subviews (each an object) and link it properly to your view controller.
It is most common and automatically generated that way, that the underlying view within your nib file corersponds to self.view (from your view controller's point of view).
You could access each view created by the nib file by navigating though the subview hierarchy of self.view. Alternatively you could define tags within nib/IB (Interface builder) to access individual view objects more easily.
"Just for your convenience" the IBOutlets were introduced. You can define an IBOutlet in the interface of your view controller and link it using IB to the dedicated object that is created using the xib file.
I am saying "Just for your covenience" because it is not really neccessary, considering other ways of addressing your view objects. But it is more than convenient and therfore strongly recommended and stimply the standard way of doing it.
You could even add further views programmatically to a form/view that was created using IB. You can change properties of those views programmatically.
The view and the subvies are created in that very moment when your view controller is initialized with a nib file using the initWithNibName:bundle: method. Then the nib file (xib these days) is opened, its content is parsed and interpreted and all views are created and added to their superviews respectively and their properties and action: selectors etc. are set accordingly. Again, the whole process is designed for your convenience. You could even create all the views etc. programmatically - witout any nib file at all. The loadView method of your custom view controller would be the appropriate place of dong so.
Second question:
AppDelegate is designed for application wide actions etc. If you can manage everything fine within your view controllers then you would not need to change anything on the AppDelegate.
It is often used as a container for variables or functions of global character (which are then properties and members of the app delegate object). Sometimes you may see it neccessary to override some of the AppDelegates methods like application:didFinishLanuncing or applicationDidBecomeActive.
Strictly spoken, UIApplicationDelegate is no class that you subclass. It is a protocol that you implement. (Very much like interfaces within Java - sort of overcoming the lack of multiple inheritance that you are familiar with from C++).

What is the need of File's owner in xcode xib files? Can i do the same things without file's owner?

Why should I set File's Owner's Class Identity rather than the Class Identity of my custom object that is shown in the nib and make the connections from it? What happens if I set file's owner to nil?
To me everything works fine with nil file's owner so what is the deference in doing the connection from it?
A NIB represents an archived object graph. You can load it and that object graph will be reconstituted. The thing, you usually want/need the newly-loaded object graph to be hooked into the already-existing object graph of your program. You don't want it to be standing apart, disconnected from everything else.
There are a few ways that the newly-loaded object graph can get connected to the rest of the program's object graph. One way is the set of proxy objects available in a NIB. There's one for the application object. Another such proxy object is File's Owner. A proxy object is a thing which has a representation in the NIB but is not actually contained in the NIB. Unlike the other objects in the NIB, the objects represented by the proxies are not created when the NIB is loaded, they exist before the NIB is loaded. The proxies allow connections between these pre-existing objects and the objects in the NIB. That's how the new object graph from the NIB can be connected to the existing object graph of your program.
The MainMenu NIB is unusual. It is automatically loaded at application startup by Cocoa, which means there isn't (can't be, really) much in the way of pre-existing objects. That NIB also usually contains an instance of the app delegate, which is a kind of coordinating controller. Usually, though, other types of NIBs would not contain coordinating controllers. (They do contain mediating controllers, like NSArrayController, but that's different.) Rather, coordinating controllers are typically created in code and, often, they are responsible for loading NIBs.
For example, you would use an NSWindowController as the coordinating controller for a window. The window would be defined in a NIB. The window controller would be instantiated in code – whichever code decides that a window should be created – and it would load the NIB. It would be the File's Owner of the NIB, too. It would manage the window and the top-level objects of the NIB.
If you are setting the File's Owner to nil, then a) you probably are dealing with very simple NIBs at this point, and b) you may be leaking top-level objects from the NIBs that you load.
File's owner is the file that contains all the IBOutlets and IBActions for that view. For example, if you have a class "ViewController" and it contains an IBOutlet UIButton *button and -(IBAction)changeViewWhenButtonPressed: (id) sender, the only way you can connect the outlet and action is through setting "ViewController" as your view's File's Owner.
I am relatively certain that Class Identity is synonymous with File's Owner.
Also, these links might be helpful:
What are File Owner and First Responder in iPhone SDK - xCode?
File's Owner Definitions
What is File's Owner
The “file's owner” is the way that objects in the nib can refer to objects outside the nib, and vise versa. (There are also some more complex ways to do that, but they're not used as often.) If you don't need to do that, you don't need to use file's owner.
For the main app, the file's owner is the Application object. You might not have a need to make connections to it, if all your application logic is in a custom class also instantiated in the nib and if you use “first responder” for action messages sent to the application. This is OK.
If you have a document window or popover or something, frequently the file's owner is the object being viewed, and so it's useful to be able to attach ui to it. You might load the same nib many times, each 'owned' by a different instance of that class — a different document or inspected-object or something.
(Fundamentally, the file's owner is just whatever object was passed to the "owner:" parameter in the nib-loading method.)

XCode/Cocoa Objective-C - A couple questions

Sorry for the stupid post, but I am new to Objective-C programming and Cocoa and have a couple of questions which I can't find the answers to, I'm hoping someone can enlighten me.
Firstly, in XCode, when using the Interface builder, when I want to create a new object I drag the object to my 'assets'. However I can't specify methods or anything without manually creating a new class file. Is there any point using the interface builder's 'object'?
The first app I built to test things with, I put most of the code in the AppDelegate class files. Research has shown me that the AppDelegate's purpose is simply handling application events like launching and closing. Was I wrong in putting the methods in this class? Does it make any difference?
Finally, if I have several class files created, each handling their own functionality with an interface built and linked to the classes, then what do I do with the 'main' file? It seems to me that the 'main' file and 'appdelegate' class files will be for the most case left as-is?
I hope that makes sense. Again i'm sorry for the silly-sounding questions but I can't find any answers.
Thanks in advance everyone!
Firstly, in XCode, when using the Interface builder, when I want to create a new object I drag the object to my 'assets'. However I can't specify methods or anything without manually creating a new class file.
Sure you can. Just set the class of the object using the inspector.
Note that you can only connect nib objects to an outlet or action. You can't specify any random methods, nor should you—the whole point of the IBOutlet, IBOutletCollection, and IBAction keywords is to declare in code that these properties/methods are used by a nib.
Is there any point using the interface builder's 'object'?
Yes, but pretty rarely. Usually you create objects in code and connect outlets to them.
The application's delegate is one object you may want to create in the MainMenu or MainWindow nib, if you build your application that way (the iOS templates have changed away from it for some reason).
The first app I built to test things with, I put most of the code in the AppDelegate class files. Research has shown me that the AppDelegate's purpose is simply handling application events like launching and closing. Was I wrong in putting the methods in this class?
Probably. The application's delegate generally should only handle business relating to the NS/UIApplicationDelegate protocol.
On the flip side, it's OK to make your root view controller the application's delegate, if it makes sense to do so (and the NS/UIApplicationDelegate implementation code is not too voluminous). The question you have to answer—and only you can answer it for your application—is whether you are making your root view controller the application's delegate or the application's delegate the root view controller. If in doubt, keep them separate.
Does it make any difference?
Long-term, yes. It's very easy, especially in the class of the application's delegate, to create a Big Ball of Mud class—one without well-defined and clearly-delineated responsibilities. Take dynamite to such a class as soon as possible.
Finally, if I have several class files created, each handling their own functionality with an interface built and linked to the classes, then what do I do with the 'main' file? It seems to me that the 'main' file and 'appdelegate' class files will be for the most case left as-is?
Yes. They're boiler-plate.
If you haven't written any code in the application's delegate (or have removed everything you had put there into new and better-delineated classes), such that all that's left are empty method bodies or none at all, you can safely remove the application's delegate. You can always create it again later if you change your mind.
Note that if you delete your application delegate class, you should also change the main.m file—or the MainMenu/MainWindow nib, if you have one—to not refer to it. Your application won't build if your UIApplicationMain call (or any other code) refers to a class that doesn't exist, and it will crash if your MainMenu/MainWindow nib (or any other nib) refers to a class that doesn't exist.
There is no shame in your application having a delegate if you need it to, but if you don't, removing it and the class you were using for it eliminates future temptation to stuff code there or use it to store third-order globals.
The point of using objects in interface builder is to connect methods of the object to UI elements.
It partly depends on what your methods are doing, but for the most part the app delegate class is going to be left alone. It isn't an actual requirement (your program will work either way) but it is common practice because it generally creates more maintainable code. The app delegate should just handle the application events ( using other classes to do any complex logic or heavy lifting ).
The 'main' file will most likely not change. I can't think of any reason to do so, but I wouldn't rule it out for some advanced cases.
To be honest I only used the Object thing in IB once, when I wanted a separate object to have some UI bindings.
About the app delegate and main file, yes, you'll leave them as-is most of the time. But if you try to do something besides test apps you'll need to handle open events to, for example, connect to a server, ask the user for a review, increment some launch counter, etc... Those are just examples!
The main file I advise you to left it alone and use the object oriented tools provided. You should have a view controller hierarchy, isolate your views from the data, and use the view controller to comunicate between view and model. Read about MVC if you want more info on how your application should be organized.

What describes the "File's Owner" best in objective-c / cocoa Nib?

Unfortunately, the explanation of File's Owner is pretty short at the Apple docs. I know it is an proxy object. But what's really the point about that "File's Owner" object? What is it good for?
Nib files are often referred to as "freeze dried" and ready to run, and they are a great way of making your apps more modular which can reduce memory usage. Nib files can be defrosted, or loaded into memory anytime when the app needs the objects inside it.
Whenever a nib file is defrosted, it needs a pointer to the object that defrosted it. And that object is usually, the File's owner. The File's owner allows objects inside the nib file to access objects that existed before the nib file was defrosted. In a way, the File's owner acts as a bridge between newly loaded objects and old objects.
It's easier to understand the meaning of the File's Owner reference if you read about and understand the nib loading process.
https://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/LoadingResources/CocoaNibs/CocoaNibs.html
Cocoa's frameworks handle many nib loads automatically on your behalf, with one of Cocoa's own built-in classes serving as the controller class that manages, or "owns" the nib file's instantiated objects. When you load your own nibs manually, you get to choose which class will serve as the file's owner.
When you read about the nib loading process, pay attention to the "owner:" parameter on many of the loading methods. Its exactly this object that will be connected to the objects in your nib file as File's Owner
I know it is an proxy object.
It's not. It's a real object. The icon in the nib is a proxy only in the sense that all the other icons represent objects archived in the nib, and the File's Owner isn't. But the FO is not a proxy object in your application.
But what's really the point about that "File's Owner" object? What is it good for?
It's the object that owns the objects in the nib.
That's it. Nothing more to it than that.
Best way to explain it is with an example of how to set it up. Let's say you have an NSWindowController subclass which is a controller for a preferences window. The preferences window is in a NIB called "Preferences".
In your NSWindowController subclass you would have the following init method:
- (id)init {
if (self = [super initWithWindowNibName:#"Preferences"]) {
//do initalisation
}
return self;
}
This initialises the window controller, associating it with the nib named "Preferences" in the application's main bundle. Note that the NIB has not yet been loaded (this will happen when you first call -window on the window controller.
In the Preferences NIB you would then click on the File's Owner icon and then go to the Class Info panel of the Inspector. In here you would set the class to the name of your window controller class (eg PreferencesController). This now represents an instance of your window controller so you can connect up outlets and actions.
While editing in IB it is just a proxy of the object, as with any object you drag to the NIB, but when the NIB is loaded it will be set to the window controller you created.
http://www.cocoadev.com/index.pl?FilesOwner
In essence, whichever object loaded the NibFile becomes the file's owner for that nib file.