title: How to create a mock view controller from storyboard
body: <p>I'm trying to create a mock view controller for a view controller that was created from a storyboard.</p>
  <p>If I try to downcast it as following, it doesn't work since the storyboard view controller is encoded:</p>
  <pre class="lang-swift prettyprint-override"><code>let _storyboard = UIStoryboard(name: &quot;Main&quot;, bundle: nil)
  let vc = _storyboard.instantiateViewController(ofType: ViewController.self) as? MockViewController
  </code></pre>
  <p>where <code>MockViewController</code> is the subclass of <code>ViewController</code>.</p>
  <p>I tried initializing the mock view controller using the nib name, but the nil error happens for the uninitialized <code>@IBOutlet</code> properties:</p>
  <pre class="lang-swift prettyprint-override"><code>class MockViewController: ViewController {
      init() {
          let controllerName = String(describing: ViewController.self)
          super.init(nibName: controllerName, bundle: nil)
      }
      
      required init?(coder: NSCoder) {
          fatalError(&quot;init(coder:) has not been implemented&quot;)
      }
  }
  </code></pre>
  <p>I could potentially create an identical view controller and initialize them manually:</p>
  <pre class="lang-swift prettyprint-override"><code>let _storyboard = UIStoryboard(name: &quot;Main&quot;, bundle: nil)
  let vc = _storyboard.instantiateViewController(ofType: ViewController.self)
  let mockViewController = MockViewController()
  mockViewController.someProperty = vc.property
  </code></pre>
  <p>but doesn't seem very efficient and also it entails always manually coordinating changes in both the production code and the test code.</p>
  <p>The most promising method I found was using this <a href="https://developer.apple.com/documentation/uikit/uistoryboard/3213989-instantiateviewcontroller" rel="nofollow noreferrer">initializer</a>:</p>
  <pre class="lang-swift prettyprint-override"><code>let controllerName = String(describing: ViewController.self)
  let mockVC = UIStoryboard(name: &quot;Main&quot;, bundle: nil).instantiateViewController(identifier: controllerName, creator: { coder -&gt; MockViewController? in
      return MockViewController(coder: coder)
  })
  </code></pre>
  <p>where the <code>MockViewController</code> is the subclass of <code>ViewController</code> again and has the following initializer:</p>
  <pre class="lang-swift prettyprint-override"><code>required init?(coder: NSCoder) {
      super.init(coder: coder)
  }
  </code></pre>
  <p>However, this also results in the same error as the first one where the <code>@IBOutlet</code> properties return nil errors.</p>