简体   繁体   中英

Objective-C Passing Method Reference As Parameter

I've seen a lot of discussions NEAR this subject, but none that actually work in Xcode 5.x, especially using ARC. I have a simple problem:

I need to pass a method reference to a CreateButton method so that when the button is called it calls my custom function, and not some generic one.

I've tried using (SEL) type, but that doesn't work with ARC. I've tried using the &func method, but that claims I haven't declared the function yet.

So my need is:

Class A calls Class B and sends over the info to make a UIButton. Within that call, I want to send over the action:method in a reference. I'm sure this is done routinely, but I can't seem to find an iOS 7 / Xcode 5.x method of doing it. I've also reviewed the O'Reilly iOS 7 fundamentals and cookbook code and couldn't find this discussed anywhere.

Thanks for you help.

When I have to pass selectors around, I convert them to strings with NSStringFromSelector() and back to selectors with NSSelectorFromString() .

Passing the strings around is a lot easier. You can store them in collections (arrays, dictionaries), serialize and unserialize them, and they will work naturally with ARC.

Example:

In your class A where you gather the information to create a button:

NSString *selectorString = NSStringFromSelector(@selector(yourActionMethodNameHere:));
// Gather more information needed by Class B here, then package
// it all up into a dictionary, for example
NSDictionary *buttonInfo = @{@"selectorString": selectorString, /* more stuff here */};

At this point, you can call your button-constructing method in Class B, passing along buttonInfo , which contains all the information that that helper method needs, including the selector. The method can convert the string back to a selector and use it like this:

SEL actionSelector = NSSelectorFromString(buttonInfo[@"selectorString"]);
// configure your button to use actionSelector here

You should be able to use SEL parameters? I know I have done before. ARC might complain and give you a warning, but it won't fail to compile. It's simply a warning because it can't quite figure out what to do memory wise.

If you really can't get that to work though, another alternative would be to use a block, so you might call your method like

[objectA performMethodWithParam:paramA paramb:paramB completion:^{ ... do somethhing ... }];

Then in that method you can just call

completion();

Instead of actually calling a method.

Another alternative would be to use the delegate pattern. Create a @protocol defining a method such as classADidFinish then make class B implement that method. Then set the instance of classB as the delegate for your classA instance, and have it call that method when it's done.

Both of these approaches will stop ARC moaning at you.

But as I said, using SEL params should work fine. There is a way you can even get the compiler to stop showing you the warnings but it's a little ugly.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM