gle*_*enc 12 rotation uisplitviewcontroller ios ios5
正如在SO上的其他问题中所报告的那样,iOS 5根据此发行说明更改了拆分视图控制器的旋转回调的发送方式.这不是一个骗局(我认为),因为我无法找到关于如何在iOS 5中调整拆分视图控制器使用以应对更改的另一个问题:
iOS 5中的旋转回调不适用于通过全屏显示的视图控制器.这意味着,如果你的代码呈现了另一个视图控制器视图控制器,然后用户随后旋转设备,以不同的取向,在解雇,底层控制器(即呈现控制器)将不会收到任何旋转回调.但请注意,呈现控制器在重新显示时将接收viewWillLayoutSubviews调用,并且可以从此方法查询interfaceOrientation属性并用于正确布局控制器.
我在根分割视图控制器中配置弹出窗口按钮时遇到问题(当你在肖像中时,应该在弹出框中显示左窗格视图).以下是当设备处于横向模式时,我的应用启动序列在iOS 4.x中的工作方式:
将拆分视图控制器安装到窗口中[window addSubview:splitViewController.view]; [window makeKeyAndVisible];.这导致在splitViewController:willHideViewController:withBarButtonItem:forPopoverController:委托上调用(即模拟横向 - >纵向旋转),即使设备已处于横向模式.
呈现全屏模式(我的加载屏幕),它完全覆盖下面的分割视图.
完成加载并关闭加载屏幕模式.由于设备处于横向模式,因此在显示分割视图控制器时,这会导致splitViewController:willShowViewController:invalidatingBarButtonItem:在代理上调用(即模拟纵向 - >横向旋转),从而使条形按钮项无效,将其从右侧移除拆分视图,留下我们想要的地方.万岁!
因此,问题在于,由于该发行说明中描述的更改,iOS 4.3内部发生的任何事情都会导致splitViewController:willShowViewController:invalidatingBarButtonItem:被调用不再发生在iOS 5中.我尝试了子类化UISplitViewController,因此我可以提供自定义的实现,viewWillLayoutSubviews如发行说明,但我不知道如何重现iOS 4触发的所需内部事件序列.我试过这个:
- (void) viewWillLayoutSubviews
{
[super viewWillLayoutSubviews];
UINavigationController *rightStack = [[self viewControllers] objectAtIndex:1];
UIViewController *rightRoot = [[rightStack viewControllers] objectAtIndex:0];
BOOL rightRootHasButton = ... // determine if bar button item for portrait mode is there
// iOS 4 never goes inside this 'if' branch
if (UIInterfaceOrientationIsLandscape( [self interfaceOrientation] ) &&
rightRootHasButton)
{
// Manually invoke the delegate method to hide the popover bar button item
[self.delegate splitViewController:self
willShowViewController:[[self viewControllers] objectAtIndex:0]
invalidatingBarButtonItem:rightRoot.navigationItem.leftBarButtonItem];
}
}
Run Code Online (Sandbox Code Playgroud)
这主要是有效的,但不是100%.问题是,自己调用委托方法实际上并不会使条形按钮项无效,因此第一次旋转到纵向时,系统认为条形按钮项仍然正确安装,并且不会尝试重新安装它.只有在您再次旋转到横向然后再回到纵向后,系统才会恢复到正确的状态,并且实际上会以纵向模式安装弹出框按钮项目.
基于这个问题,我还尝试手动调用所有旋转回调而不是触发委托方法,例如:
// iOS 4 never goes inside this 'if' branch
if (UIInterfaceOrientationIsLandscape( [self interfaceOrientation] ) &&
rightRootHasButton)
{
[self willRotateToInterfaceOrientation:self.interfaceOrientation duration:0];
[self willAnimateRotationToInterfaceOrientation:self.interfaceOrientation duration:0];
[self didRotateFromInterfaceOrientation:self.interfaceOrientation];
}
Run Code Online (Sandbox Code Playgroud)
然而,这似乎导致无限循环回到viewWillLayoutSubviews:(
有谁知道模拟iOS4风格旋转事件的正确方法是从全屏幕模式后面出现的分割视图控制器?或者你根本不应该模拟它们,还有另一种最佳实践方法已经成为iOS5的标准吗?
任何帮助真的很感激,因为这个问题阻碍了我们将iOS5 bugfix版本提交到App Store.
Noa*_*son 10
我不知道处理这种情况的正确方法.但是,以下似乎在iOS 5中对我有用.
在splitViewController:willHideViewController:withBarButtonItem:forPopoverController:,存储对barButtonItem的引用self.barButtonItem.比如,将用于显示按钮的代码移动到单独的方法中ShowRootPopoverButtonItem.
在splitViewController:willShowViewController:invalidatingBarButtonItem:,明确指出self.barButtonItem.比如,将用于显示按钮的代码移动到单独的方法中InvalidateRootPopoverButtonItem.
在viewWillLayoutSubviews,手动显示或隐藏按钮,具体取决于界面方向
这是我的实现viewWillLayoutSubviews.请注意,调用self.interfaceOrientation总是返回肖像,因此我使用statusBarOrientation.
- (void)viewWillLayoutSubviews
{
if (UIInterfaceOrientationIsPortrait(
[UIApplication sharedApplication].statusBarOrientation))
{
[self ShowRootPopoverButtonItem:self.barButtonItem];
}
else
{
[self InvalidateRootPopoverButtonItem:self.barButtonItem];
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
4689 次 |
| 最近记录: |