我正在尝试从xCode 6模板开发一个主细节iOS应用程序(仅限iPad)。它在iOS 8上运行良好,但在iOS 7.0或7.1上运行会在运行时产生崩溃,我评论道:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
UISplitViewController *splitViewController = (UISplitViewController *)self.window.rootViewController;
UINavigationController *navigationController = [splitViewController.viewControllers lastObject];
// this line throws a "[MasterViewController topViewController]: unrecognized selector sent to instance 0x796dde90"
navigationController.topViewController.navigationItem.leftBarButtonItem = splitViewController.displayModeButtonItem;
splitViewController.delegate = self;
return YES;
}
重现错误:
- 打开xCode 6
- 文件>新建>项目
- 在"iOS应用程序"下方选择"Master Details应用程序"
- 将项目目标更改为7.0
- 在模拟器或设备上运行
我调查了一下,似乎iOS 7和iOS 8上的对象类型不同:
- 在iOS8上,self.window.rootViewController是一个UISplitViewController
- 在iOS7上,self.window.rootViewController是第一个UINavigationController(左)
为什么会有这种行为?
将其置于prepareForSegue:
下以确保向后兼容性。
DetailViewController *controller;
if ([[segue destinationViewController] isKindOfClass:[UINavigationController class]]) {
controller = (DetailViewController *)[[segue destinationViewController] topViewController];
}
else {
controller = (DetailViewController *)[segue destinationViewController];
}
[controller setDetailItem:object];
尝试此替换:
if ([splitViewController respondsToSelector:@selector(displayModeButtonItem)]){
navigationController.topViewController.navigationItem.leftBarButtonItem = splitViewController.displayModeButtonItem;
}
工程师似乎忘记检查他的模板的向后兼容性。使用xCode 5.1.1主细节模板中的故事板解决了问题。对于那些来自谷歌的人,你可以在这里下载xCode 5.1.1:https://developer.apple.com/devcenter/download.action?path=/Developer_Tools/xcode_5.1.1/xcode_5.1.1.dmg
displayModeButtonItem
仅适用于iOS 8或更高版本。