Problem: closing the document window produces the following exception:
An instance 0x600000140630 of class SimpleApp.Document was deallocated while key value
observers were still registered with it. Current observation info: <NSKeyValueObservationInfo 0x6100000424f0> …
<NSKeyValueObservance 0x6100000c2f40: Observer: 0x6280000c7a10, Key path: managedObjectContext, Options: <New: NO, Old: NO, Prior: NO> Context: 0x0, Property: 0x6100000429a0>
and
-[NSAutoreleasePool drain]: This pool has already been drained, do not release it (double release).
Here’ what I’ve done:
Created a new Xcode Project using:
- Use Storyboards
- Create Document-Based Application
- Use Core Data
In Document.xcdatamodeld
- created an Entity (Part) with 2 attributes, width and length
In Main.storyboard,
dragged a table view (view based), 2 buttons (“Add” and “Remove”) and an ArrayController to the view controller
ArrayController mode set to Entity
Bindings:
- tableView content: ArrayController arrangedObjects, Selection Indexes: ArrayController selectionIndexes
- the 2 table view cells were bound to Table Cell View, keyPath: objectValue.width and objectValue.length
Now the first problem was to bind the ArrayController managedObjectContext. I needed a reference to the Document subclass. So I added
weak var document: Document? {
didSet {
print("ViewController, document didSet")
}
}
in ViewController and bound the ArrayController managed object context to it (document.managedObjectContext).
After trying, without success, to set this var in various places (ViewController.viewDidLoad() , in a NSWindowController subclass's windowDidLoad(), NSDocumentController.sharedDocumentController().documentForWindow(self.window!) was always nil.
I made it work using the following in Document.makeWindowControllers()
if let viewController = windowController.contentViewController {
viewController.setValue(self, forKey: "document")
}
So, now I can create a new document, and save it, open a saved document but as soon as I close the window I get the previous exception. I added deinit methods to the view controller and the document and the exception occurs after Document.deinit is called but before ViewController.deinit. So it looks like the array controller is still observing the Document managedObjectContext which no longer exists.
Maybe I’m missing something obvious here, but I can’t find a simple example on how to use storyboards, array controller and document together. BTW, I also tried without Core Data and got the same exception.
UPDATED
I've made a github project https://github.com/Miyan0/SimpleApp.git
The steps to reproduce the crash:
- create a new document
- save it
- reopen the document
- make any modifications
- click the closebox (without saving)
- crash