多窗口/ NIB可可应用程序的问题

时间:2010-02-04 03:18:05

标签: cocoa interface-builder cocoa-design-patterns

我的Cocoa应用程序出现问题。我正在使用我的app委托作为控制器,并在NIB文件中打开一个窗口。单击工具栏按钮将打开另一个NIB的另一个窗口。单击第二个窗口上的save将调用app delegate / controller上的方法。这一切都很好。

奇怪的是,我无法弄清楚当我单击工具栏按钮时,应用程序委托指向一个内存位置,在第二个窗口上单击保存后指向不同的内存位置。这就好像正在创建第二个应用程序委托/控制器,虽然单步执行代码并没有给出任何关于这种情况的指示。

有没有更好的方法来构建这种类型的应用程序?知道我哪里出错了吗?

1 个答案:

答案 0 :(得分:2)

听起来你正在窗口的nib文件中创建AppController类的第二个实例。您不能这样做,当nib在运行时取消存档时,将实例化nib文件中对象的每个实例。这意味着如果AppController中有MainMenu.xib个实例,而MyWindow.xib文件中有AppController个实例,则First Responder对象将被分配并初始化两次。

通常,处理此问题的方法是使用响应程序链。在您的Window笔尖中,您将-respondsToSelector:指定为您的操作的目标。这意味着当调用action方法时,如果应用程序通过调用NSApplication方法并传入操作选择器来响应方法,那么应用程序将询问当前关注的视图/控件(具有第一响应者状态的视图/控件)

如果第一个响应者没有响应该方法,则消息沿着响应者链向上移动,直到找到响应该方法的对象。如果没有对象响应该方法,NSBeep()实例将对其进行处理并调用NSApplication

在将方法发送到AppController实例之前,会询问应用程序委托是否响应选择。在这种情况下,如果您的[[NSApp delegate] yourMethod]对象被设置为应用程序委托,它将从窗口nib中的对象接收作为操作发送的消息。

如果不够清楚,则值得阅读Event Handling guide

您没有拥有来使用响应者链。您可以通过调用NSWindowController在应用程序委托上调用方法。您还可以通过将其作为实例变量添加到加载nib并在创建时设置它的- (id)initWithAppController:(id)aController { self=[super initWithWindowNibName:@"YourWindowNibName"]; if(self) { appController = [aController retain]; } return self; } 对象来存储对app控制器的引用,如下所示:

{{1}}

您的窗口控制器可以直接调用AppController的方法。