I would like a parent ViewController
to handle Target-Actions generated by one of its child ViewControllers
.
According to the Apple docs this should be possible by setting target
to nil
and following the responder chain.
If you specify nil for the target object, the control searches the responder chain for an object that defines the specified action method. https://developer.apple.com/documentation/uikit/uicontrol
But how do I write the action method signature when target
is nil
?
Typically you enclose the function name in #selector()
which gives you compile time checks that a method exists with that signature. Like so:
class MyViewController: UIViewController {
override func viewDidLoad() {
self.button.addTarget(self, action: #selector(buttonPressed(sender:)), for: .touchDown)
}
func buttonPressed(sender: UIButton) { }
}
But since target
is nil
the compiler complains because it can't find it:
// ! Use of unresolved identifier "buttonPressed(sender:)"
button.addTarget(nil, action: #selector(buttonPressed(sender:)), for: .touchDown)
I tried initializing a Selector using a String, but the compiler also complains.
// ! String literal is not a valid Objective-C selector
button.addTarget(nil, action: Selector("buttonPressed(sender:)"), for: .touchDown)
The solution is to prefix with the name of the defining class.
FYI I got the answer through this nice blog post from Jan 2016, downloading the source files, and having XCode convert it to Swift 3 syntax :-)