How to fire uibarbuttonitem click event programmatically

24,873

Solution 1

Not knowing the current bar button item action you can invoke it this way:

[barButtonItem.target performSelector:barButtonItem.action]

This will however bring "unknown selector" compiler warning, but this may be worked around.

Solution 2

Another way to do that and avoiding warnings is as follows:

[[UIApplication sharedApplication] sendAction:barButtonItem.action
                                           to:barButtonItem.target
                                         from:nil
                                     forEvent:nil];

Solution 3

@ton1n8o 's solution worked for me. Here is the implementation in swift:

UIApplication.sharedApplication().sendAction(barButtonItem.action, to: barButtonItem.target, from: nil, forEvent: nil)

Solution 4

I've read the accepted answer and it is awfully DANGEROUS. you should never suppress such warnings in order to shortcut the path to your desired result!

the safest way to do so:

SEL selector=barButton.action;
id target=barButton.target;
  if(selector && target){
     IMP imp = [target methodForSelector:selector];
     void (*func)(id, SEL) = (void *)imp;
     func(target, selector);
  }

Please read the original post here: performSelector may cause a leak because its selector is unknown

Solution 5

For my case with RxCocoa I needed to provide a nil - object to the perform action otherwise it would crash with EXC_BAD_ACCESS:

let button = sut.navigationItem.leftBarButtonItem!
_ = button.target?.perform(button.action, with: nil)
Share:
24,873
Jean Paul
Author by

Jean Paul

Updated on July 05, 2022

Comments

  • Jean Paul
    Jean Paul almost 2 years

    I have created a UIActionSheet

    UIActionSheet * action = [[UIActionSheet alloc]initWithTitle:@""
                                                                  delegate:self
                                                         cancelButtonTitle: @"cancel"
                                                    destructiveButtonTitle: @"OK"
                                                         otherButtonTitles: nil];
              [action showInView:self.view];
              [action release];
    

    On the event of the cancel button in the UIActionSheet I want to fire the event of a UIBarButtonItem, which is in my view.

    My question is how can I fire the button event(without touching the button) in the UIActionSheet delegate method

  • Jean Paul
    Jean Paul over 12 years
    UIBarButtonItem may not respond to sendActionsForControlEvents
  • NSExpression
    NSExpression almost 12 years
    This was really helpful to me. Thanks @Krrish
  • anders
    anders almost 11 years
    does anyone else get ARC warning here "may cause leak"?
  • Pang
    Pang over 9 years
    To suppress the "may cause leak" warning, see this answer.
  • ayoy
    ayoy over 9 years
    Nope, it is absolutely valid case. You are allowed to use performSelector: as well as barButtonItem.action, no private API usage here.
  • Mutawe
    Mutawe about 8 years
    Thanks for the from nil, because most actions has sender
  • nickromano
    nickromano over 6 years
    Swift version: _ = editButton.target?.perform(editButton.action)