Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
745 views
in Technique[技术] by (71.8m points)

cocoa - NSTokenField and deleting tokens

My app allows users to attach tags to certain model objects (subclasses of NSManagedObject). The Tag class is also a subclass of NSManagedObject. I decided to use NSTokenField to display the tags, where each token holds an instance of Tag as the represented object. It all works pretty good but I'm stuck in situations where the user deletes a token as I want to check whether the associated Tag has become obsolete and should be deleted.

I was expecting a method in NSTokenFieldDelegate or NSTokenFieldCellDelegate which would allow me to intercept and check a delete action on a token.

After some googling I found this post addressing the topic. I implemented the suggested method controlTextDidChange: in my controller (the delegate of the token field). Upon inspecting the control that is passed as an argument, it revealed to be an instance of NSTokenTextView for which I cannot find any documentation (probably a private class).

Has anybody run into this and found a solution to gracefully delete tokens while maintaining the underlying model of represented objects?

EDIT

I found this as well, which seems to suggest that for some reason it just is not designed to work like the rest of us would expect.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

You should be able to simulate a delete delegate by creating a token wrapper class that has a pointer back to the owner as well as the wrapped object:

@protocol TokenWrapperDelegate 
-(void)tokenWasDeleted:(id)token;
@end

@interface TokenWrapper : NSObject {
  id<TokenWrapperDelegate> owner;
  id token;
}
-(id)initWithWrappedToken:(id)token owner:(id<TokenWrapperDelegate>)owner;
@property (nonatomic, weak) id<TokenWrapperDelegate> owner;
@property (nonatomic, strong) id token;
@end

Then have the TokenWrapper dealloc notify the owner that the token was deleted:

@implementation TokenWrapper

...

-(void)dealloc {
  [owner tokenWasDeleted:self.token];
  self.token = nil;
  [super dealloc];
}

@end

Then in your representedObjectForEditingString callback, return an autoreleased wrapper pointing at your owner and your real token. You'll also have to make sure to change the other NSTokenField delegate callbacks to delve into the wrapper object. Make sure the owner sets a bit to ignore these callbacks when you're manually changing the contents of the NSTokenField (like by calling setObjectValue).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...