当我推动具有不同支持方向的控制器时,为什么UINavigationController不会改变方向?

时间:2017-03-07 09:08:19

标签: uiviewcontroller uinavigationcontroller orientation uiinterfaceorientation

我的代码设置方式:

我使用导航控制器,并使用控制方向的委托:

class NavDelegate: UINavigationControllerDelegate {
  func navigationControllerSupportedInterfaceOrientations(_ navigationController: UINavigationController) -> UIInterfaceOrientationMask {
    print("Checking orientation")
    if topViewController != nil {
      return topViewController!.supportedInterfaceOrientations
    }
    return .portrait
  }

  ...
}

我的应用程序的主视图控制器名为MainController,它只是纵向:

class MainController: UIViewController {
  override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
    return .portrait
  }

  ...
}

我有另一个控制器PhotoController,它支持所有四个方向:

class PhotoController: UIViewController {
  override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
    return .all
  }

  ...
}

我使用pushViewController()将PhotoController推送到MainController的顶部。

问题:

每个控制器本身正确处理方向 - 当我将手机旋转到所有四个方向时,MainController保持纵向,PhotoController旋转到所有四个方向。

但是这种情况无法正常运行:

  1. 将手机置于风景中,主控制器在屏幕上。
  2. 控制器位于portait(正如预期的那样)。
  3. 将PhotoController推入堆栈。
  4. 我希望PhotoController基于设备方向以横向打开,但仍然是纵向。如果我来回手动旋转手机,控制器随手机一起旋转。显然,用户永远不必这样做,来回旋转手机让控制器旋转。

    当我点按MainController中推送PhotoController的按钮时,不会调用navigationControllerSupportedInterfaceOrientations()。

    我还尝试了什么:

    • 覆盖shouldAutorotate以在PhotoController中返回true。
    • ...并在MainController中。
    • 覆盖UINavigationController中的supportedInterfaceOrientations,而不是使用委托。
    • 检查UINavigationController.visibleViewController而不是.topViewController。这不起作用,因为topviewController原来是一个iOS私有类UISnapshotModalViewController,而不是我的类,所以在它上面调用supportedInterfaceOrientation()可能不会返回正确的值。

    这些都不起作用。

1 个答案:

答案 0 :(得分:2)

解决方案原来是调用UIViewController。 viewWillAppear()或viewDidAppear()中的attemptRotationToDeviceOrientation()。

在前一种情况下,推动控制器的动画与设备旋转动画同时发生,这看起来很奇怪。在后一种情况下,旋转发生在控制器转换动画完成之后。虽然以不同的方式看起来也很奇怪。