iOS 8.3 键盘方向错误

iOS 8.3 keyboard orientation bug

我遇到了一个奇怪的 iOS 8.3 问题,该问题显示键盘方向错误(视图控制器处于横向模式,但键盘显示为纵向模式):

我可以按照以下步骤触发此问题:

  1. 创建 2 UIViewController 子类:ViewControllerAViewControllerB

  2. ViewControllerA中实现supportedInterfaceOrientations和returnUIInterfaceOrientationMaskPortrait

  3. ViewControllerB中实现supportedInterfaceOrientations和returnUIInterfaceOrientationMaskLandscape

  4. 创建一个名为 NavigationControllerUINavigationController 子类,实现 supportedInterfaceOrientations 和 return [self.topViewController supportedInterfaceOrientations](我这样做是因为我想要防止 NavigationController 和它的 rootVC 旋转)

  5. 使用 NavigationController 作为应用程序的初始视图控制器,将 ViewControllerA 设置为 NavigationControllerrootViewContrller

  6. 启动应用程序,ViewControllerA 将显示在肖像中。在 ViewControllerA 上显示一个按钮,按下按钮将使用 presentViewController:animated:completion

  7. 显示 ViewControllerB
  8. ViewControllerB 会出现在横向;在 ViewControllerB 上显示一个文本字段,点击文本字段将触发键盘,但键盘是纵向模式,就像上图一样。

PS。您可以下载 运行 Xcode 项目 on github

这个问题似乎只出现在 iOS 8.3 上。难道我做错了什么 ?或者这可能只是 iOS 的另一个错误?

顺便说一句,如果您直接显示 ViewControllerA 而没有 ViewController,则不会发生此问题。因此,如果这是 iOS 的错误,我怎样才能避免子类化 UINavigationController 但仍然保持 ViewControllerAUINavigationController 的 rootViewController 旋转。


更新:这个错误仍然出现在 iOS 8.4 上,我在 2015 年 6 月 17 日发布了一个错误报告并得到了苹果的回复,他们说它已经在最新的 iOS 9 beta 中得到解决.

我问过技术支持,他们说

Our engineers have reviewed your request and have determined that this would be best handled as a bug report.

看来确认是系统bug

而我目前的解决方案是在ViewControllerA和ViewControllerB之间添加一个ViewControllerC(同时支持纵向和横向模式):ViewControllerA应该为ViewControllerC呈现动画,在ViewControllerC出现之后,呈现ViewControllerB而没有动画。

为了使过渡看起来自然,您可以将与 ViewControllerB 相同的背景颜色设置为 ViewControllerC,或者拍摄 ViewControllerB 的屏幕截图并将其作为背景图像添加到 ViewControllerC。

这不是一个完美的解决方案,对于用户来说,他们可能会发现 ViewControllerB 需要更多的时间来加载。

我们通过诱使设备认为它旋转到不同的方向然后旋转到其预期方向来解决这个问题。

- (void)viewDidAppear:(BOOL)animated
{
    [super viewDidAppear:animated];
    self.segmentedControl.selectedSegmentIndex = 0;
    if(!self.rotatingForDismissal)
    {
        [self.tableNumberTextField becomeFirstResponder];
    }


    if(SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(@"8.3"))
    {
        [[UIDevice currentDevice] setValue:@(UIDeviceOrientationLandscapeLeft) forKey:@"orientation"];
        [[UIDevice currentDevice] setValue:@(self.interfaceOrientation) forKey:@"orientation"];
    }

}

我能够使用以下方法使键盘正确显示。

- (void)viewDidAppear:(BOOL)animated
{
  [super viewDidAppear:animated];

  if (SYSTEM_VERSION_GREATER_THAN(@"7.1") && SYSTEM_VERSION_LESS_THAN(@"9.0"))
  {
    UIDeviceOrientation orientation = [[UIDevice currentDevice] orientation];
    [[UIDevice currentDevice] setValue:@(UIDeviceOrientationUnknown) forKey:@"orientation"];
    [[UIDevice currentDevice] setValue:@(orientation) forKey:@"orientation"];
  }
}

请注意,使用 UIDeviceOrientationUnknown 不会导致副作用,例如不适当的视图自动旋转。