I'm currently subclassing a UINavigationController
for a framework that serves a view controller flow (in a way, like UIImagePickerController
do)
Here's an example of my implementation, reduced to be as simple as possible, that can be run in a playground.
import UIKit
public class MyNavigationController: UINavigationController {
public var anyVar: Int?
public init(anyVar: Int) {
let viewController = UIViewController()
super.init(rootViewController: viewController)
self.anyVar = anyVar
}
required public init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
}
let navigationController = MyNavigationController(anyVar: 42)
The last line is crashing, with a EXC_BAD_INSTRUCTION
. When I run in Xcode, it's tells me at runtime that init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: NSBundle?)
was missing.
And if I override the method:
public override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: NSBundle?) {
super.init(nibName: nibNameOrNil, bundle: nibBundleOrNil)
}
...everything works well: you can try with your own playground.
I can't understand why. It doesn't sounds logic to me.
The UIViewController
documentation says:
If you subclass UIViewController, you must call the super implementation of this method, even if you aren't using a NIB. (As a convenience, the default init method will do this for you, and specify nil for both of this methods arguments.)
But my init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: NSBundle?)
override gets called, from super.init(rootViewController: viewController)
initialization!
Without overriding it, I guess the UIViewController's init(nibName:bundle:)
should be called, but not.
I still cannot understand why overriding the method and calling super
make the program works better. IMO, overriding a method while only calling super.thisMethod
is totally useless, it only adds a method call in the call stack.
I must missing something essentials about Swift init methods, but I can't figure out what.