我的NSDocument子类实现了selectAll:。唯一的问题是,我正在使用NSTableView,它还实现了selectAll:。但是,NSTableView中的selectAll:action不能满足我的需要,它确实阻止了我的Document类中的selectAll:方法在响应者链中被访问。
我已经有了一个NSTableView的子类,经过一点点的讨论后,我通过在我的NSTableView子类中添加一个respondsToSelector:方法来实现我想要的工作方式,该子类位于运行时,告诉它没有selectAll:action:
-(BOOL)respondsToSelector:(SEL)targetSelector
{
if (targetSelector == @selector(selectAll:)) {
return FALSE; // we don't want tableView's implementation of selectAll
}
return [super respondsToSelector:targetSelector];
}
这似乎工作正常,允许我的文档子类中的selectAll:方法做它的事情。但这个解决方案让我有点不安。我在这个子类中实现的其他动作方法怎么样?我是否需要手动检查并为每个人返回true?我确实在这个子类中定义了两个动作,moveLeft:和moveRight:,它们似乎有效,即使我没有在respondsToSelector中处理它们:所以我的问题是,我正确地做到了这一点,还是我缺少一些东西?或者也许有一些完全不同的方法来正确地做到这一点?
顺便说一句,我从OmniGroup论坛上的这篇文章中得到了覆盖respondsToSelector的想法:
http://mac-os-x.10953.n7.nabble.com/Removing-an-action-from-a-subclass-td27045.html
答案 0 :(得分:1)
向super
发送邮件会影响我们使用的实施方法。它不会改变self
是谁。
让我们试着想象一下respondsToSelector:
是如何运作的。给定一个选择器mySelector
,它可能会反省超类链上的每个类,从[self class]
开始,看它是否实际实现 mySelector
。
现在,假设您的子类名为MyTableView。当MyTableView说
时[super respondsToSelector:targetSelector]
会发生什么?运行时将查找超类链以获得respondsToSelector:
的另一个实现,并最终找到NSObject的原始实现。这个实现有什么作用?好吧,我们刚回答:它开始在targetSelector
中搜索[self class]
的实现。那仍然是MyTableView类!因此,如果您在MyTableView中定义了moveLeft:
,则respondsToSelector:
会找到它并为moveLeft:
返回YES,正如您所希望的那样。
因此,为了概括,此搜索已被变态的仅选择器是搜索selectAll:
- 正如您希望和期望的那样。因此,我认为你可以放松并相信你所做的不仅是可以接受的,而且是可行的,而是你原先提出的问题的正常解决方案。
您可能还想查看Apple的 Objective-C运行时编程指南中的消息转发章节。