在单个窗口界面中跨多个视图控制器绑定选择

时间:2010-03-03 01:33:29

标签: core-data binding nsarraycontroller nsviewcontroller nsobjectcontroller

我遇到了一个问题,即如何在两个视图控制器之间连接几个NSArrayControllers。我想在源列表表视图中同步选择以更新第二个详细信息视图控制器中的值。

我使用Cocoa Dev Central Build A Core Data Tutorial作为起点,但已经破坏了架构,因此有一个NSWindowController包含两个NSViewControllers:一个用于左边的posts表,另一个用于post的详细信息右边。

NSWindowController子类有一个绑定到Post实体的NSArrayController和一个指向[[NSApp delegate] managedObjectContext]

的只读managedObjectContext访问器

然后我在windowDidLoad方法中初始化两个视图控制器。

- (void)windowDidLoad
{
  static NSInteger kSourceListViewIndex = 0;
  static NSInteger kDetailViewIndex = 1;

  self.postsListsViewController = [[MDVCPostsListViewController alloc] initWithWindowController:self];  
    NSView *sourceListSplitViewContentView = [[self.splitView subviews] objectAtIndex:kSourceListViewIndex];
  NSView *sourceListView = [self.postsListsViewController view];
  [sourceListView setFrame:[sourceListSplitViewContentView bounds]];
  [sourceListView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
  [sourceListSplitViewContentView addSubview:sourceListView]; 

  // And now let's load the detail view.
  self.postDetailViewController = [[MDVCPostDetailViewController alloc] initWithWindowController:self];
    NSView *detailSplitViewContentView = [[self.splitView subviews] objectAtIndex:kDetailViewIndex];
  NSView *detailView = [self.postDetailViewController view];
  [detailView setFrame:[detailSplitViewContentView bounds]];
  [detailView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
  [detailSplitViewContentView addSubview:detailView]; 
}

MDVCPostsListViewController有一个绑定到Post实体的NSArrayController及其绑定到父窗口控制器的托管对象上下文的托管对象上下文(全部通过Interface Builder)

MDVCPostDetailViewController有一个NSObjectController绑定到窗口控制器的托管对象上下文,内容对象通过postsListsViewController.postsArrayController.selection绑定到窗口控制器。这似乎是一个非常糟糕的黑客。

如何更改MDVCPostsListViewController的表格视图中的选项以更新MDVCPostDetailViewController中的选定值?我觉得我很亲近,但我不确定缺少什么或者最佳路线是什么。我觉得postsListsViewController.postsArrayController.selection绑定是非常hacky。希望有更好的方法。

我上传了我的示例项目,展示了那些喜欢查看代码而不仅仅是阅读描述的人。您可以在我的网站http://www.secondgearsoftware.com/attachments/stackoverflow_objectcontroller.zip

抓取它

2 个答案:

答案 0 :(得分:3)

您希望每个窗口控制器如何发现主窗口控制器?

从快速浏览一下该项目,您似乎只是向每个NIB添加了一个MDVCMainWindowController实例。这些将是实际运行主窗口的实例。

您需要将源列表表selectionIndexes绑定到Post数组控制器。否则,将无法在控制器级别知道选择。

我建议将阵列控制器移动到主窗口控制器中。在windowDidLoad方法中,您可以将其传递给列表和详细信息视图。该列表将绑定到arrangeObjects和selectionIndexes,详细信息视图将绑定到selection.someKey。

答案 1 :(得分:1)

问题在于详细视图xib中NSObjectController实例的内容对象绑定。列表视图xib中的数组控制器正确发布KVO通知(通过使MDVCPostDetailViewController实例用KVO观察这个来检查),所以我不确定原因,但由于某种原因,对象控制器没有响应它们。 / p>

但是,您可以采取几种不同的方法。您可以删除对象控制器并将详细视图xib中的文本字段等直接绑定到数组控制器(File的Owner.windowController.postsListsViewController.postsArrayController.selection.whatever)。或者,您可以保留对象控制器并让您的详细视图控制器观察数组控制器的选择属性,并在选择更改时“手动”设置对象控制器的内容对象属性。