Replacements for the deprecated NSNibLoading methods (loadNibFile:, loadNibNamed:, etc.)?

大城市里の小女人 提交于 2019-12-12 07:46:36

问题


I have found that the NSNibLoading methods in NSBundle:

+[NSBundle loadNibFile:externalNameTable:withZone:]
+[NSBundle loadNibNamed:owner:]
-[NSBundle loadNibFile:externalNameTable:withZone:]

have all been marked deprecated in 10.8 - what is the proper way to load the nibs in 10.8 and later?

I'm trying to create a custom sheet in my app, do I have to create NSWindowController with initWithWindowNibName for the custom sheet?


回答1:


The NSBundle class method loadNibNamed:owner: is deprecated in OS X v10.8,
loadNibNamed:owner:topLevelObjects: is not and the comments in the documentation state why:

Unlike legacy methods, the objects adhere to the standard cocoa memory management rules; it is necessary to keep a strong reference to them by using IBOutlets or holding a reference to the array to prevent the nib contents from being deallocated.




回答2:


If your app is going to support Lion, then loadNibNamed:owner:topLevelObjects: will not fire and you'll get an exception (unrecognized selector) when run on Lion. After some searching around I came up with this:

    // loadNibNamed:owner:topLevelObjects was introduced in 10.8 (Mountain Lion).
    // In order to support Lion and Mountain Lion +, we need to see which OS we're
    // on. We do this by testing to see if [NSBundle mainBundle] responds to
    // loadNibNamed:owner:topLevelObjects: ... If so, the app is running on at least
    // Mountain Lion... If not, then the app is running on Lion so we fall back to the
    // the older loadNibNamed:owner: method. If your app does not support Lion, then
    // you can go with strictly the newer one and not deal with the if/else conditional.

    if ([[NSBundle mainBundle] respondsToSelector:@selector(loadNibNamed:owner:topLevelObjects:)]) {
        // We're running on Mountain Lion or higher
        [[NSBundle mainBundle] loadNibNamed:@"NibName"
                                      owner:self
                            topLevelObjects:nil];
    } else {
        // We're running on Lion
        [NSBundle loadNibNamed:@"NibName"
                         owner:self];
    }

If you really want to use topLevelObjects:&array for Mountain Lion +, and you also want to support Lion, it looks like you will need to fall back on loadNibFile:externalNameTable:withZone: (available as both a class and instance method) for the Lion condition (I could be wrong about this one). I'm getting the impression that loadNibNamed:owner:topLevelObjects: was created to replace this.

I've also read elsewhere that when using the newer loadNibNamed:owner:topLevelObjects: for a sheet that you should uncheck "Release When Closed" for the sheet (window). This should be taken care of when you close the sheet:

[self.sheet close];
self.sheet = nil;

I'm not sure exactly what should be done about that checkbox if you're opening a non-modal window. Any ideas?



来源:https://stackoverflow.com/questions/12767838/replacements-for-the-deprecated-nsnibloading-methods-loadnibfile-loadnibnamed

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!