0

I need to pass two actions for single UIButton.

First argument passed successfully asa follows:

[imageButton addTarget:self action:@selector(imageClicked:) forControlEvents:UIControlEventTouchUpInside];
imageButton.tag = 1;

But I need to pass another argument also for the same button:

int secondAction =10;
    [imageButton addTarget:self action:@selector(imageClicked:*secondAction) forControlEvents:UIControlEventTouchUpInside];

Can anybody help how to pass two values for a single button/selector?

Lin Du
  • 88,126
  • 95
  • 281
  • 483
Rajesh Loganathan
  • 11,129
  • 4
  • 78
  • 90
  • 2
    For passing multiple arguments via a selector see http://stackoverflow.com/questions/1018195/objective-c-calling-selectors-with-multiple-arguments – Satheesh Nov 29 '13 at 07:44
  • 1
    This is not the duplicate! In the above mentioned solution there is [self performSelector:] solution, not the [Object addTarget] solution! – pedrouan May 31 '14 at 15:53

4 Answers4

1

You can use Objective C Runtime feature for associating data with objects as :

Step 1 : Import this in your class : #import <objc/runtime.h>

step 2 : Crete a key name as : static char * kDataAssociationKey = "associated_data_key";

Step 3 : Associate data with your object (Ex: button) as :

NSString *your_data =@"Data which is being associated";
    objc_setAssociatedObject(imageButton,
                             kDataAssociationKey,
                             your_data,
                             OBJC_ASSOCIATION_RETAIN);

Step 4 : Get associated data in your method as :

NSString *value  = (NSString *)objc_getAssociatedObject(imageButton, kDataAssociationKey);

Hope it helps you.

Nishant Tyagi
  • 9,893
  • 3
  • 40
  • 61
  • You're wrapping up the argument in an NSNumber for no reason - you could just use OBJC_ASSOCIATION_ASSIGN and associate the int. Then you're getting the NSNumber pointer back and casting it to an int, which will give you the address of the NSNumber in memory, not the original argument. – Simon Nov 29 '13 at 10:01
  • @Simon yes I should've used OBJC_ASSOCIATION_ASSIGN for integer value. But My focus was here not for integer parameter only, My focus was to let the users know how any type of data can be associated this way. – Nishant Tyagi Nov 29 '13 at 12:55
0

One argument that the button can receive is (id)sender. This means you can create a new button, inheriting from UIButton, that allows you to store the other intended arguments. Hopefully these two snippets illustrate what to do.

imageButton.tag = 1;
[imageButton addTarget:self action:@selector(buttonTouchUpInside:) forControlEvents:UIControlEventTouchUpInside];

and

 - (IBAction) buttonTouchUpInside:(id)sender {

    MyOwnButton *button = (MyOwnButton *)sender; //MyOwnButton inherited from UIButton

        or 


  UIButton *button = (UIButton *) sender;
  //do as you please with imageButton.tag
  NSLog(@"%d",button.tag);

  }

please refer this link for further explanation passing-parameters-on-button-actionselector

Community
  • 1
  • 1
Suhit Patil
  • 11,748
  • 3
  • 50
  • 60
0

Every event has a sender that can be get at selector method by

    (void)notify:(NSNotification *)notification {

     id notificationSender = [notification object];
     //do stuff

    }

now this sender is actually an instance whose attributes could be used to get the information about it now what you can do is you can create a class and add some attribute to it that you want to pass through selector and then use NSNotificationCenter for broad casting your event

    [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(notify:) name:@"Event" object:yourobjectwithattributes];

put this in the class where you want to recieve the event and have the selector

and

    [[NSNotificationCenter defaultCenter] postNotificationName:@"Event" object:notificationSender];

this where you want to throw an event

Mureinik
  • 297,002
  • 52
  • 306
  • 350
0

Short answer: You don't. The @selector there tells the button what method to call when it gets tapped, not the arguments that it should pass to the method.

Longer answer: If you know when you're creating the button what the argument is going to be, then you can wrap it up like this:

// In loadView or viewDidLoad or wherever:
[imageButton addTarget:self action:@selector(imageButtonTapped:) forControlEvents:UIControlEventTouchUpInside];

... later ...

- (void)imageButtonTapped:(id)sender
{
    [self doStuffToMyImageWithArgument:10];
}

- (void)doStuffToMyImageWithArgument:(NSInteger)argument
{
    ... do what you gotta do ...

If you don't know, then you probably want to save the argument to a variable somewhere.

// In your @interface
@property (nonatomic, assign) NSInteger imageStuffArgument;

... later ...

// In loadView or viewDidLoad or wherever:
[imageButton addTarget:self action:@selector(imageButtonTapped:) forControlEvents:UIControlEventTouchUpInside];

... later ...

- (void)respondToWhateverChangesTheArgument
{
    self.imageStuffArgument = 10;
}

... later ...

- (void)imageButtonTapped:(id)sender
{
    [self doStuffToMyImageWithArgument:self.imageStuffArgument];
}

- (void) doStuffToMyImageWithArgument:(NSInteger)argument
{
    ... do what you gotta do ...
Simon
  • 25,468
  • 44
  • 152
  • 266