I'm trying to make this extension:
extension UIViewController { class func initialize(storyboardName: String, storyboardId: String) -> Self { let storyboad = UIStoryboard(name: storyboardName, bundle: nil) let controller = storyboad.instantiateViewControllerWithIdentifier(storyboardId) as! Self return controller } }
But I get compile error:
error: cannot convert return expression of type 'UIViewController' to return type 'Self'
Is it possible? Also I want to make it as init(storyboardName: String, storyboardId: String)
Similar as in Using 'self' in class extension functions in Swift, you can define a generic helper method which infers the type of self from the calling context:
extension UIViewController { class func instantiateFromStoryboard(storyboardName: String, storyboardId: String) -> Self { return instantiateFromStoryboardHelper(storyboardName, storyboardId: storyboardId) } private class func instantiateFromStoryboardHelper<T>(storyboardName: String, storyboardId: String) -> T { let storyboard = UIStoryboard(name: storyboardName, bundle: nil) let controller = storyboard.instantiateViewControllerWithIdentifier(storyboardId) as! T return controller } }
Then
let vc = MyViewController.instantiateFromStoryboard("name", storyboardId: "id")
compiles, and the type is inferred as MyViewController
.
Update for Swift 3:
extension UIViewController { class func instantiateFromStoryboard(storyboardName: String, storyboardId: String) -> Self { return instantiateFromStoryboardHelper(storyboardName: storyboardName, storyboardId: storyboardId) } private class func instantiateFromStoryboardHelper<T>(storyboardName: String, storyboardId: String) -> T { let storyboard = UIStoryboard(name: storyboardName, bundle: nil) let controller = storyboard.instantiateViewController(withIdentifier: storyboardId) as! T return controller } }
Another possible solution, using unsafeDowncast
:
extension UIViewController { class func instantiateFromStoryboard(storyboardName: String, storyboardId: String) -> Self { let storyboard = UIStoryboard(name: storyboardName, bundle: nil) let controller = storyboard.instantiateViewController(withIdentifier: storyboardId) return unsafeDowncast(controller, to: self) } }
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With