我想知道的是我初始化的窗口控制器如何
NSWindowController *c=[[NSWindowController alloc] initWithWindowNibName:@"Win" owner:myObj]
如果 myObj 不是控制器本身,知道它应该在 Win.xib 文件中控制哪个窗口吗?通常我将窗口控制器设置为所有者,这样我就可以在 IB 中设置它的窗口和插座。内存管理是否全部由窗口控制器完成,即使它不是所有者?
我想知道的是我初始化的窗口控制器如何
NSWindowController *c=[[NSWindowController alloc] initWithWindowNibName:@"Win" owner:myObj]
如果 myObj 不是控制器本身,知道它应该在 Win.xib 文件中控制哪个窗口吗?通常我将窗口控制器设置为所有者,这样我就可以在 IB 中设置它的窗口和插座。内存管理是否全部由窗口控制器完成,即使它不是所有者?
窗口控制器将执行顶级对象的内存管理,即使它不是所有者。从NSWindowController
类参考:
不管文件的所有者是谁,窗口控制器都负责释放它加载的 nib 文件中的所有顶级对象。
但是,窗口控制器通常是 NIB 的所有者,连接其窗口插座通常是它知道要控制哪个窗口的方式。也可以使用该-setWindow:
方法显式设置它。
可以想象NSWindowController
在 NIB 的顶级对象中搜索一个窗口来控制插座是否未连接,但我认为它不会那样做。
你有没有观察到一些你不理解的行为?它以前如何?
此方法适用于您拥有基于文档的应用程序的情况;见NSDocument
。在这种情况下,您将创建一个NSDocument
NIB 文件所有者的实例(NSDocument
有一个-setWindow:
方法但没有 getter)。控制器仍然会从文档实例中了解它的窗口。代码大致是:
NSDocument * document = ...;
NSWindowController * winCtrl = [[NSWindowController alloc]
initWithWindowNibName:@"SomeNib" owner:document];
[document addWindowController:winCtrl];
[winCtrl loadWindow];
现在文档是 NIB 文件的所有者,但窗口控制器仍然接收到对分配给文档的窗口的引用。
当然,此代码仅用于演示目的,正确的方法实际上是子类NSDocument
,覆盖makeWindowControllers
,并在那里启动所有必需的控制器。
如果您的文档始终只有一个来自单个 NIB 文件的窗口,您也可以将NSDocument
属性设置windowNibName
为您的 NIB 文件的名称,然后调用默认makeWindowControllers
实现,大致执行以下操作:
NSWindowController * winCtrl = [[NSWindowController alloc]
initWithWindowNibName:self.windowNibName owner:self];
[self addWindowController:winCtrl];
还要检查 GNUStep 的实现NSWindowController
,它可能与 Apple 的不同(Apple 的不是开源的,所以我们不知道),但它的行为应该是相同的:
- (void) loadWindow
{
NSDictionary *table;
if ([self isWindowLoaded])
{
return;
}
table = [NSDictionary dictionaryWithObject: _owner forKey: NSNibOwner];
if ([NSBundle loadNibFile: [self windowNibPath]
externalNameTable: table
withZone: [_owner zone]])
{
_wcFlags.nib_is_loaded = YES;
if (_window == nil && _document != nil && _owner == _document)
{
[self setWindow: [_document _transferWindowOwnership]];
}
else
{
// The window was already retained by the NIB loading.
RELEASE(_window);
}
}
else
{
if (_window_nib_name != nil)
{
NSLog (@"%@: could not load nib named %@.nib",
[self class], _window_nib_name);
}
}
}
来源: https ://github.com/gnustep/libs-gui/blob/master/Source/NSWindowController.m
它将使用私有方法从其文档中获取窗口,_transferWindowOwnership
但前提是加载后没有设置窗口,设置一个文档并且该文档已设置为加载的 NIB 文件的所有者。