Pat*_*ckV 12 uinavigationcontroller uisplitviewcontroller ios8
在我的UISplitViewController中,主视图是一个包含UITableViewController的UINavigationController.有时,当用户选择表中的项时,我必须在主视图中的现有表上推送另一个tableViewController.
在iOS 7中,在我的第一个UITableViewController中,我只是调用它
[self.navigationController pushViewController:otherTableVC animated:YES];
Run Code Online (Sandbox Code Playgroud)
在iOS 8中:
折叠拆分视图时,otherTableVC将成为详细视图!旋转设备后,我们并排看到两张桌子......
更糟糕的是,如果设备显示两个窗格,代码工作得很好,第二个表被推到主视图中的第一个表.但是,经过两次旋转后,两张桌子又是并排的.似乎UISplitViewController的折叠模式干扰了我自己的导航控制器......
如何在主视图中管理自己的UINavigationController?
谢谢
编辑:
我的主视图和详细信息视图都有一个导航控制器.为了解决我的问题,我刚刚发现,在折叠模式下,我必须创建一个额外的导航控制器并将其推送到主导航控制器上.
UINavigationController *navController = [[UINavigationController alloc] initWithRootViewController:otherTableVC];
[self.navigationController pushViewController:navController animated:YES];
Run Code Online (Sandbox Code Playgroud)
所以我发现帽子我们可以将导航控制器推到另一个导航控制器中.
小智 24
简而言之,您可以通过UISplitViewControllerDelegate方法控制此行为:
splitViewController:collapseSecondaryViewController:ontoPrimaryViewController:
splitViewController:separateSecondaryViewControllerFromPrimaryViewController:
Run Code Online (Sandbox Code Playgroud)
我怀疑你真正想做的是处理你有一个基于iOS 8 UISplitViewController的应用程序的情况,你的主要和详细视图都是UINavigationControllers,并且你想要只出现一些viewControllers(在这些导航控制器中)拆分视图的主要部分或细节部分.以下答案涉及此问题.它还可以处理您有时希望视图替换Detail导航控制器中的视图而不是被推到那里的情况.
一个小警告:下面的代码不处理所有可能的情况,并有一些假设:
我不建议只实现splitViewController的一面:collapseSecondaryViewController:ontoPrimaryViewController:/ splitViewController:separateSecondaryViewControllerFromPrimaryViewController:logic并取决于另一方的默认实现.Apple做了一些奇怪的事情,例如将UINavigationViewController从Detail端放入主要侧作为Primary导航控制器堆栈中的一个viewControllers,然后将其他视图控制器推到它上面,即使你完全理解仍然无法复制你自己的代码.因此,最好自己处理这两个过程.
这是我使用的:
#pragma mark -
#pragma mark Split View Controller delegate.
- (BOOL)splitViewController:(UISplitViewController *)splitViewController showViewController:(UIViewController *)vc sender:(id)sender
{
//Standard behaviour. This won't get called in our case when the split view is collapsed and the primary view controllers are obscured.
return NO;
}
// Since we treat warnings as errors, silence warning about unknown selector below on UIViewController subclasses.
#pragma GCC diagnostic ignored "-Wundeclared-selector"
- (BOOL)splitViewController:(UISplitViewController *)splitViewController showDetailViewController:(UIViewController *)vc sender:(id)sender
{
if (splitViewController.collapsed == NO)
{
// The navigation controller we'll be adding the view controller vc to.
UINavigationController *navController = splitViewController.viewControllers[1];
UIViewController *topDetailViewController = [navController.viewControllers lastObject];
if ([topDetailViewController isKindOfClass:[BlankViewController class]] ||
([vc respondsToSelector:@selector(shouldReplaceDetailedView)] && [vc performSelector:@selector(shouldReplaceDetailedView)]))
{
// Replace the (expanded) detail view with this new view controller.
[navController setViewControllers:@[vc] animated:NO];
}
else
{
// Otherwise, just push.
[navController pushViewController:vc animated:YES];
}
}
else
{
// Collapsed. Just push onto the conbined primary and detailed navigation controller.
UINavigationController *navController = splitViewController.viewControllers[0];
[navController pushViewController:vc animated:YES];
}
// We've handled this ourselves.
return YES;
}
- (BOOL)splitViewController:(UISplitViewController *)splitViewController collapseSecondaryViewController:(UIViewController *)secondaryViewController ontoPrimaryViewController:(UIViewController *)primaryViewController
{
UINavigationController *primaryNavController = (UINavigationController *)primaryViewController;
UINavigationController *secondaryNavController = (UINavigationController *)secondaryViewController;
UIViewController *bottomSecondaryView = [secondaryNavController.viewControllers firstObject];
if ([bottomSecondaryView isKindOfClass:[BlankViewController class]])
{
NSAssert([secondaryNavController.viewControllers count] == 1, @"BlankViewController is not only detail view controller");
// If our secondary controller is blank, do the collapse ourself by doing nothing.
return YES;
}
// We need to shift these view controllers ourselves.
// This should be the primary views and then the detailed views on top.
// Otherwise the UISplitViewController does wacky things like embedding a UINavigationController inside another UINavigation Controller, which causes problems for us later.
NSMutableArray *newPrimaryViewControllers = [NSMutableArray arrayWithArray:primaryNavController.viewControllers];
[newPrimaryViewControllers addObjectsFromArray:secondaryNavController.viewControllers];
primaryNavController.viewControllers = newPrimaryViewControllers;
return YES;
}
- (UIViewController *)splitViewController:(UISplitViewController *)splitViewController separateSecondaryViewControllerFromPrimaryViewController:(UIViewController *)primaryViewController
{
UINavigationController *primaryNavController = (UINavigationController *)primaryViewController;
// Split up the combined primary and detail navigation controller in their component primary and detail view controller lists, but with same ordering.
NSMutableArray *newPrimaryViewControllers = [NSMutableArray array];
NSMutableArray *newDetailViewControllers = [NSMutableArray array];
for (UIViewController *controller in primaryNavController.viewControllers)
{
if ([controller respondsToSelector:@selector(shouldDisplayInDetailedView)] && [controller performSelector:@selector(shouldDisplayInDetailedView)])
{
[newDetailViewControllers addObject:controller];
}
else
{
[newPrimaryViewControllers addObject:controller];
}
}
if (newDetailViewControllers.count == 0)
{
// If there's no detailed views on the top of the navigation stack, return a blank view (in navigation controller) for detailed side.
UINavigationController *blankDetailNavController = [[UINavigationController alloc] initWithRootViewController:[[BlankViewController alloc] init]];
return blankDetailNavController;
}
// Set the new primary views.
primaryNavController.viewControllers = newPrimaryViewControllers;
// Return the new detail navigation controller and views.
UINavigationController *detailNavController = [[UINavigationController alloc] init];
detailNavController.viewControllers = newDetailViewControllers;
return detailNavController;
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
11649 次 |
| 最近记录: |