Search code examples
macoscocoaswift3appkit

NSDrawer causes crash when added to App Window


I'm trying to programmatically add an NSDrawer to my app's main window (which also has an NSOutlineViewwhich was setup in IB):

Ivar:

var dd: NSDrawer? = nil

Then, when a disclosure triangle button is clicked:

if dd == nil {
            var drawer_rect = NSInsetRect(self.window.frame, 30, 30).size
            drawer_rect.height = 150
            dd = NSDrawer.init(contentSize: drawer_rect, preferredEdge: NSRectEdge.minY)
            dd!.contentView = self.status_scroll
            dd!.parentWindow = self.window
        }

So when the user tries to 'disclose' the drawer, the above code creates an NSDrawer and then displays it. It all works fine but Xcode dumps the following out as the parentWindow is set:

[General] ERROR: Setting <NSOutlineView: 0x100f0b9b0> as the first responder for window <NSDrawerWindow: 0x100fc8900>, but it is in a different window (<NSWindow: 0x6080001e0600>)! This would eventually crash when the view is freed. The first responder will be set to nil.
(
    0   AppKit                              0x00007fff9fc289cf -[NSWindow _validateFirstResponder:] + 557
    1   AppKit                              0x00007fff9f3a374c -[NSWindow _setFirstResponder:] + 31
    2   AppKit                              0x00007fff9f90c35b -[NSDrawerWindow _setParentWindow:] + 64
    3   AppKit                              0x00007fff9f90b666 -[NSDrawer(DrawerInternals) _doSetParentWindow:] + 382
    4   AppKit                              0x00007fff9f907786 -[NSDrawer setParentWindow:] + 78

Comment out the setting of the parentWindow and nothing gets dumped to the console.


Solution

  • NSDrawer is deprecated as per Apple documentation. You should consider a different design. If you still use NSDrawer, you may face such issues.