Re: Completely remove a window (from NSApp)?
site_archiver@lists.apple.com Delivered-To: cocoa-dev@lists.apple.com Thread-index: Accs8sJ8AOoeiJjmEdu3QAAWy6NyrA== Thread-topic: Completely remove a window (from NSApp)? User-agent: Microsoft-Entourage/11.3.2.061213 on 06/12/27 18:59, PGM at meirmans@sympatico.ca wrote:
I made a little test-project and it seems that the magic is not so much in -setReleasedWhenClosed itself, but simply in releasing the instance of NSWindow...
If I recall correctly, for document windows normally NSWindowController takes care of releasing the window it manages, so that when a NSDocument instance releases its windowControllers, the windowControllers release their windows. So you probably hacked your NSDocument subclass in such a way that this does not happen anymore.
Yes, it took me a few days to get this figured out, but the actual story is more complicated than we thought... -setReleasedWhenClosed is not the answer, because, in the documentation for -[NSWindow setReleasedWhenClosed:], it is plainly stated: "Release when closed, however, is ignored for windows owned by window controllers." Well, I have a window, owned by an NSWindowController subclass, which I would like to be released when closed. What do I do? The answer seems to be that the owning NSWindowController WILL ALWAYS -release the window, and also (magically) it will be removed from NSApp's -windows, when the owning NSWindowController itself is dealloced. And this is, it would seem, the natural death that the Cocoa gods have intended for "NSWindowControlled" windows. The reason my windows weren't going away is because, of course, code that I wrote many months ago, when I was a newer newbie, was full of stupid memory leaks and retain cycles, so that my NSWindowController was not getting deallocced, therefore its window was not getting deallocced. But there's a little more. After I fixed all the memory leaks and retain cycles, I found that my app would crash after the window disappeared. The reason for the crashes was the -setReleasedWhenClosed workaround method that I had implemented a few days ago, the one that is supposedly "ignored". Hmmm... Again, my workaround method was: - (void)removeWindow { [[self window] setReleasedWhenClosed:YES] ; [self close] ; } and it was invoked just before the final -release was sent to the NSWindowController, which now also sends the final -release to the NSWindow. But it's not quite being "ignored" as documented. By asking BOOL isSet = [self window] isReleasedWhenClosed] ; I get YES immediately after I set it, but apparently some kludge in Cocoa clobbers it to NO soon afterward, and this is how it is "ignored". My workaround outsmarted their kludge by setting it immediately before it was needed, so their kludge did not get a chance to clobber it. So, my workaround did indeed close, release and deallocc the window. Then, a few microsecs later, the NSWindowController itself is deallocced, and, apparently, sends its regular -release to its now-deallocced NSWindow, and you know the rest of the story. So, the solution to the original question is: If you want an "NSWindowControlled" window to be deallocced and removed from NSApp's -windows, practice proper memory management, and both these outcomes will occur when its NSWindowController is deallocced. Do not use the workaround -removeWindow method which I posted earlier in this thread. I still think it would be nice if, instead of automagically removing them, NSApp exposed a -removeWindow method, for those of us who want to rely on its -windows, without having to do perfect memory management. But my memory management is perfect now :| _______________________________________________ Cocoa-dev mailing list (Cocoa-dev@lists.apple.com) Do not post admin requests or moderator comments to the list. Contact the moderators at cocoa-dev-admins(at)lists.apple.com Help/Unsubscribe/Update your Subscription: http://lists.apple.com/mailman/options/cocoa-dev/site_archiver%40lists.apple... This email sent to site_archiver@lists.apple.com
participants (1)
-
Jerry Krinock