从父iOS访问容器视图控制器

Ada*_*ite 198 objective-c uiviewcontroller ios uicontainerview swift

在iOS6中,我注意到了新的Container View,但我不太确定如何从包含视图访问它的控制器.

场景:

例

我想从容纳容器视图的视图控制器访问Alert视图控制器中的标签.

它们之间有一个区别,我能用它吗?

Pet*_*r E 360

是的,您可以使用segue访问子视图控制器(及其视图和子视图).alertview_embed使用Storyboard中的Attributes检查器为segue指定标识符(例如).然后让父视图控制器(容纳容器视图的那个)实现这样的方法:

- (void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
   NSString * segueName = segue.identifier;
   if ([segueName isEqualToString: @"alertview_embed"]) {
       AlertViewController * childViewController = (AlertViewController *) [segue destinationViewController];
       AlertView * alertView = childViewController.view;
       // do something with the AlertView's subviews here...
   }
}
Run Code Online (Sandbox Code Playgroud)

  • 是的,当第二个视图控制器成为第一个视图控制器的子节点时,会出现一个嵌入segue.prepareForSegue:在此之前调用.您可以利用此机会将数据传递给子项,或者存储对子项的引用以供以后使用.另见http://developer.apple.com/library/ios/#documentation/uikit/reference/UIStoryboardSegue_Class/Reference/Reference.html (24认同)
  • 我将在建议的解决方案中添加一个警告:在访问(子)目标视图控制器的视图属性时要非常小心:在某些情况下,这将导致其viewDidLoad在那里被调用然后.我建议事先设置任何所需的segue数据以便viewDidLoad可以安全地触发. (2认同)

rde*_*mar 55

您可以简单地使用self.childViewControllers.lastObject(假设您只有一个孩子,否则使用objectAtIndex:).

  • @Fydo,处理'准备segue'中的所有多个容器有什么问题? (2认同)
  • 这是我通常的做法,但现在它崩溃了,因为我太快访问`childViewControllers`了 (2认同)

Sru*_*Suk 24

用于Swift编程

你可以写这样的

var containerViewController: ExampleViewController?
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
    // you can set this name in 'segue.embed' in storyboard
    if segue.identifier == "checkinPopupIdentifierInStoryBoard" {
        let connectContainerViewController = segue.destinationViewController as ExampleViewController
        containerViewController = connectContainerViewController
    }
}
Run Code Online (Sandbox Code Playgroud)


Sim*_*lGy 17

prepareForSegue方法有效,但它依赖于segue标识符魔术字符串.也许有更好的方法.

如果你知道你所追求的VC的类,你可以非常巧妙地使用计算属性:

var camperVan: CamperVanViewController? {
  return childViewControllers.flatMap({ $0 as? CamperVanViewController }).first
  // This works because `flatMap` removes nils
}
Run Code Online (Sandbox Code Playgroud)

这取决于childViewControllers.虽然我同意依靠第一个可能很脆弱,但是你所寻找的课程命名使它看起来非常可靠.

  • `return childViewControllers.filter {$ 0是CamperVanViewController} .first` in one liner (3认同)

Rob*_*rty 9

Swift 3的更新答案,使用计算属性:

var jobSummaryViewController: JobSummaryViewController {
    get {
        let ctrl = childViewControllers.first(where: { $0 is JobSummaryViewController })
        return ctrl as! JobSummaryViewController
    }
}
Run Code Online (Sandbox Code Playgroud)

这只会迭代子列表,直到达到第一个匹配.


Gau*_*ain 8

self.childViewControllers 当你需要来自父母的控制时更相关.例如,如果子控制器是一个表视图,并且您想要通过按钮点击或父视图控制器上的任何其他事件强制重新加载它或更改属性,则可以通过访问ChildViewController的实例而不是通过prepareForSegue来完成.两者都以不同的方式应用.