Добавление видов или окон в MainWindow

Я спотыкаюсь о некоторых базовых понятиях, которые я не могу понять. Надеюсь, кто-то может очистить меня, потому что я не нашел никакого ресурса, который бы объяснил это. Или, может быть, он в ярком открытии, и я просто не вижу его.

До сих пор понятны: MainWindow содержит меню и поэтому более или менее существенен. В info.plist содержится nib, загруженный в appstart.

Не понял до сих пор: я пытаюсь использовать одно окно. Я могу сделать все в appDelegate (пока все прекрасно работает), и у меня может быть дополнительный контроллер, к которому я могу подключиться UIElements от MainWindow до (пока работает, хотя и прекрасно). НО: То, что я действительно хотел бы сделать, есть MainWIndow, у которого есть только меню, а также отдельный контроллер и nib (возможно, даже более чем один из них позже), которые загружаются и добавляются впоследствии.

Мои вопросы:

  • Используйте NSWindowController или NSViewController? И почему? (Я бы использовал NSViewController)

  • Что, где и как создать экземпляр (предположительно в didFinishLaunching appDelegate?)

  • Как добавить окно или представление в одно и только главное окно вместо второго независимого окна (я еще не настроен для multiDocumentApps)

Thanx много, любые мысли оценены!

Ответ 1

Не понял до сих пор: я пытаюсь использовать одно окно. Я могу сделать все в appDelegate (отлично работает до сих пор), и у меня может быть дополнительный контроллер, к которому я могу подключить UIElements из MainWindow (пока работает, хотя и прекрасно). НО: То, что я действительно хотел бы сделать, есть MainWIndow, у которого есть только меню, а также отдельный контроллер и nib (возможно, даже более чем один из них позже), которые загружаются и добавляются впоследствии.

Для ясности MainWindow является файлом nib, поэтому я называю его MainWindow.nib. Это стандартное имя файла nib, указанное в файле Info.plist приложения, в качестве файла nib для загрузки при запуске приложения.

По умолчанию Xcode создает файл MainWindow.nib, содержащий как главное меню, так и главное окно. Вы можете удалить окно из файла MainWindow.nib и добавить еще один файл nib для хранения этого окна. Позволяет называть этот другой файл nib MyWindow.nib.

Использовать NSWindowController или NSViewController? И почему? (Я бы склонен к viewController)

Поскольку у вас есть отдельный файл nib для хранения окна, вы используете NSWindowController. Создайте подкласс NSWindowController, например. MyWindowController, который будет отвечать за управление окном, хранящимся в MyWindow.nib. Этот подкласс будет иметь выходы, указывающие на элементы пользовательского интерфейса в этом окне и потенциально другие объекты, которые вы определяете в MyWindow.nib.

При этом важно, чтобы вы делали следующее в MyWindow.nib:

  • Установите владельца файла как тип MyWindowController;

  • Подключите выход window к владельцу файла к объекту окна.

NSViewController используется для управления представлением, обычно загружаемым из файла nib, и оно не применяется к окнам.

Вы можете повторить это - окно в файле .nib, подкласс NSWindowController для управления этим окном - для того, чтобы сколько угодно окон.

Что, где и как создать экземпляр (предположительно в файле didFinishLaunching appDelegate?)

Поскольку вы хотите использовать одно окно в своем приложении, один из них - для вашего делегата приложения, чтобы удерживать ссылку (переменную экземпляра, объявленное свойство) одному оконному контроллеру, который управляет этим окном. Затем, в -applicationDidFinishLaunching:, создайте экземпляр указанного контроллера.

Например:

// MyAppDelegate.h

@class MyWindowController;

@interface MyAppDelegate : NSObject <NSApplicationDelegate>
@property (retain) MyWindowController *myWindowController;
@end

и

// MyAppDelegate.m

#import "MyAppDelegate.h"
#import "MyWindowController.h"

@implementation MyAppDelegate

@synthesize myWindowController;

- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
    self.myWindowController = [[[MyWindowController alloc]
        initWithWindowNibName:@"MyWindow"] autorelease];
    [self.myWindowController showWindow:self];
}

…
@end

Если вам нужно больше окон, это просто вопрос об объявлении переменных/свойств экземпляра для хранения соответствующих контроллеров и создания экземпляров таких контроллеров, как указано выше.

Как добавить окно или просмотреть одно и только главное окно вместо второго независимого окна (я еще не настроен для multiDocumentApps)

Вы действительно хотите добавить окно в главное окно? Если да, то будем называть вложенным окном. Вы можете использовать вышеприведенный механизм (поместите окно в свой собственный файл nib, подклассом NSWindowController, чтобы управлять им, чтобы ваш оригинальный MyWindowController удерживал ссылку (переменную экземпляра, объявленное свойство) подключенному оконному контроллеру и создать экземпляр/загрузить прикрепленный файл окна nib, если это необходимо), а затем использовать -[NSWindow - addChildWindow:ordered:] для присоединения вторичного окна к главному окну.

Например, рассмотрение MyWindowController имеет объявленное свойство secondaryWindowController, в MyWindowController.m:

- (void)someAction:(id)sender {
    // If the secondary window hasn't been loaded yet, load it and add its
    // window as a window attached to the main window
    if (self.secondaryWindowController == nil) {
        self.secondaryWindowController = [[[MySecondaryWindowController alloc]
            initWithWindowNibName:@"MySecondaryWindow"] autorelease];
        [[self window] addChildWindow:self.secondaryWindowController.window
                              ordered:NSWindowAbove];
    }
}

Если вы хотите добавить представление в главное окно, самый простой способ - сделать это непосредственно в файле nib.

Если вам нужно/нужно сделать это программно, вам нужно иметь ссылку на представление, а затем добавить его в представление содержимого основного окна, например:

[self.window.contentView addSubView:someView];

Вы можете программно создать someView или загрузить его из отдельного файла nib. В последнем случае процедура похожа на описанную выше, но вместо использования подкласса NSWindowController youd использует подкласс NSViewController.

Например, в MyWindowController.m:

- (void)anotherAction:(id)sender {
    // If the view hasn't been loaded yet, load it and add it
    // as a subview of the main window content view
    if (self.someViewController == nil) {
        self.someViewController = [[[MyViewController alloc]
            initWithNibName:@"MyView" bundle:nil] autorelease];
        // You'll probably want to set the view frame, e.g.
        // [self.someViewController.view setFrame:...];
        [self.window.contentView addSubview:self.someViewController.view];
    }
}