views:

162

answers:

3

So I'm beginning to learn how to use Cocoa. I think I've pretty much got it but I'm hung up on creating and switching views. I'm rewriting a game I made a little bit ago for practice. All I want is one window (preferably not resizable) and I want to be able to switch out views for different screens in the game.

First, I have the main menu (Start Game, High Scores, Exit). Then I need a window for each screen (Gameplay screen, Highscore screen).

What I'm getting confused with is how to design this. I looked up NSViewController thinking it manages views but it doesn't. It only manages one view by loading it really. I don't understand why I'd need to use NSViewController then. Couldn't I just have a window class that contains multiple subclasses of NSView and load them like that? I'm not sure I understand the purpose of the ViewController.

Does my Window Class really need to subclass NSWindowController? I was trying to follow the example of Apple's ViewController example and it has a window controller class that's a subclass of NSWindowController. I don't see what the purpose was of subclassing that. All NSWindowController seems to add is - initWithPath:(NSString *)newPath but I fail to see the use in that either when I can just edit the plist file to open the window on start up. Apple's example also has an NSView variable and an NSViewController variable. Don't you only need one variable to store the current view?

Thanks in advance guys, I'm really confused as to how this works.

+1  A: 

Use following functions defined in UIVew (which is part of your existing window)

- (void)addSubview:(UIView *)view
- (void)removeFromSuperview
Girish Kolari
I'm doing Cocoa on the Desktop right now.
David Garcia
same interface in available in Desktop (NSView)
Girish Kolari
So what I'd like to know is why should I use NSViewController. Should I? Should I make a subclass of NSWindowController with an NSView and NSViewController variable? I'm not sure what is really necessary to make a window with switchable views. From my understanding, I don't need NSViewController at all but I don't know since Apple's example used it and it's supposed to make things easier for you.
David Garcia
You can do view replacement decision can be done in ViewController.Apple Document: " An application changes the content of that window by presenting a new set of views using a view controller object."
Girish Kolari
+2  A: 

You use NSWindowController and NSViewController to manage a window or a view because you should only need to create subclasses of NSWindow or NSView for new "kinds" of window or view. For example, if you wanted to use a circular window, you would subclass NSWindow. If you just want to have controls in a window, you subclass NSwindowController.

It's the same with NSViewController: Generally an NSViewController's view will be of some base class such as NSView (or perhaps your own NSView subclass that draws a custom background). The NSViewController manages the interaction among the subviews of that view, allowing it to act as a single unit within your larger application.

Think of it this way: Views draw, and they turn raw input events into higher-level actions. Controllers supply information to views, and handle actions.

Composing things this way can greatly improve the modularity of your code, making it easier to design, write, and debug.

Chris Hanson
I guess that makes a bit more sense. Do you think I'd have to use `initWithNibName:bundle:` to load the view or could I just set the view's "File's Owner" to the ViewController?
David Garcia
You need to do both. You use `-initWithNibName:bundle:` to instantiate your NSViewController subclass. That loads the specified nib file and acts as its File's Owner; set the class of the nib's File's Owner to your NSViewController subclass, and point File's Owner's "view" outlet at your view.
Chris Hanson
A: 

It sounds like you're trying to swap out the content view within a window? If that is the case, you can use -[NSView replaceSubview:with:] with -[NSWindow contentView] as the receiver.

Say you have a title page named titleView and a menu page named menuView and you want to swap these in and out of your application's main window. If the title page is visible and the user clicks on a "main menu" button or link, you would put something like this in the button's delegate method:

[[[NSApp mainWindow] contentView] replaceSubview:titleView with:menuView];

Two things to be aware of:

  1. The old view, titleView in this case, is released by this call. If you want it still be available, you will have to retain it prior to replacing it.
  2. The parent view will not resize if your pages have different dimensions. Changing the frame size of the window, and therefore the contentView is easy enough, but you can add a little Core Animation into the mix to give it some style.

I hope this helps!

Paul
Alright, thanks! I'll look into that as well. You guys are all really helpful.
David Garcia