在 Apples MultipleDetailViews 示例中加载已初始化的 DetailViewControllers
Apple 在其 iOS 开发网站上提供了一个有关如何使用具有不同详细视图的 splitview 的示例(请参阅 MultipleDetailViews 示例)。在 RootViewController 中,每次单元格被选中时,都会初始化一个新的 DetailViewController:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
/*
Create and configure a new detail view controller appropriate for the selection.
*/
NSUInteger row = indexPath.row;
UIViewController <SubstitutableDetailViewController> *detailViewController = nil;
if (row == 0) {
FirstDetailViewController *newDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
detailViewController = newDetailViewController;
}
if (row == 1) {
SecondDetailViewController *newDetailViewController = [[SecondDetailViewController alloc] initWithNibName:@"SecondDetailView" bundle:nil];
detailViewController = newDetailViewController;
}
// Update the split view controller's view controllers array.
NSArray *viewControllers = [[NSArray alloc] initWithObjects:self.navigationController, detailViewController, nil];
splitViewController.viewControllers = viewControllers;
[viewControllers release];
// Dismiss the popover if it's present.
if (popoverController != nil) {
[popoverController dismissPopoverAnimated:YES];
}
// Configure the new view controller's popover button (after the view has been displayed and its toolbar/navigation bar has been created).
if (rootPopoverButtonItem != nil) {
[detailViewController showRootPopoverButtonItem:self.rootPopoverButtonItem];
}
[detailViewController release];
}
现在我的想法是,不必每次都初始化视图控制器,只需在 viewDidLoad (以及标题)中初始化控制器,并在单元格被选中时传递它们的引用:
rootviewcontroller 中 viewDidLoad 的一部分:
firstDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
secondDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
现在 tableView didselectrow 方法如下所示:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
/*
Create and configure a new detail view controller appropriate for the selection.
*/
NSUInteger row = indexPath.row;
UIViewController <SubstitutableDetailViewController> *detailViewController = nil;
if (row == 0) {
detailViewController = firstDetailViewController;
}
if (row == 1) {
detailViewController = secondDetailViewController;
}
// Update the split view controller's view controllers array.
NSArray *viewControllers = [[NSArray alloc] initWithObjects:self.navigationController, detailViewController, nil];
splitViewController.viewControllers = viewControllers;
[viewControllers release];
// Dismiss the popover if it's present.
if (popoverController != nil) {
[popoverController dismissPopoverAnimated:YES];
}
// Configure the new view controller's popover button (after the view has been displayed and its toolbar/navigation bar has been created).
if (rootPopoverButtonItem != nil) {
[detailViewController showRootPopoverButtonItem:self.rootPopoverButtonItem];
}
//[detailViewController release];
}
在横向模式下一切正常,但在纵向模式下,从第一个detailviewcontroller,到第二个,然后到第一个,然后想切换到第二个。出现以下消息:由于未捕获的异常“NSInvalidArgumentException”而终止应用程序,原因:“无法从没有窗口的视图中呈现弹出窗口。”
从昨天晚上开始,我就试图解决这个问题,但没有找到解决方案。有人有想法吗?
干杯,多米尼克
Apple presents on their iOS Development sites an example on how to use a splitview with different detailviews (see MultipleDetailViews Example). In the RootViewController eery time the cell gets selected, a new DetailViewController is initialized:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
/*
Create and configure a new detail view controller appropriate for the selection.
*/
NSUInteger row = indexPath.row;
UIViewController <SubstitutableDetailViewController> *detailViewController = nil;
if (row == 0) {
FirstDetailViewController *newDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
detailViewController = newDetailViewController;
}
if (row == 1) {
SecondDetailViewController *newDetailViewController = [[SecondDetailViewController alloc] initWithNibName:@"SecondDetailView" bundle:nil];
detailViewController = newDetailViewController;
}
// Update the split view controller's view controllers array.
NSArray *viewControllers = [[NSArray alloc] initWithObjects:self.navigationController, detailViewController, nil];
splitViewController.viewControllers = viewControllers;
[viewControllers release];
// Dismiss the popover if it's present.
if (popoverController != nil) {
[popoverController dismissPopoverAnimated:YES];
}
// Configure the new view controller's popover button (after the view has been displayed and its toolbar/navigation bar has been created).
if (rootPopoverButtonItem != nil) {
[detailViewController showRootPopoverButtonItem:self.rootPopoverButtonItem];
}
[detailViewController release];
}
Now my idea is instead of initialising the viewcontrollers everytime, just initialize the controllers in the viewDidLoad (and also header) and pass the references of them when the cell gets selected:
part of the viewDidLoad in the rootviewcontroller:
firstDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
secondDetailViewController = [[FirstDetailViewController alloc] initWithNibName:@"FirstDetailView" bundle:nil];
Now the tableView didselectrow method looks like this:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
/*
Create and configure a new detail view controller appropriate for the selection.
*/
NSUInteger row = indexPath.row;
UIViewController <SubstitutableDetailViewController> *detailViewController = nil;
if (row == 0) {
detailViewController = firstDetailViewController;
}
if (row == 1) {
detailViewController = secondDetailViewController;
}
// Update the split view controller's view controllers array.
NSArray *viewControllers = [[NSArray alloc] initWithObjects:self.navigationController, detailViewController, nil];
splitViewController.viewControllers = viewControllers;
[viewControllers release];
// Dismiss the popover if it's present.
if (popoverController != nil) {
[popoverController dismissPopoverAnimated:YES];
}
// Configure the new view controller's popover button (after the view has been displayed and its toolbar/navigation bar has been created).
if (rootPopoverButtonItem != nil) {
[detailViewController showRootPopoverButtonItem:self.rootPopoverButtonItem];
}
//[detailViewController release];
}
In landscape mode everything works fine, but when in portrait mode a get an error, when switching from the firstdetailviewcontroller, to the second, then to the first and then want to switch to the second. Following message occurs: Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Popovers cannot be presented from a view which does not have a window.'
Since yesterday evening I am trying to figure this out, but i do not find a solution. Anybody an idea?
Cheers, Dominik
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
我有类似的问题,但我发现这个 post 演示了在设置 splitView 的视图控制器之前必须从先前的DetailView 中删除 leftBarButtonItem 的想法。这段代码为我解决了这个问题。
这是 TPoschel 编写的代码。
}
I had a similar issue, but I found this post that demonstrated the idea that you have to remove the leftBarButtonItem from the previous detailView before setting up the splitView's view controllers. This code fixed the issue for me.
This is the code from that written by TPoschel.
}