FROM : Tim Hewett
DATE : Fri Nov 19 18:11:20 2004
Hello,
A while back I reported being unable to get buttons and other
controls to call their action methods when those controls were
located in a NSDrawer attached to a modal NSPanel under
10.2.8. Clicking the button/slider/matrix etc just caused a system
beep with the action method not being called at all.
This was kludged by subclassing the control and providing a
mouseDown replacement which handled all the highlighting
of the button, and the calling of the action method on the target.
Worked fine, but now my app needs to have a NSSlider call an
action method continuously while sliding, which resulted in a
hail of system beep "bullets" like a machine gun... Overloading
mouseDown for NSSlider was getting complex since it is more
than just a button so a different way was found (now I'm a little
further a long the learning curve since last time) by overloading
the sendAction:to: NSControl method instead.
This turns out to be a generic solution for all NSControls that
won't work in modal panel drawers, and doesn't disrupt behaviour
under 10.3 either. This is the code sample:
@implementation MyButton // inherits from NSButton
- (BOOL)sendAction:(SEL)theAction to:(id)theTarget
{
if ( !theAction || !theTarget )
return FALSE;
objc_msgSend( theTarget, theAction, self );
return TRUE;
}
@end
It lacks one feature of the normal implementation, where the target
can be nil leading to a search algorithm being triggered to find an
object which supports the particular selector. There are possible
other things missing too, but it works well enough for me.
BTW I don't know why objc_msgSend() has to be used instead of
performSelector:withObject:afterDelay: but it does.
Note that if this is used for NSMatrix then for some reason theAction
and theTarget are always received as nil, so instead do:
objc_msgSend( [self target], [self action], self );
Works great.
HTH,
Tim Hewett.
DATE : Fri Nov 19 18:11:20 2004
Hello,
A while back I reported being unable to get buttons and other
controls to call their action methods when those controls were
located in a NSDrawer attached to a modal NSPanel under
10.2.8. Clicking the button/slider/matrix etc just caused a system
beep with the action method not being called at all.
This was kludged by subclassing the control and providing a
mouseDown replacement which handled all the highlighting
of the button, and the calling of the action method on the target.
Worked fine, but now my app needs to have a NSSlider call an
action method continuously while sliding, which resulted in a
hail of system beep "bullets" like a machine gun... Overloading
mouseDown for NSSlider was getting complex since it is more
than just a button so a different way was found (now I'm a little
further a long the learning curve since last time) by overloading
the sendAction:to: NSControl method instead.
This turns out to be a generic solution for all NSControls that
won't work in modal panel drawers, and doesn't disrupt behaviour
under 10.3 either. This is the code sample:
@implementation MyButton // inherits from NSButton
- (BOOL)sendAction:(SEL)theAction to:(id)theTarget
{
if ( !theAction || !theTarget )
return FALSE;
objc_msgSend( theTarget, theAction, self );
return TRUE;
}
@end
It lacks one feature of the normal implementation, where the target
can be nil leading to a search algorithm being triggered to find an
object which supports the particular selector. There are possible
other things missing too, but it works well enough for me.
BTW I don't know why objc_msgSend() has to be used instead of
performSelector:withObject:afterDelay: but it does.
Note that if this is used for NSMatrix then for some reason theAction
and theTarget are always received as nil, so instead do:
objc_msgSend( [self target], [self action], self );
Works great.
HTH,
Tim Hewett.
| Related mails | Author | Date |
|---|---|---|
| No related mails found. | ||






Cocoa mail archive

