Jor*_*n H 173 interface-builder master-detail uisplitviewcontroller ios ios8
我在Xcode 6中使用通用故事板,目标是iOS 7及更高版本.我已经实现了一个UISplitViewController
现在支持运行iOS 8的iPhone本身支持,Xcode将自动向iOS 7后端移植.它运行得非常好,除非你在iPhone上以iOS 8纵向启动应用程序,拆分视图的详细视图我希望第一次看到主视图控制器时显示控制器.我相信这是iOS 8的一个错误,因为当您在iOS 7上运行应用程序时,它会正确显示主视图控制器.但iOS 8现在是通用汽车,而且这种情况仍在发生.如何进行设置以便在拆分拆分视图控制器时(屏幕上只显示一个视图控制器),当显示拆分视图控制器时,它会显示主视图控制器而不是详细信息?
我在Interface Builder中创建了这个拆分视图控制器.拆分视图控制器是标签栏控制器中的第一个视图控制器.主控和详细VC都是导航控制器,其中嵌入了表视图控制器.
小智 234
哦,伙计,这让我头疼了几天,无法弄清楚如何做到这一点.最糟糕的是,使用master-detail模板创建一个新的Xcode iOS项目工作得很好.幸运的是,最后,我找到解决方案的那个小事实.
我发现有一些帖子表明解决方案是实现新primaryViewControllerForCollapsingSplitViewController:
方法UISplitViewControllerDelegate
.我试过没有用.Apple在主要细节模板中所做的工作似乎是实现新的(深呼吸说出所有这一切)splitViewController:collapseSecondaryViewController:ontoPrimaryViewController:
委托方法(再次UISplitViewControllerDelegate
).根据文档,这种方法:
要求代理调整主视图控制器并将辅助视图控制器合并到折叠界面中.
请务必阅读该方法的讨论部分以获取更具体的详细信息.
Apple处理此问题的方式是:
- (BOOL)splitViewController:(UISplitViewController *)splitViewController
collapseSecondaryViewController:(UIViewController *)secondaryViewController
ontoPrimaryViewController:(UIViewController *)primaryViewController {
if ([secondaryViewController isKindOfClass:[UINavigationController class]]
&& [[(UINavigationController *)secondaryViewController topViewController] isKindOfClass:[DetailViewController class]]
&& ([(DetailViewController *)[(UINavigationController *)secondaryViewController topViewController] detailItem] == nil)) {
// Return YES to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
return YES;
} else {
return NO;
}
}
Run Code Online (Sandbox Code Playgroud)
此实现基本上执行以下操作:
secondaryViewController
是我们期待的(a UINavigationController
),并且它显示了我们期望的东西(a DetailViewController
- 你的视图控制器),但是没有模型(detailItem
),那么" Return YES to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
"NO
让分割视图控制器尝试并将辅助视图控制器的内容合并到折叠的界面中"iPhone的纵向结果如下(从纵向开始或纵向旋转 - 或者更精确的紧凑尺寸类):
清除泥土.
Cli*_*rum 60
以下是Swift中接受的答案.只需创建此子类并将其分配给故事板中的splitViewController即可.
//GlobalSplitViewController.swift
import UIKit
class GlobalSplitViewController: UISplitViewController, UISplitViewControllerDelegate {
override func viewDidLoad() {
super.viewDidLoad()
self.delegate = self
}
func splitViewController(splitViewController: UISplitViewController, collapseSecondaryViewController secondaryViewController: UIViewController!, ontoPrimaryViewController primaryViewController: UIViewController!) -> Bool{
return true
}
}
Run Code Online (Sandbox Code Playgroud)
Niñ*_*ipt 19
由Apple的Master-Detail模板提供.
func splitViewController(splitViewController: UISplitViewController, collapseSecondaryViewController secondaryViewController:UIViewController, ontoPrimaryViewController primaryViewController:UIViewController) -> Bool {
guard let secondaryAsNavController = secondaryViewController as? UINavigationController else { return false }
guard let topAsDetailController = secondaryAsNavController.topViewController as? DetailViewController else { return false }
if topAsDetailController.detailItem == nil {
// Return true to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
return true
}
return false
}
Run Code Online (Sandbox Code Playgroud)
(Mark S所说的有些令人困惑)
调用此委托方法splitViewController: collapseSecondaryViewController: ontoPrimaryViewController:
,因为它就是它的作用.当更改为更紧凑的宽度尺寸时(例如,将手机从横向旋转到纵向时),需要将拆分视图控制器折叠为其中一个.
此函数返回一个布尔值,以决定是否应折叠Detail并显示Master.
因此,在我们的案例中,我们将根据是否选择了详细信息来决定.我们如何知道我们的细节是否被选中?如果我们遵循Apple的Master-Detail模板,详细视图控制器应该有一个带有详细信息的可选变量,所以如果它是nil(.None),则没有选择任何东西,我们应该显示Master,以便用户可以选择一些东西.
而已.
我的应用程序是用Swift 2.x编写的,运行良好.将其转换为Swift 3.0(使用XCode转换器)后,它首先开始显示细节,而不是纵向模式下的master.问题是函数splitViewController的名称未更改为与UISplitViewControllerDelegate的新名称匹配.
手动更改该功能的名称后,我的应用程序现在可以正常工作:
func splitViewController(_ splitViewController: UISplitViewController, collapseSecondary secondaryViewController:UIViewController, onto primaryViewController:UIViewController) -> Bool {
guard let secondaryAsNavController = secondaryViewController as? UINavigationController else { return false }
guard let topAsDetailController = secondaryAsNavController.topViewController as? DetailViewController else { return false }
if topAsDetailController.game == nil {
// Return true to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
return true
}
return false
}
Run Code Online (Sandbox Code Playgroud)
从文档中,您需要使用委托来告诉UISplitViewController
不要将详细视图合并到"折叠界面"(即您的情况下的"纵向模式").在Swift 4中,为其实现的委托方法已重命名:
func splitViewController(_ splitViewController: UISplitViewController, collapseSecondary secondaryViewController:UIViewController, onto primaryViewController:UIViewController) -> Bool {
return true
}
Run Code Online (Sandbox Code Playgroud)
#import <UIKit/UIKit.h>
@interface SplitProductView : UISplitViewController<UISplitViewControllerDelegate>
@end
Run Code Online (Sandbox Code Playgroud)
.M:
#import "SplitProductView.h"
#import "PriceDetailTableView.h"
@interface SplitProductView ()
@end
@implementation SplitProductView
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view.
self.delegate = self;
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
/*
#pragma mark - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
// Get the new view controller using [segue destinationViewController].
// Pass the selected object to the new view controller.
}
*/
- (BOOL)splitViewController:(UISplitViewController *)splitViewController
collapseSecondaryViewController:(UIViewController *)secondaryViewController
ontoPrimaryViewController:(UIViewController *)primaryViewController {
if ([secondaryViewController isKindOfClass:[UINavigationController class]]
&& [[(UINavigationController *)secondaryViewController topViewController] isKindOfClass:[PriceDetailTableView class]]
//&& ([(PriceDetailTableView *)[(UINavigationController *)secondaryViewController topViewController] detailItem] == nil)
) {
// Return YES to indicate that we have handled the collapse by doing nothing; the secondary controller will be discarded.
return YES;
} else {
return NO;
}
}
@end
Run Code Online (Sandbox Code Playgroud)
小智 7
如果您没有要在详细视图控制器中显示的默认值,您只需删除故事板中SplitViewController和详细信息UIViewController之间的默认segue.这将使它始终首先进入主视图控制器.
这样做的副作用是,在横向视图中看不到两个视图,您将在SplitViewController中看到一个完整大小的视图,直到主视图控制器中的Show Detail Segue被触发.
归档时间: |
|
查看次数: |
56460 次 |
最近记录: |