I’ve seen many ways to implement delete in an NSTableView. Many are good. Many hardcode references to something they shouldn’t, and those are bad.
Here’s an easy way:
Subclass NSTableView and override keyDown:
- (void)keyDown:(NSEvent *)theEvent {
// handle delete
unichar key = [[theEvent charactersIgnoringModifiers] characterAtIndex:0];
if (key == NSDeleteCharacter && self.selectedRow != -1) {
[NSApp sendAction:@selector(delete:) to:nil from:self];
} else {
[super keyDown:theEvent];
}
}
This just lets the responder chain take care of it. Your window controller can easily handle it by just implementing delete:
- (IBAction)delete:(id)sender {
if (self.tableView.selectedRowIndexes.count > 0) {
[_tableView beginUpdates];
[[self _patternSequence] removeChildrenAtIndexes:self.tableView.selectedRowIndexes];
[_tableView endUpdates];
}
}
EDIT: I probably should only call super keyDown if it wasn’t the delete key…otherwise we beep.

I might be missing something obvious, but the line
[[self _patternSequence] removeChildrenAtIndexes:self.tableView.selectedRowIndexes];
could do with a bit more explanations. Is _patternSequence the datasource of the NSTableView ?
Hi Guillaume —- that’s my model; it is backed by a core data obect. Maybe I’ll do a post on how to update your model and have a view based tableview animate along with it.
corbin
Hi Corbin,
Yes please, that would be a nice follow-up to this one :)
Yeah we need a little more detail. In particular, I’m surprised I don’t see any “reloadData”. Maybe it’s because you’re using Cocoa Bindings ? or are the beginUpdates/endUpdates enough in all scenarios (with or without bindings ?)
I’m glad you’re writing new Cocoa post. Those were missing (a lot). Thanks
Yeah, I am using CoreData…but I have it semi-using bindings.
Delete is easy, but what about copy? Can’t send the copy: action to nil because it’ll just get sent back to itself since the tableview is first responder.