After looking through all the methods and discussing with friends below, the solution I used is used, since UIBarButtonItem answers both taps and takes a long time to press (TapOrLongPressBarButtonItem).
It is based on the following principles:
- Subclass UIBarButtonItem
- Use a custom view (so it’s really trivial to handle a long press - since our user view has no problems with a long click gesture handler ...)
... Until now, this approach has been in a different stream of SO - and I did not like this approach, since I could not find and easily enough create a custom view similar to the iPad navigation bar button ... Soooo ...
Use UIGlossyButton from Water Lou (thanks to the water!). This usage is encapsulated in a subclass ...
The resulting code is as follows:
@protocol TapOrPressButtonDelegate; @interface TapOrPressBarButtonItem : UIBarButtonItem { UIGlossyButton* _tapOrPressButton; __weak id<TapOrPressButtonDelegate> _delegate; } - (id)initWithTitle:(NSString*)title andDelegate:(id<TapOrPressButtonDelegate>)delegate; @end @protocol TapOrPressButtonDelegate<NSObject> - (void)buttonTapped:(UIButton*)button withBarButtonItem:(UIBarButtonItem*)barButtonItem; - (void)buttonLongPressed:(UIButton*)button withBarButtonItem:(UIBarButtonItem*)barButtonItem; @end @implementation TapOrPressBarButtonItem - (void)buttonLongPressed:(UILongPressGestureRecognizer*)gesture { if (gesture.state != UIGestureRecognizerStateBegan) return; if([_delegate respondsToSelector:@selector(buttonLongPressed:withBarButtonItem:)]) { [_delegate buttonLongPressed:_tapOrPressButton withBarButtonItem:self]; } } - (void)buttonTapped:(id)sender { if (sender != _tapOrPressButton) { return; } if([_delegate respondsToSelector:@selector(buttonTapped:withBarButtonItem:)]) { [_delegate buttonTapped:_tapOrPressButton withBarButtonItem:self]; } } - (id)initWithTitle:(NSString*)title andDelegate:(id<TapOrPressButtonDelegate>)delegate { if (self = [super init]) {
And all you have to do is:
1. An instant is as follows:
TapOrPressBarButtonItem* undoMenuButton = [[TapOrPressBarButtonItem alloc] initWithTitle:NSLocalizedString(@"Undo", @"Undo Menu Title") andDelegate:self];
2. Connect the button to the navigation bar:
[self.navigationItem setLeftBarButtonItem:undoMenuButton animated:NO]
3. Enter the TapOrPressButtonDelegate protocol, and you're done ...
-(void)buttonTapped:(UIButton*)button withBarButtonItem:(UIBarButtonItem*)barButtonItem { [self menuItemUndo:barButtonItem]; } -(void)buttonLongPressed:(UIButton*)button withBarButtonItem:(UIBarButtonItem*)barButtonItem { [self undoMenuClicked:barButtonItem]; }
Hope this helps someone else ...