Trailing where clause for extension of non-generic type

Sunkas picture Sunkas · Mar 23, 2016 · Viewed 9.2k times · Source

I have the following code:

func registerNotification(name:String, selector:Selector)
{
    NSNotificationCenter.defaultCenter().addObserver(self, selector: selector, name: name, object: nil)
}

func registerKeyboardNotifications()
{
    let isInPopover = navigationController?.popoverPresentationController != nil
    let ignore = isInPopover && DEVICE_IS_IPAD
    if !ignore {
        registerNotification(UIKeyboardWillShowNotification, selector: Selector("keyboardWillShow:"))
        registerNotification(UIKeyboardWillHideNotification, selector: Selector("keyboardWillHide:"))
    }
}

in an extension to UIViewController. This code is reused by many viewcontroller to register for keyboard notifications. However with Swift 2.2 it produces a warning. I like the new #selector syntax but not sure how to implement it in this case.

I think the correct solution is to make a protocol and extend UIViewController only for instances that conform to that protocol. My code so far:

@objc protocol KeyboardNotificationDelegate
{
    func keyboardWillShow(notification: NSNotification)
    func keyboardWillHide(notification: NSNotification)
}

extension UIViewController where Self: KeyboardNotificationDelegate
{
    func registerKeyboardNotifications()
    {
        let isInPopover = navigationController?.popoverPresentationController != nil
        let ignore = isInPopover && DEVICE_IS_IPAD
        if !ignore {
            registerNotification(UIKeyboardWillShowNotification, selector: #selector(KeyboardNotificationDelegate.keyboardWillShow(_:)))
            registerNotification(UIKeyboardWillHideNotification, selector: #selector(KeyboardNotificationDelegate.keyboardWillHide(_:)))
        }
    }
}

However this get me the error

trailing where clause for extension of non-generic type

on the extension row. Any ideas?

Answer

Sunkas picture Sunkas · Mar 23, 2016

The solution was simple to switch the order in the extension clause:

extension UIViewController where Self: KeyboardNotificationDelegate

should be

extension KeyboardNotificationDelegate where Self: UIViewController