[swift-users] #selector with Swift 3?

Brent Royal-Gordon brent at architechies.com
Fri Jun 17 12:31:44 CDT 2016


> I was asked to try out the latest betas of Cocoa to check if a SceneKit bug I reported has been fixed. As part of this I decided to try an update to Swift 3. I've run into a number of minor issues, but one has me frustrated. In my menu validate method, I have:
> 
> 		switch menuItem.action {
> 			case #selector!(showRescale) :
> 
> This worked fine in 2.2, but now it complains that it expects a ( after #selector. Removing the ! fixes that problem, but now returns an error that there's a missing !, which it inserts to cause the original error again. I also tried placing it after the ()'s, and now it complains that it's expecting the :
> 
> Does anyone know the proper Swift 3 syntax for this?

tl;dr: Write this instead:

	case #selector(showRescale)?:

The explanation:

In Swift 2, Selectors could *always* be nil, even when they weren't optional. The same was true of UnsafePointer and a few other types, and it wasn't great. So in Swift 3, we've changed these types so they now can only be nil if they're optional.

Because of this change, the type of `NSMenuItem.action` changed from `Selector` to `Selector?`. That means the patterns in your `switch` statement need to look like:

	case Optional.some(#selector(showRescale)):

Which you can specify in a pattern match (like a case statement) using the convenient trailing-question-mark syntax I showed above:

	case #selector(showRescale)?:

The Swift 3 migrator should have generated this code, so you've probably encountered a bug. It would help them if you could create a small example project and file a bug report at <https://bugreport.apple.com/>. (The migrator is closed source.)

Hope this helps,
-- 
Brent Royal-Gordon
Architechies



More information about the swift-users mailing list